Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
8a60094
feat(video-call): Enhance Windows Graphics Capture handling in RDP se…
jeanfbrito Nov 24, 2025
1eb676d
fix(rollup): Update output directory for preload files
jeanfbrito Nov 24, 2025
f8534e2
fix(i18n): Update Russian translation for video call screen capture f…
jeanfbrito Nov 24, 2025
1336cb2
Merge remote-tracking branch 'origin/fix-rdp-wgc-issues' into fix-rdp…
jeanfbrito Nov 27, 2025
ce05fb8
refactor(videoCall): Clean up code formatting and improve readability
jeanfbrito Nov 27, 2025
4dadbf2
refactor(videoCall): Migrate video call window to TypeScript and enha…
jeanfbrito Nov 27, 2025
6378c41
refactor(videoCall): Simplify ScreenSharePicker component and improve…
jeanfbrito Nov 27, 2025
a77d6a5
refactor(videoCall): Update preload script path in video call window
jeanfbrito Nov 27, 2025
f5a0e0a
refactor(videoCall): Enhance ScreenSharePicker and improve preload sc…
jeanfbrito Nov 27, 2025
b4d3f68
feat(videoCall): Add prewarm capturer cache functionality and enhance…
jeanfbrito Nov 27, 2025
4be9285
feat(videoCall): Enhance video call window and screen sharing flow
jeanfbrito Nov 27, 2025
6a1cc97
refactor(videoCall): Improve video call webview detection and preload…
jeanfbrito Nov 27, 2025
3c5cbc1
feat(videoCall): Update screen picker IPC handling and improve URL re…
jeanfbrito Nov 28, 2025
69371df
fix(videoCall): Reset screen picker promise on error to prevent stale…
jeanfbrito Nov 28, 2025
85b2f18
fix(videoCall): Add missing type import for screenPickerModulePromise
jeanfbrito Nov 28, 2025
a913a3b
fix(videoCall): Ensure visibility state is reset on screen share pick…
jeanfbrito Nov 28, 2025
9773781
Fix markdownlint MD040: Add language identifiers to code blocks
jeanfbrito Nov 28, 2025
344b652
feat(videoCall): Enhance video call webview handling and URL validation
jeanfbrito Nov 28, 2025
1271425
feat(videoCall): Revise video call window documentation and enhance p…
jeanfbrito Nov 28, 2025
f1e9b18
fix(videoCall): Simplify webview webpreferences attribute
jeanfbrito Dec 1, 2025
66db25a
feat(notifications): Add category field to notifications for better c…
jeanfbrito Dec 1, 2025
857e1e7
fix(videoCall): Update webview preferences and partition naming
jeanfbrito Dec 2, 2025
ef0e178
Merge branch 'master' into fix-rdp-wgc-issues
jeanfbrito Dec 3, 2025
5737e25
feat(videoCall): Enhance screen sharing documentation and implement s…
jeanfbrito Dec 3, 2025
edee7c3
fix(videoCall): Update video call webview handling by removing unused…
jeanfbrito Dec 3, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
550 changes: 362 additions & 188 deletions docs/video-call-screen-sharing.md

Large diffs are not rendered by default.

206 changes: 168 additions & 38 deletions docs/video-call-window-flow.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,64 +2,194 @@

## Overview

The video call window system in Rocket.Chat Electron has two main parts:

1. **Window Management** - How the video call window is created and managed
2. **Screen Sharing** - How screen sharing works within the video call
The video call window system in Rocket.Chat Electron provides a dedicated, high-performance environment for video conferencing with any provider (Jitsi, PEXIP, self-hosted, and others). The core system is provider-agnostic and works with any HTTP/HTTPS video call URL.

## Architecture

The system uses a **vanilla JavaScript bootstrap** with **deferred React loading**:

```
┌─────────────────────────────────────────────────────────────┐
│ Video Call Window │
├─────────────────────────────────────────────────────────────┤
│ video-call-window.ts (Vanilla JS) │
│ ├── i18n initialization │
│ ├── Webview lifecycle management │
│ ├── Loading/error overlays (DOM) │
│ └── IPC communication │
├─────────────────────────────────────────────────────────────┤
│ screenSharePickerMount.tsx (React - Lazy Loaded) │
│ └── ScreenSharePicker component │
├─────────────────────────────────────────────────────────────┤
│ Desktop Capturer Cache (Stale-While-Revalidate) │
│ ├── Pre-warmed on webview load │
│ ├── Instant response, background refresh │
│ └── Persists across calls │
└─────────────────────────────────────────────────────────────┘
```

