️(frontend) avoid subscribing to full local participant changes

Subscribing to the whole local participant caused re-renders on
every local participant update, even when the consumer only cared
about a specific attribute.

Narrow the subscription so only the relevant attributes trigger a
re-render.
This commit is contained in:
lebaudantoine
2026-07-16 11:39:55 +02:00
committed by aleb_the_flash
parent d2e13cc826
commit 97a9735c0b
3 changed files with 14 additions and 10 deletions
@@ -3,10 +3,10 @@ import { Button, Text } from '@/primitives'
import { useCallback, useMemo, useRef } from 'react'
import { screenSharePreferenceStore } from '@/stores/screenSharePreferences'
import { useSnapshot } from 'valtio'
import { useLocalParticipant } from '@livekit/components-react'
import type { TrackReferenceOrPlaceholder } from '@livekit/components-core'
import { useTranslation } from 'react-i18next'
import { useSize } from '@/features/rooms/livekit/hooks/useResizeObserver'
import { LocalParticipant } from 'livekit-client'
export const FullScreenShareWarning = ({
trackReference,
@@ -17,7 +17,6 @@ export const FullScreenShareWarning = ({
const warningContainerRef = useRef<HTMLDivElement>(null)
const { width: containerWidth } = useSize(warningContainerRef)
const { localParticipant } = useLocalParticipant()
const screenSharePreferences = useSnapshot(screenSharePreferenceStore)
const isFullScreenSharing = useMemo(() => {
@@ -57,8 +56,10 @@ export const FullScreenShareWarning = ({
screenSharePreferences.enabled && isFullScreenSharing
const handleStopScreenShare = async () => {
if (!localParticipant.isScreenShareEnabled) return
await localParticipant.setScreenShareEnabled(false, {}, {})
const participant = trackReference.participant
if (!(participant instanceof LocalParticipant)) return
if (!participant.isScreenShareEnabled) return
await (participant as LocalParticipant).setScreenShareEnabled(false, {}, {})
}
const handleDismissWarning = useCallback(() => {
@@ -1,18 +1,21 @@
import { useTranslation } from 'react-i18next'
import { styled } from '@/styled-system/jsx'
import { useLocalParticipant } from '@livekit/components-react'
import { useTrackToggle } from '@livekit/components-react'
import { Track } from 'livekit-client'
export const StageFrame = ({ children }: { children: React.ReactNode }) => {
const { t } = useTranslation('rooms', {
keyPrefix: 'pictureInPicture',
})
const { localParticipant } = useLocalParticipant()
const { enabled: isScreenSharing } = useTrackToggle({
source: Track.Source.ScreenShare,
})
return (
<Container
role="region"
aria-label={t('stage')}
{...(!localParticipant.isScreenShareEnabled ? { inert: '' } : {})}
{...(!isScreenSharing ? { inert: '' } : {})}
>
{children}
</Container>
@@ -9,8 +9,8 @@ import useLongPress from '@/features/shortcuts/useLongPress'
import { ActiveSpeaker } from '@/features/rooms/components/ActiveSpeaker'
import {
useIsSpeaking,
useLocalParticipant,
useMaybeRoomContext,
useRoomContext,
} from '@livekit/components-react'
import type { ButtonRecipeProps } from '@/primitives/buttonRecipe'
import type { ToggleButtonProps } from '@/primitives/ToggleButton'
@@ -169,7 +169,7 @@ export const ToggleDevice = <T extends ToggleSource>({
}
const ActiveSpeakerWrapper = () => {
const { localParticipant } = useLocalParticipant()
const isSpeaking = useIsSpeaking(localParticipant)
const room = useRoomContext()
const isSpeaking = useIsSpeaking(room.localParticipant)
return <ActiveSpeaker isSpeaking={isSpeaking} pushToTalk />
}