How Fluxer Display Media Capture Works: Source Caching and Cross-Platform Handling

Fluxer implements display media capture through a coordinated Electron main-renderer architecture that uses per-request caching, a global 60-second source cache, and platform-specific fallbacks to handle screen sharing across Windows, macOS, and Linux.

Fluxer's screen sharing system is built into its desktop Electron process and manages navigator.mediaDevices.getDisplayMedia requests through a custom IPC pipeline. According to the fluxerapp/fluxer source code, the implementation balances performance optimization through source caching with strict cross-platform compatibility requirements, particularly for Linux portal environments.

Architecture Overview

The display media capture system operates across three coordinated components: the Electron main process handler, the source caching layer, and the renderer-side picker interface.

Main Process Handler in Window.tsx

In src/main/Window.tsx, Fluxer registers a display-media request handler on each Electron Session via setupDisplayMediaHandler. When a renderer invokes getDisplayMedia, the handler generates a unique requestId using the format display-media-${++displayMediaRequestCounter} and forwards the request to the renderer via IPC (webContents.send('display-media-requested', …)).

The handler stores the resolution callback in a pendingDisplayMediaRequests map and initiates a 60-second timeout that auto-rejects the request if the UI remains unresponsive. This prevents dangling promises from orphaned picker windows.

Renderer Coordination via Preload Scripts

The preload script at src/preload/index.tsx exposes three critical IPC helpers to the web context:

  • onDisplayMediaRequested: Listens for main-process display-media events
  • selectDisplayMediaSource: Transmits the user's source selection back to the main process
  • getDesktopSources: Retrieves cached source lists or triggers fresh captures

Request Lifecycle and Timeout Management

Fluxer implements strict request lifecycle management to prevent memory leaks and zombie picker states.

When the main process receives a getDisplayMedia call, it:

  1. Generates a unique request identifier
  2. Stores the pending callback with a 60-second timeout timer
  3. Awaits the select-display-media-source IPC message from the renderer

If the user selects a source, the main process resolves the pending request, clears the timeout, and invokes the callback with an Electron.Streams object. If the timeout expires or the user cancels, the callback receives null to reject the promise.

Source Caching Strategy

Fluxer employs a dual-layer caching system to minimize redundant calls to desktopCapturer.getSources while avoiding stale data on dynamic desktop environments.

Global Cache with TTL

When the renderer requests desktop sources via get-desktop-sources, the main process calls desktopCapturer.getSources and caches the result in latestDesktopSources alongside a latestDesktopSourcesTimestamp. This global cache remains valid for 60 seconds (controlled by DESKTOP_SOURCE_CACHE_TTL_MS).

Per-Request Cache Attachment

The request handler can attach the cached source list to individual pending requests. When a display-media-requested event fires, the handler checks for cached sources and attaches them to pending.cachedSources if available. During source selection, the code prefers the per-request cache, falling back to the global cache if fresh.

Cross-Platform Handling and Limitations

Fluxer adapts its caching behavior based on the operating system to accommodate platform-specific constraints in screen capture permissions and portal implementations.

Windows (win32)

On Windows, Fluxer fully utilizes both the per-request and global caches within the 60-second TTL. The platform supports loopback audio capture by setting streams.audio = 'loopback' in the returned stream configuration.

macOS (darwin)

macOS follows the same caching logic as Windows but adds a native permission check. Before displaying the picker UI, Fluxer verifies that the application holds screen recording permission using system APIs. Unlike Windows, macOS does not support loopback audio through this mechanism, though system audio can be added through secondary means.

Linux (linux) Portal Limitations

Linux requires special handling due to XDG Desktop Portal behavior. The source code explicitly excludes Linux from global cache reuse for new requests to prevent duplicate portal picker windows from appearing.

If a display media request arrives and the global cache has expired, the main process immediately cancels the pending request by calling pending.callback(null) and forces the UI to re-initiate a fresh picker workflow. This ensures users never encounter conflicting permission dialogs. Linux also lacks built-in loopback audio support in this implementation.

Renderer-Side Picker Implementation

The React hook useElectronScreenSharePicker.tsx in the renderer process orchestrates the user-facing picker flow:

  1. Registers the onDisplayMediaRequested listener
  2. Validates that video is requested (rejects audio-only calls)
  3. On macOS, verifies native screen-recording permissions
  4. Fetches sources via electronApi.getDesktopSources
  5. Automatic selection: If only one source exists, it selects immediately without showing a modal
  6. Manual selection: If multiple sources exist, opens ScreenShareSourceModal for user choice
  7. Transmits the selection via selectDisplayMediaSource or cancels on timeout

Summary

  • Fluxer intercepts getDisplayMedia calls in the Electron main process using setupDisplayMediaHandler in Window.tsx, assigning unique request IDs and 60-second timeouts.
  • The system maintains a global 60-second source cache and per-request cached source lists to optimize performance, stored in latestDesktopSources.
  • Windows supports full caching and loopback audio; macOS adds native permission verification but lacks loopback support.
  • Linux never reuses stale caches for new requests to avoid duplicate portal windows, cancelling requests immediately if the cache misses.
  • The renderer-side React hook handles automatic single-source selection and modal-based multi-source picking through IPC exposed in preload/index.tsx.

Frequently Asked Questions

How does Fluxer prevent duplicate permission dialogs on Linux?

Fluxer explicitly disables cache reuse for display media requests on Linux. If the global source cache has expired when a new request arrives, the main process immediately cancels the pending callback with null and forces the UI to re-initiate a fresh capture workflow. This prevents the XDG Desktop Portal from spawning multiple concurrent picker windows.

What happens if the user doesn't select a source within 60 seconds?

The main process starts a 60-second timeout timer when a display media request enters the pendingDisplayMediaRequests map. If the timeout expires before the renderer sends a select-display-media-source message, the stored callback is invoked with null, rejecting the getDisplayMedia promise and cleaning up the pending request entry.

Does Fluxer support system audio capture during screen sharing?

Audio support varies by platform. Windows supports loopback audio via streams.audio = 'loopback'. macOS does not support loopback audio through this mechanism but can capture system audio through additional configuration. Linux has no built-in loopback audio support in the current implementation.

How does Fluxer handle single-source vs. multi-source scenarios?

In useElectronScreenSharePicker.tsx, the renderer checks the length of the cached source list returned by getDesktopSources. If exactly one source exists, it automatically selects that source and sends the selection to the main process without displaying a modal. If multiple sources exist, it renders the ScreenShareSourceModal component to let the user choose between available displays and windows.

Have a question about this repo?

These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:

Share the following with your agent to get started:
curl -s "https://instagit.com/install.md"

Works with
Claude Codex Cursor VS Code OpenClaw Any MCP Client

Maintain an open-source project? Get it listed too →