**Key design decisions:**
- Vanilla JS for critical path (faster load, simpler recovery)
- React only for ScreenSharePicker (complex UI component)
- Stale-while-revalidate caching (instant UX, fresh data)
- Cache pre-warming (no loading state on first screen share)

## Documentation Files

### 📊 [Window Management Flow](./video-call-window-management.md)
**What it covers:** How Rocket.Chat opens a video call window when you click a video call button.
### [Window Management Flow](./video-call-window-management.md)

**What it covers:** Complete lifecycle from click to active video call.

This document explains the complete process from when you click "Join Call" to when you see a working video call interface. It shows how the app creates a separate window for your video call, sets it up safely, handles any problems that might occur, and makes sure everything works reliably even on slower computers.
This document explains the vanilla JS architecture that manages the video call window. It shows how the app creates a separate window, initializes without React overhead, handles loading states through direct DOM manipulation, and provides automatic error recovery.

**You'll learn about:**
- How the app validates video call URLs for security
- Why video calls open in separate windows
- How the app handles errors and tries to fix them automatically
- The retry system that makes video calls work reliably
- How multiple attempts ensure success even with slow internet
- What happens when you close a video call window
- ✨ **New**: Smart loading system that prevents flicker and loading interruptions
- Vanilla JS bootstrap architecture
- Why React is deferred (performance benefits)
- Webview creation and attribute ordering
- Loading and error overlay management
- Smart loading system (no flicker, no interruption)
- Progressive error recovery strategies
- Window cleanup and resource management

**Perfect for understanding:** Why video calls sometimes take a moment to open, how the app recovers from problems, and what's happening behind the scenes when you start a video call.
**Architecture highlights:**
- No React in critical path
- Direct DOM manipulation for overlays
- Deferred React import for screen sharing
- Cache pre-warming on load completion

### 🖥️ [Screen Sharing Flow](./video-call-screen-sharing.md)
**What it covers:** How screen sharing works when you're already in a video call.
### [Screen Sharing Flow](./video-call-screen-sharing.md)

This document explains what happens when you click the screen share button during a video call. It shows how the app finds all your windows and screens, how it makes the selection process fast with smart caching, and how it ensures what you choose actually works before sharing it with others.
**What it covers:** Screen sharing with stale-while-revalidate caching.

This document explains the caching architecture that makes screen sharing feel instant. It shows how the cache is pre-warmed when the video call loads, how stale data is returned immediately while fresh data is fetched in the background, and why the cache persists indefinitely.

**You'll learn about:**
- How the app discovers all your open windows and screens
- Why screen sharing feels instant the second time you use it
- How the app organizes your options into easy-to-use tabs
- The smart caching system that makes everything fast
- How the app handles closed windows and disconnected screens
- What happens to memory and cache when you end calls
- Stale-while-revalidate pattern
- Cache pre-warming strategy
- Why cache never expires
- Background refresh mechanics
- Deferred React loading for picker
- Source validation and filtering
- Memory usage characteristics

**Cache characteristics:**
- Always returns data immediately
- Background refresh when stale (>3s)
- Persists until app quit or error

**Perfect for understanding:** Why screen sharing opens quickly, how the preview thumbnails are generated, what the app does when windows disappear, and how it manages computer resources efficiently.
### [WGC Limitations](./video-call-window-wgc-limitations.md)

**What it covers:** Windows Graphics Capture limitations and workarounds.

This document explains why screen sharing fails in Remote Desktop (RDP) sessions and how the app handles this through automatic detection and fallback mechanisms.

## How They Work Together

### The Complete User Journey

1. **📊 Window Management** → You click a video call button, and the app creates a working video call window
2. **🖥️ Screen Sharing** → While in the call, you click screen share and select what to share
```
1. User clicks video call button
└─► Window Management Flow
├── Create BrowserWindow
├── Vanilla JS bootstrap
├── Load webview with provider URL
└── Pre-warm desktop capturer cache

2. Video call active
└─► User clicks screen share
└─► Screen Sharing Flow
├── Show ScreenSharePicker (React, lazy loaded)
├── Return cached sources instantly
├── Background refresh if stale
└── Stream selected source
```

