npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@webrtc2/ui

v1.0.0

Published

WebRTC2 UI - Cross-platform React components for WebRTC applications including video calls, audio controls, and media device management

Readme

@webrtc2/ui - WebRTC React Components

npm version React TypeScript WebRTC

Cross-platform React components for WebRTC applications - Ready-to-use UI components for video calls, audio controls, and media device management across React Native, Web, and Electron.

🚀 WebRTC UI Components Made Simple

@webrtc2/ui provides beautiful, accessible WebRTC components:

  • 🎥 Video Components: Video call interfaces, participant grids
  • 🎛️ Media Controls: Camera, microphone, screen sharing controls
  • 📱 Cross-Platform: React Native, Web browsers, Electron desktop
  • 🎨 Customizable: Themeable components with CSS-in-JS
  • ♿ Accessible: WCAG 2.1 compliant with keyboard navigation
  • 📦 Tree-Shakeable: Import only the components you need

📦 Installation

npm install @webrtc2/ui @webrtc2/client

Peer Dependencies

npm install react react-dom
# For React Native:
npm install react-native

🎯 Quick Start

Basic Video Call Interface

import React from 'react';
import { 
  VideoCallContainer,
  LocalVideo,
  RemoteVideo,
  CallControls 
} from '@webrtc2/ui';
import { useWebRTC } from '@webrtc2/client';

function VideoCallApp() {
  const { localStream, remoteStream, connect, disconnect, isConnected } = useWebRTC();

  return (
    <VideoCallContainer>
      <RemoteVideo 
        stream={remoteStream}
        placeholder="Waiting for participant..."
        showConnectionStatus
      />
      
      <LocalVideo 
        stream={localStream}
        muted
        mirror
        position="bottom-right"
        size="small"
      />
      
      <CallControls
        onJoin={() => connect('room-123')}
        onLeave={disconnect}
        isConnected={isConnected}
        showScreenShare
        showRecording
      />
    </VideoCallContainer>
  );
}

Media Device Controls

import React from 'react';
import { 
  MediaControlPanel,
  CameraButton,
  MicrophoneButton,
  ScreenShareButton,
  DeviceSelector 
} from '@webrtc2/ui';
import { useMediaDevices } from '@webrtc2/client';

function MediaControls() {
  const {
    isCameraEnabled,
    isMicrophoneEnabled,
    isScreenSharing,
    toggleCamera,
    toggleMicrophone,
    toggleScreenShare,
    devices,
    switchCamera,
    switchMicrophone
  } = useMediaDevices();

  return (
    <MediaControlPanel>
      <CameraButton
        enabled={isCameraEnabled}
        onClick={toggleCamera}
        variant="primary"
        size="large"
      />
      
      <MicrophoneButton
        enabled={isMicrophoneEnabled}
        onClick={toggleMicrophone}
        showMeter
        sensitivity={0.5}
      />
      
      <ScreenShareButton
        enabled={isScreenSharing}
        onClick={toggleScreenShare}
        showPreview
      />
      
      <DeviceSelector
        type="camera"
        devices={devices.cameras}
        selectedDevice={devices.selectedCamera}
        onDeviceChange={switchCamera}
      />
      
      <DeviceSelector
        type="microphone"
        devices={devices.microphones}
        selectedDevice={devices.selectedMicrophone}
        onDeviceChange={switchMicrophone}
      />
    </MediaControlPanel>
  );
}

🎥 Video Components

Video Call Container

import { VideoCallContainer } from '@webrtc2/ui';

<VideoCallContainer
  layout="grid"           // 'grid' | 'sidebar' | 'spotlight' | 'presentation'
  maxParticipants={9}     // Maximum participants in grid
  aspectRatio="16:9"      // Video aspect ratio
  backgroundColor="#000"   // Background color
  showConnectionStatus    // Show connection indicators
  enablePictureInPicture  // Enable PiP mode
  onLayoutChange={(layout) => console.log('Layout changed:', layout)}
>
  {/* Video components */}
</VideoCallContainer>

Participant Video

import { ParticipantVideo } from '@webrtc2/ui';

<ParticipantVideo
  stream={remoteStream}
  participant={{
    id: 'user-123',
    name: 'John Doe',
    avatar: 'https://example.com/avatar.jpg',
    isMuted: false,
    isVideoEnabled: true
  }}
  showName
  showMuteIndicator
  showConnectionQuality
  enableDoubleClickFullscreen
  onDoubleClick={() => console.log('Video double clicked')}
/>

Video Grid Layout

import { VideoGrid } from '@webrtc2/ui';

<VideoGrid
  participants={participants}
  localStream={localStream}
  layout="auto"          // 'auto' | '1x1' | '2x2' | '3x3' | '4x4'
  showLocalVideo
  localVideoPosition="top-right"
  enableDragAndDrop
  onParticipantClick={(participant) => console.log('Clicked:', participant)}
  onLayoutChange={(layout) => console.log('Grid layout:', layout)}
/>

🎛️ Control Components

Call Control Bar

import { CallControlBar } from '@webrtc2/ui';

<CallControlBar
  position="bottom"       // 'top' | 'bottom' | 'floating'
  variant="minimal"       // 'full' | 'minimal' | 'compact'
  showLabels
  showTooltips
  autoHide={5000}        // Auto-hide after 5 seconds
  controls={[
    'camera',
    'microphone', 
    'screen-share',
    'chat',
    'participants',
    'settings',
    'leave'
  ]}
  onControlClick={(control) => console.log('Control clicked:', control)}
/>

Advanced Media Controls

import { 
  AdvancedMediaControls,
  VolumeSlider,
  QualitySelector,
  EffectsPanel 
} from '@webrtc2/ui';

<AdvancedMediaControls>
  <VolumeSlider
    type="input"          // 'input' | 'output'
    volume={0.8}
    muted={false}
    showMeter
    onVolumeChange={(volume) => console.log('Volume:', volume)}
  />
  
  <QualitySelector
    currentQuality="720p"
    availableQualities={['240p', '480p', '720p', '1080p']}
    onQualityChange={(quality) => console.log('Quality:', quality)}
  />
  
  <EffectsPanel
    enableBackgroundBlur
    enableVirtualBackground
    enableNoiseReduction
    onEffectToggle={(effect, enabled) => console.log(effect, enabled)}
  />
</AdvancedMediaControls>

📱 Cross-Platform Components

React Native Components

import React from 'react';
import { View } from 'react-native';
import { 
  RNVideoCallContainer,
  RNLocalVideo,
  RNRemoteVideo,
  RNCallControls 
} from '@webrtc2/ui/react-native';

function ReactNativeVideoCall() {
  return (
    <RNVideoCallContainer style={{ flex: 1 }}>
      <RNRemoteVideo
        streamURL={remoteStream?.toURL()}
        style={{ flex: 1 }}
        resizeMode="cover"
        showConnectionStatus
      />
      
      <RNLocalVideo
        streamURL={localStream?.toURL()}
        style={{ 
          position: 'absolute',
          top: 50,
          right: 20,
          width: 120,
          height: 160
        }}
        mirror
      />
      
      <RNCallControls
        style={{ position: 'absolute', bottom: 50 }}
        onCameraToggle={toggleCamera}
        onMicrophoneToggle={toggleMicrophone}
        onEndCall={endCall}
      />
    </RNVideoCallContainer>
  );
}

Electron Components

import { 
  ElectronVideoCall,
  ElectronMenuBar,
  ElectronNotifications 
} from '@webrtc2/ui/electron';

function ElectronApp() {
  return (
    <div className="electron-app">
      <ElectronMenuBar
        showMinimize
        showMaximize
        showClose
        enableDragRegion
      />
      
      <ElectronVideoCall
        enableSystemAudio
        enableMultipleDisplays
        enableNotifications
        onScreenShareSelect={(source) => console.log('Screen:', source)}
      />
      
      <ElectronNotifications
        position="top-right"
        enableSound
        enableBadge
      />
    </div>
  );
}

🎨 Theming and Customization

Theme Provider

import { ThemeProvider, createWebRTCTheme } from '@webrtc2/ui';

const customTheme = createWebRTCTheme({
  colors: {
    primary: '#007AFF',
    secondary: '#5856D6',
    success: '#34C759',
    warning: '#FF9500',
    error: '#FF3B30',
    background: '#000000',
    surface: '#1C1C1E',
    text: '#FFFFFF'
  },
  spacing: {
    xs: 4,
    sm: 8,
    md: 16,
    lg: 24,
    xl: 32
  },
  borderRadius: {
    sm: 4,
    md: 8,
    lg: 12,
    full: 9999
  }
});