### Real-World Example

**Starting a call:**
- You click "Join Video Call" in a Rocket.Chat message
- Window Management Flow takes over
- A new window opens and loads the video call interface
- You see other participants and can talk/video chat
1. Click "Join Video Call" in Rocket.Chat
2. Window Management Flow creates dedicated window
3. Vanilla JS shows loading overlay with localized text
4. Webview loads video call provider interface (Jitsi, PEXIP, or any provider)
5. Cache pre-warmed in background
6. Loading overlay hidden, video call visible
7. If Jitsi: jitsiBridge auto-detects and initializes (required for screen sharing)

**Sharing your screen:**
- You click the screen share button in the video call
- Screen Sharing Flow takes over
- A small window shows all your options with preview images
- You click on a window or screen to share it
- Others in the call immediately see what you're sharing

Both systems work together seamlessly to give you a complete video calling experience that's fast, reliable, and easy to use.
1. Click screen share button in video call
2. ScreenSharePicker React component loaded (first time) or shown
3. Cached sources displayed instantly (no loading spinner)
4. Background refresh updates thumbnails if stale
5. Select window or screen
6. Stream starts immediately

## Key Innovations

### Vanilla JS Bootstrap
Traditional Electron apps render everything with React. This video call window uses vanilla JavaScript for the critical path:
- **Faster startup**: No React bundle to parse/execute initially
- **Simpler recovery**: Direct DOM manipulation, no state management
- **Lower memory**: React only loaded when needed

### Stale-While-Revalidate Cache
Traditional caching uses TTL (time-to-live) expiration. This system uses stale-while-revalidate:
- **Always instant**: Returns cached data immediately
- **Always fresh**: Background refresh keeps data current
- **Never empty**: Cache persists, no expiration
- **Error resilient**: Keeps last good data on fetch failure

### Cache Pre-warming
Traditional apps fetch data on demand. This system pre-warms:
- **Proactive fetch**: Cache populated when webview loads
- **Zero wait**: First screen share shows sources instantly
- **Background operation**: No impact on video call startup

## Provider Support

The video call window is designed to work with any video conferencing provider. The core system is generic and provider-agnostic:

### Generic Support (All Providers)
- **URL validation**: Only checks HTTP/HTTPS protocol (no provider-specific patterns)
- **Webview lifecycle**: Standard Electron webview handling
- **Screen sharing**: Uses generic Electron desktop capturer API
- **Partition**: Uses generic `persist:video-call-session` partition

### Jitsi-Specific Requirements
For Jitsi servers, a required bridge module (`jitsiBridge.ts`) is essential for screen sharing:
- **Auto-detection**: Automatically detects Jitsi meetings and initializes integration
- **Screen sharing coordination**: Required for screen sharing to work with Jitsi's External API
- **Event handling**: Listens for Jitsi-specific events and messages

**Important**: The jitsiBridge is **required** for Jitsi calls - screen sharing will not work without it. Other providers (like PEXIP) work with the standard generic events and do not need a bridge.

### PEXIP and Other Providers
PEXIP and other providers work seamlessly with the generic event system:
- No special bridge code required
- Uses standard webview events and IPC communication
- Screen sharing works through the generic desktop capturer API
- Easier to integrate than Jitsi (no bridge needed)

## File Structure

```
src/videoCallWindow/
├── video-call-window.ts # Vanilla JS bootstrap (generic)
├── screenSharePicker.tsx # React screen picker UI (generic)
├── screenSharePickerMount.tsx # React mounting utilities (generic)
├── ipc.ts # Main process handlers (generic)
└── preload/
├── index.ts # Webview preload script (generic)
└── jitsiBridge.ts # Jitsi-specific bridge (required for Jitsi screen sharing)

src/public/
├── video-call-window.html # Window HTML with overlay containers
├── loading.css # Loading overlay styles
└── error.css # Error overlay styles
```

## Related Documentation

- [Supported Versions Flow](./supported-versions-flow.md) - Server version compatibility
- [Testing Documentation](./testing/) - Test procedures and guidelines

Both window management and screen sharing systems work together seamlessly to provide a fast, reliable, and user-friendly video calling experience.
Loading
Loading