function App() {
  return (
    <ThemeProvider theme={customTheme}>
      <VideoCallApp />
    </ThemeProvider>
  );
}

Custom Styled Components

import styled from 'styled-components';
import { VideoCallContainer as BaseContainer } from '@webrtc2/ui';

const CustomVideoContainer = styled(BaseContainer)`
  background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
  border-radius: 16px;
  box-shadow: 0 20px 40px rgba(0, 0, 0, 0.1);
  
  .participant-video {
    border-radius: 12px;
    overflow: hidden;
  }
  
  .control-bar {
    background: rgba(255, 255, 255, 0.1);
    backdrop-filter: blur(20px);
  }
`;

♿ Accessibility Features

Keyboard Navigation

import { AccessibleVideoCall } from '@webrtc2/ui';

<AccessibleVideoCall
  enableKeyboardNavigation
  keyboardShortcuts={{
    'Space': 'toggle-microphone',
    'KeyV': 'toggle-camera',
    'KeyS': 'toggle-screen-share',
    'Escape': 'leave-call'
  }}
  announceConnectionChanges
  announceParticipantChanges
  enableHighContrast
  enableReducedMotion
/>

Screen Reader Support

import { ScreenReaderAnnouncements } from '@webrtc2/ui';

<ScreenReaderAnnouncements
  announceConnectionStatus
  announceParticipantJoins
  announceMediaStateChanges
  announceQualityChanges
  language="en-US"
/>

📊 Analytics Integration

Usage Analytics

import { AnalyticsProvider } from '@webrtc2/ui';

<AnalyticsProvider
  trackClicks
  trackHovers
  trackKeyboardUsage
  trackPerformance
  onEvent={(event, data) => {
    console.log('UI Event:', event, data);
    // Send to analytics service
  }}
>
  <VideoCallApp />
</AnalyticsProvider>

🔧 Advanced Features

Picture-in-Picture Mode

import { PictureInPictureProvider, usePiP } from '@webrtc2/ui';

function VideoWithPiP() {
  const { isPiPEnabled, enterPiP, exitPiP } = usePiP();
  
  return (
    <PictureInPictureProvider>
      <VideoCallContainer>
        <RemoteVideo
          stream={remoteStream}
          enablePictureInPicture
          onPiPToggle={isPiPEnabled ? exitPiP : enterPiP}
        />
      </VideoCallContainer>
    </PictureInPictureProvider>
  );
}

Virtual Backgrounds

import { VirtualBackgroundProvider, BackgroundSelector } from '@webrtc2/ui';

<VirtualBackgroundProvider>
  <BackgroundSelector
    backgrounds={[
      { id: 'blur', type: 'blur', intensity: 0.8 },
      { id: 'office', type: 'image', url: '/backgrounds/office.jpg' },
      { id: 'nature', type: 'image', url: '/backgrounds/nature.jpg' }
    ]}
    onBackgroundChange={(background) => console.log('Background:', background)}
  />
  
  <LocalVideo
    stream={localStream}
    enableVirtualBackground
  />
</VirtualBackgroundProvider>

📚 Component Reference

Core Components

  • VideoCallContainer - Main container for video calls
  • LocalVideo - Local user video stream
  • RemoteVideo - Remote participant video stream
  • VideoGrid - Grid layout for multiple participants
  • CallControls - Basic call control buttons
  • MediaControlPanel - Advanced media controls

Control Components

  • CameraButton - Camera toggle button
  • MicrophoneButton - Microphone toggle with meter
  • ScreenShareButton - Screen sharing control
  • DeviceSelector - Media device selection dropdown
  • VolumeSlider - Volume control slider
  • QualitySelector - Video quality selection

Layout Components

  • SidebarLayout - Sidebar-based layout
  • GridLayout - Grid-based layout
  • SpotlightLayout - Spotlight/focus layout
  • PresentationLayout - Presentation mode layout

📚 Related Packages

�� Contributing

We welcome contributions! Please see our Contributing Guide for details.

📄 License

MIT License - see LICENSE for details.


Keywords: WebRTC UI, React WebRTC components, video call UI, WebRTC interface, React Native WebRTC UI, Electron WebRTC UI, video call components, media controls, WebRTC design system, cross-platform UI