@memberjunction/ai-realtime-client 6.2.0-edge.3 → 6.2.0-edge.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +156 -29
- package/dist/audio/audioMeter.d.ts +71 -0
- package/dist/audio/audioMeter.d.ts.map +1 -1
- package/dist/audio/audioMeter.js +83 -0
- package/dist/audio/audioMeter.js.map +1 -1
- package/dist/audio/mediaElementAudioRouter.d.ts +41 -0
- package/dist/audio/mediaElementAudioRouter.d.ts.map +1 -0
- package/dist/audio/mediaElementAudioRouter.js +82 -0
- package/dist/audio/mediaElementAudioRouter.js.map +1 -0
- package/dist/audio/micCapture.d.ts +12 -3
- package/dist/audio/micCapture.d.ts.map +1 -1
- package/dist/audio/micCapture.js +15 -1
- package/dist/audio/micCapture.js.map +1 -1
- package/dist/audio/pcmPlayback.d.ts +72 -4
- package/dist/audio/pcmPlayback.d.ts.map +1 -1
- package/dist/audio/pcmPlayback.js +101 -1
- package/dist/audio/pcmPlayback.js.map +1 -1
- package/dist/drivers/assemblyAIRealtimeClient.d.ts +2 -0
- package/dist/drivers/assemblyAIRealtimeClient.d.ts.map +1 -1
- package/dist/drivers/assemblyAIRealtimeClient.js +14 -0
- package/dist/drivers/assemblyAIRealtimeClient.js.map +1 -1
- package/dist/drivers/elevenLabsRealtimeClient.d.ts +2 -0
- package/dist/drivers/elevenLabsRealtimeClient.d.ts.map +1 -1
- package/dist/drivers/elevenLabsRealtimeClient.js +14 -0
- package/dist/drivers/elevenLabsRealtimeClient.js.map +1 -1
- package/dist/drivers/geminiAvatarOutput.d.ts +132 -0
- package/dist/drivers/geminiAvatarOutput.d.ts.map +1 -0
- package/dist/drivers/geminiAvatarOutput.js +310 -0
- package/dist/drivers/geminiAvatarOutput.js.map +1 -0
- package/dist/drivers/geminiEnterpriseRealtimeClient.d.ts +38 -0
- package/dist/drivers/geminiEnterpriseRealtimeClient.d.ts.map +1 -0
- package/dist/drivers/geminiEnterpriseRealtimeClient.js +99 -0
- package/dist/drivers/geminiEnterpriseRealtimeClient.js.map +1 -0
- package/dist/drivers/geminiRealtimeClient.d.ts +325 -50
- package/dist/drivers/geminiRealtimeClient.d.ts.map +1 -1
- package/dist/drivers/geminiRealtimeClient.js +782 -184
- package/dist/drivers/geminiRealtimeClient.js.map +1 -1
- package/dist/drivers/openAILiveClient.d.ts +5 -8
- package/dist/drivers/openAILiveClient.d.ts.map +1 -1
- package/dist/drivers/openAILiveClient.js +19 -32
- package/dist/drivers/openAILiveClient.js.map +1 -1
- package/dist/drivers/openAIRealtimeClient.d.ts +13 -26
- package/dist/drivers/openAIRealtimeClient.d.ts.map +1 -1
- package/dist/drivers/openAIRealtimeClient.js +28 -55
- package/dist/drivers/openAIRealtimeClient.js.map +1 -1
- package/dist/drivers/xaiRealtimeClient.d.ts.map +1 -1
- package/dist/drivers/xaiRealtimeClient.js +19 -14
- package/dist/drivers/xaiRealtimeClient.js.map +1 -1
- package/dist/generic/baseRealtimeClient.d.ts +183 -29
- package/dist/generic/baseRealtimeClient.d.ts.map +1 -1
- package/dist/generic/baseRealtimeClient.js +246 -14
- package/dist/generic/baseRealtimeClient.js.map +1 -1
- package/dist/generic/openAIProtocolClient.d.ts +2 -0
- package/dist/generic/openAIProtocolClient.d.ts.map +1 -1
- package/dist/generic/openAIProtocolClient.js +17 -0
- package/dist/generic/openAIProtocolClient.js.map +1 -1
- package/dist/index.d.ts +2 -3
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +3 -3
- package/dist/index.js.map +1 -1
- package/dist/media/attachVideoSource.d.ts +23 -0
- package/dist/media/attachVideoSource.d.ts.map +1 -0
- package/dist/media/attachVideoSource.js +49 -0
- package/dist/media/attachVideoSource.js.map +1 -0
- package/dist/media/channelVideoSource.d.ts +110 -14
- package/dist/media/channelVideoSource.d.ts.map +1 -1
- package/dist/media/channelVideoSource.js +183 -18
- package/dist/media/channelVideoSource.js.map +1 -1
- package/dist/media/decoders/frameScheduler.d.ts +119 -0
- package/dist/media/decoders/frameScheduler.d.ts.map +1 -0
- package/dist/media/decoders/frameScheduler.js +238 -0
- package/dist/media/decoders/frameScheduler.js.map +1 -0
- package/dist/media/decoders/imageFrameDecoder.d.ts +58 -0
- package/dist/media/decoders/imageFrameDecoder.d.ts.map +1 -0
- package/dist/media/decoders/imageFrameDecoder.js +110 -0
- package/dist/media/decoders/imageFrameDecoder.js.map +1 -0
- package/dist/media/decoders/mseFmp4Decoder.d.ts +130 -0
- package/dist/media/decoders/mseFmp4Decoder.d.ts.map +1 -0
- package/dist/media/decoders/mseFmp4Decoder.js +402 -0
- package/dist/media/decoders/mseFmp4Decoder.js.map +1 -0
- package/dist/media/decoders/streamCanvas.d.ts +46 -0
- package/dist/media/decoders/streamCanvas.d.ts.map +1 -0
- package/dist/media/decoders/streamCanvas.js +163 -0
- package/dist/media/decoders/streamCanvas.js.map +1 -0
- package/dist/media/decoders/videoMimeTypes.d.ts +29 -0
- package/dist/media/decoders/videoMimeTypes.d.ts.map +1 -0
- package/dist/media/decoders/videoMimeTypes.js +50 -0
- package/dist/media/decoders/videoMimeTypes.js.map +1 -0
- package/dist/media/decoders/webCodecsChunkDecoder.d.ts +99 -0
- package/dist/media/decoders/webCodecsChunkDecoder.d.ts.map +1 -0
- package/dist/media/decoders/webCodecsChunkDecoder.js +265 -0
- package/dist/media/decoders/webCodecsChunkDecoder.js.map +1 -0
- package/dist/media/displayCapture.d.ts +128 -0
- package/dist/media/displayCapture.d.ts.map +1 -0
- package/dist/media/displayCapture.js +245 -0
- package/dist/media/displayCapture.js.map +1 -0
- package/dist/media/frameCapture.d.ts +25 -8
- package/dist/media/frameCapture.d.ts.map +1 -1
- package/dist/media/frameCapture.js +42 -72
- package/dist/media/frameCapture.js.map +1 -1
- package/dist/media/frameSampler.d.ts +94 -0
- package/dist/media/frameSampler.d.ts.map +1 -0
- package/dist/media/frameSampler.js +134 -0
- package/dist/media/frameSampler.js.map +1 -0
- package/dist/media/index.d.ts +32 -0
- package/dist/media/index.d.ts.map +1 -0
- package/dist/media/index.js +32 -0
- package/dist/media/index.js.map +1 -0
- package/dist/media/localMediaController.d.ts +116 -0
- package/dist/media/localMediaController.d.ts.map +1 -0
- package/dist/media/localMediaController.js +281 -0
- package/dist/media/localMediaController.js.map +1 -0
- package/dist/media/mediaLayout.d.ts +93 -0
- package/dist/media/mediaLayout.d.ts.map +1 -0
- package/dist/media/mediaLayout.js +187 -0
- package/dist/media/mediaLayout.js.map +1 -0
- package/dist/media/mediaPreview.d.ts +94 -0
- package/dist/media/mediaPreview.d.ts.map +1 -0
- package/dist/media/mediaPreview.js +154 -0
- package/dist/media/mediaPreview.js.map +1 -0
- package/dist/media/mediaStage.d.ts +99 -0
- package/dist/media/mediaStage.d.ts.map +1 -0
- package/dist/media/mediaStage.js +171 -0
- package/dist/media/mediaStage.js.map +1 -0
- package/dist/media/model.d.ts +154 -0
- package/dist/media/model.d.ts.map +1 -0
- package/dist/media/model.js +9 -0
- package/dist/media/model.js.map +1 -0
- package/dist/media/playbackClock.d.ts +20 -0
- package/dist/media/playbackClock.d.ts.map +1 -0
- package/dist/media/playbackClock.js +13 -0
- package/dist/media/playbackClock.js.map +1 -0
- package/dist/media/videoFrameDecoder.d.ts +86 -0
- package/dist/media/videoFrameDecoder.d.ts.map +1 -0
- package/dist/media/videoFrameDecoder.js +2 -0
- package/dist/media/videoFrameDecoder.js.map +1 -0
- package/dist/media/videoFrameDecoderRegistry.d.ts +40 -0
- package/dist/media/videoFrameDecoderRegistry.d.ts.map +1 -0
- package/dist/media/videoFrameDecoderRegistry.js +69 -0
- package/dist/media/videoFrameDecoderRegistry.js.map +1 -0
- package/dist/media/videoPacing.d.ts +32 -0
- package/dist/media/videoPacing.d.ts.map +1 -0
- package/dist/media/videoPacing.js +37 -0
- package/dist/media/videoPacing.js.map +1 -0
- package/dist/media/videoPlayout.d.ts +168 -0
- package/dist/media/videoPlayout.d.ts.map +1 -0
- package/dist/media/videoPlayout.js +217 -0
- package/dist/media/videoPlayout.js.map +1 -0
- package/dist/media/videoSourceArbiter.d.ts +250 -0
- package/dist/media/videoSourceArbiter.d.ts.map +1 -0
- package/dist/media/videoSourceArbiter.js +423 -0
- package/dist/media/videoSourceArbiter.js.map +1 -0
- package/dist/testing/conformanceAssertions.d.ts +25 -0
- package/dist/testing/conformanceAssertions.d.ts.map +1 -0
- package/dist/testing/conformanceAssertions.js +64 -0
- package/dist/testing/conformanceAssertions.js.map +1 -0
- package/dist/testing/conformanceFixtures.d.ts +76 -0
- package/dist/testing/conformanceFixtures.d.ts.map +1 -0
- package/dist/testing/conformanceFixtures.js +169 -0
- package/dist/testing/conformanceFixtures.js.map +1 -0
- package/dist/testing/conformanceGates.d.ts +32 -0
- package/dist/testing/conformanceGates.d.ts.map +1 -0
- package/dist/testing/conformanceGates.js +35 -0
- package/dist/testing/conformanceGates.js.map +1 -0
- package/dist/testing/conformanceMicrophone.d.ts +10 -0
- package/dist/testing/conformanceMicrophone.d.ts.map +1 -0
- package/dist/testing/conformanceMicrophone.js +71 -0
- package/dist/testing/conformanceMicrophone.js.map +1 -0
- package/dist/testing/conformanceTimeline.d.ts +128 -0
- package/dist/testing/conformanceTimeline.d.ts.map +1 -0
- package/dist/testing/conformanceTimeline.js +32 -0
- package/dist/testing/conformanceTimeline.js.map +1 -0
- package/dist/testing/conformanceVideoStream.d.ts +29 -0
- package/dist/testing/conformanceVideoStream.d.ts.map +1 -0
- package/dist/testing/conformanceVideoStream.js +39 -0
- package/dist/testing/conformanceVideoStream.js.map +1 -0
- package/dist/testing/index.d.ts +29 -0
- package/dist/testing/index.d.ts.map +1 -0
- package/dist/testing/index.js +28 -0
- package/dist/testing/index.js.map +1 -0
- package/dist/testing/realtimeVideoConformance.d.ts +23 -0
- package/dist/testing/realtimeVideoConformance.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformance.js +139 -0
- package/dist/testing/realtimeVideoConformance.js.map +1 -0
- package/dist/testing/realtimeVideoConformanceChecks.d.ts +4 -0
- package/dist/testing/realtimeVideoConformanceChecks.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformanceChecks.js +164 -0
- package/dist/testing/realtimeVideoConformanceChecks.js.map +1 -0
- package/dist/testing/realtimeVideoConformanceFrameChecks.d.ts +4 -0
- package/dist/testing/realtimeVideoConformanceFrameChecks.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformanceFrameChecks.js +63 -0
- package/dist/testing/realtimeVideoConformanceFrameChecks.js.map +1 -0
- package/dist/testing/realtimeVideoConformanceSession.d.ts +108 -0
- package/dist/testing/realtimeVideoConformanceSession.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformanceSession.js +270 -0
- package/dist/testing/realtimeVideoConformanceSession.js.map +1 -0
- package/dist/testing/realtimeVideoConformanceTurnChecks.d.ts +4 -0
- package/dist/testing/realtimeVideoConformanceTurnChecks.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformanceTurnChecks.js +248 -0
- package/dist/testing/realtimeVideoConformanceTurnChecks.js.map +1 -0
- package/dist/testing/realtimeVideoConformanceTypes.d.ts +155 -0
- package/dist/testing/realtimeVideoConformanceTypes.d.ts.map +1 -0
- package/dist/testing/realtimeVideoConformanceTypes.js +2 -0
- package/dist/testing/realtimeVideoConformanceTypes.js.map +1 -0
- package/dist/testing/recordingPlayout.d.ts +84 -0
- package/dist/testing/recordingPlayout.d.ts.map +1 -0
- package/dist/testing/recordingPlayout.js +120 -0
- package/dist/testing/recordingPlayout.js.map +1 -0
- package/package.json +29 -4
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Shared types for the `/media` entry point: the local devices and capture state that the
|
|
3
|
+
* media controllers and the UI exchange.
|
|
4
|
+
*
|
|
5
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
6
|
+
*/
|
|
7
|
+
/** A kind of local device the user captures from. */
|
|
8
|
+
export type LocalMediaKind = 'camera' | 'microphone';
|
|
9
|
+
/** What a device does: a camera or a microphone the user captures from, or a speaker that plays sound. */
|
|
10
|
+
export type MediaDeviceKind = LocalMediaKind | 'speaker';
|
|
11
|
+
/** One device. */
|
|
12
|
+
export interface MediaDevice {
|
|
13
|
+
/** The browser's id for the device, stable for this site until the user clears its data. */
|
|
14
|
+
DeviceID: string;
|
|
15
|
+
Kind: MediaDeviceKind;
|
|
16
|
+
/** The device's name. Browsers leave it empty until the user has allowed this site that kind of device. */
|
|
17
|
+
Label: string;
|
|
18
|
+
/** Devices on the same physical product (a webcam's camera and microphone) share a group id. */
|
|
19
|
+
GroupID: string;
|
|
20
|
+
}
|
|
21
|
+
/** Why a local device could not be used. */
|
|
22
|
+
export type LocalMediaFailure =
|
|
23
|
+
/** The user, the operating system or the page's permissions policy refused access. */
|
|
24
|
+
'denied'
|
|
25
|
+
/** There is no device of that kind, or not the one asked for. */
|
|
26
|
+
| 'not-found'
|
|
27
|
+
/** The device exists, but another application is using it. */
|
|
28
|
+
| 'in-use'
|
|
29
|
+
/** The browser cannot capture at all (no `getUserMedia`). */
|
|
30
|
+
| 'unsupported'
|
|
31
|
+
/** Anything else; see the message. */
|
|
32
|
+
| 'error';
|
|
33
|
+
/** One kind of local capture. */
|
|
34
|
+
export interface LocalTrackState {
|
|
35
|
+
Status: 'off' | 'starting' | 'on' | 'failed';
|
|
36
|
+
/** The device in use, while `on`. */
|
|
37
|
+
DeviceID?: string;
|
|
38
|
+
/** That device's name, while `on`. */
|
|
39
|
+
Label?: string;
|
|
40
|
+
/** Why capture failed, while `failed`. */
|
|
41
|
+
Failure?: LocalMediaFailure;
|
|
42
|
+
/** The browser's message for the failure. */
|
|
43
|
+
Message?: string;
|
|
44
|
+
}
|
|
45
|
+
/** Everything captured locally, as the `LocalMediaController` reports it. */
|
|
46
|
+
export interface LocalMediaState {
|
|
47
|
+
Camera: LocalTrackState;
|
|
48
|
+
Microphone: LocalTrackState;
|
|
49
|
+
/** The input devices the browser lists now. */
|
|
50
|
+
Devices: MediaDevice[];
|
|
51
|
+
}
|
|
52
|
+
/** The outcome of starting or switching a local device. It always resolves; it never rejects. */
|
|
53
|
+
export type LocalMediaResult = {
|
|
54
|
+
Status: 'started';
|
|
55
|
+
Stream: MediaStream;
|
|
56
|
+
} | {
|
|
57
|
+
Status: 'failed';
|
|
58
|
+
Reason: LocalMediaFailure;
|
|
59
|
+
Message: string;
|
|
60
|
+
};
|
|
61
|
+
/**
|
|
62
|
+
* A source of video to show: a live `MediaStream` (a camera, a shared screen, a WebRTC track), or a player that
|
|
63
|
+
* must own the `<video>` element (MSE or WebCodecs playout of encoded video, such as an avatar). Renderers show
|
|
64
|
+
* either with `AttachVideoSource`.
|
|
65
|
+
*/
|
|
66
|
+
export type MediaVideoSource =
|
|
67
|
+
/** A live stream, shown muted: its audio is played elsewhere. */
|
|
68
|
+
{
|
|
69
|
+
Kind: 'stream';
|
|
70
|
+
Stream: MediaStream;
|
|
71
|
+
}
|
|
72
|
+
/** A player that takes over the element and returns a function that releases it. */
|
|
73
|
+
| {
|
|
74
|
+
Kind: 'element';
|
|
75
|
+
Attach(element: HTMLVideoElement): () => void;
|
|
76
|
+
};
|
|
77
|
+
/**
|
|
78
|
+
* What a participant's video shows. Open vocabulary. These are on-screen kinds; the video source arbiter's
|
|
79
|
+
* `VideoSourceKind` is a different list, of what the model is shown.
|
|
80
|
+
*/
|
|
81
|
+
export type MediaSourceKind = 'camera' | 'screen' | 'avatar' | (string & {});
|
|
82
|
+
/** Where a surface appears: the main stage, a picture-in-picture tile, a tab, or nowhere. */
|
|
83
|
+
export type MediaPlacement = 'stage' | 'pip' | 'tab' | 'hidden';
|
|
84
|
+
/** Every placement, in the order a displaced surface falls back through them. */
|
|
85
|
+
export declare const MEDIA_PLACEMENTS: readonly MediaPlacement[];
|
|
86
|
+
/** One person or agent in a session, as the media stage and its tiles see them. */
|
|
87
|
+
export interface MediaParticipant {
|
|
88
|
+
/** Stable identity within the session. */
|
|
89
|
+
Identity: string;
|
|
90
|
+
DisplayName: string;
|
|
91
|
+
/** `'self'` is the local user. */
|
|
92
|
+
Role: 'self' | 'agent' | 'host' | 'participant';
|
|
93
|
+
/** Whether the participant is speaking now. */
|
|
94
|
+
IsSpeaking: boolean;
|
|
95
|
+
/** The participant's videos, by kind: a camera, a shared screen, an avatar. */
|
|
96
|
+
Video: Partial<Record<MediaSourceKind, MediaVideoSource>>;
|
|
97
|
+
/** Which video a tile shows when there are several. Defaults to a shared screen, then the camera, then the avatar. */
|
|
98
|
+
PreferredVideo?: MediaSourceKind;
|
|
99
|
+
/** Whether the participant's microphone is off. */
|
|
100
|
+
IsMuted?: boolean;
|
|
101
|
+
/** The connection's quality, when the platform reports one. */
|
|
102
|
+
ConnectionQuality?: MediaConnectionQuality;
|
|
103
|
+
/** Reads the participant's current audio level, 0..1, for a meter. Called on every animation frame. */
|
|
104
|
+
GetAudioLevel?: () => number;
|
|
105
|
+
/**
|
|
106
|
+
* Whether an agent can see this participant's camera and shared screen: they allowed it, and an agent is there to
|
|
107
|
+
* watch. A tile shows "Agent can see". Absent means no.
|
|
108
|
+
*/
|
|
109
|
+
AgentCanSee?: boolean;
|
|
110
|
+
}
|
|
111
|
+
/** A participant's connection quality. */
|
|
112
|
+
export type MediaConnectionQuality = 'excellent' | 'good' | 'poor' | 'lost' | 'unknown';
|
|
113
|
+
/** The agent's conversational state, for an indicator. */
|
|
114
|
+
export type MediaAgentState = 'idle' | 'listening' | 'thinking' | 'speaking';
|
|
115
|
+
/** The state of a session's connection, for an overlay. */
|
|
116
|
+
export type MediaConnectionStatus = 'idle' | 'connecting' | 'connected' | 'reconnecting' | 'disconnected' | 'error';
|
|
117
|
+
/** Why a session ended. */
|
|
118
|
+
export type MediaDisconnectReason = 'client-initiated' | 'server-shutdown' | 'participant-removed' | 'room-deleted' | 'connection-lost' | 'duplicate-identity' | 'unknown';
|
|
119
|
+
/** A device the user picked in a device menu. */
|
|
120
|
+
export interface MediaDeviceSelection {
|
|
121
|
+
Kind: MediaDeviceKind;
|
|
122
|
+
DeviceID: string;
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Something that can be placed: a channel's surface (a whiteboard, a remote browser) or a participant's video
|
|
126
|
+
* (the avatar, the user's camera, a shared screen).
|
|
127
|
+
*/
|
|
128
|
+
export interface MediaSurface {
|
|
129
|
+
/** Stable key, usually the channel key. The user's moves are recorded against it. */
|
|
130
|
+
Key: string;
|
|
131
|
+
Label: string;
|
|
132
|
+
/** Where it goes unless the user moved it. */
|
|
133
|
+
DefaultPlacement: MediaPlacement;
|
|
134
|
+
/** Where the user may move it. Defaults to every placement. */
|
|
135
|
+
AllowedPlacements?: readonly MediaPlacement[];
|
|
136
|
+
/** The participant video it shows, when it is one; absent for a component surface such as a whiteboard. */
|
|
137
|
+
Video?: {
|
|
138
|
+
ParticipantIdentity: string;
|
|
139
|
+
Kind: MediaSourceKind;
|
|
140
|
+
};
|
|
141
|
+
}
|
|
142
|
+
/** One move the user made: a surface to a placement. */
|
|
143
|
+
export interface MediaPlacementMove {
|
|
144
|
+
SurfaceKey: string;
|
|
145
|
+
Placement: MediaPlacement;
|
|
146
|
+
}
|
|
147
|
+
/** A picture-in-picture box as fractions of the stage (0 to 1), so it survives a resized window: what a host saves. */
|
|
148
|
+
export interface MediaPipRect {
|
|
149
|
+
X: number;
|
|
150
|
+
Y: number;
|
|
151
|
+
W: number;
|
|
152
|
+
H: number;
|
|
153
|
+
}
|
|
154
|
+
//# sourceMappingURL=model.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"model.d.ts","sourceRoot":"","sources":["../../src/media/model.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Shared types for the `/media` entry point: the local devices and capture state that the
|
|
3
|
+
* media controllers and the UI exchange.
|
|
4
|
+
*
|
|
5
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
6
|
+
*/
|
|
7
|
+
/** Every placement, in the order a displaced surface falls back through them. */
|
|
8
|
+
export const MEDIA_PLACEMENTS = ['stage', 'pip', 'tab', 'hidden'];
|
|
9
|
+
//# sourceMappingURL=model.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"model.js","sourceRoot":"","sources":["../../src/media/model.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AA8EH,iFAAiF;AACjF,MAAM,CAAC,MAAM,gBAAgB,GAA8B,CAAC,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,QAAQ,CAAC,CAAC"}
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview PLAYBACK CLOCK: where the voice is, so a video player can show each frame when the voice reaches it and
|
|
3
|
+
* the face moves with the voice.
|
|
4
|
+
*
|
|
5
|
+
* The voice is the master clock, as in the meeting bot: a driver that times both its PCM and its video frames on one media
|
|
6
|
+
* timeline gives the player its PCM playback (`RealtimePcmPlayback`) as `VideoPlayoutOptions.Clock`. The chunk and image
|
|
7
|
+
* decoders then show a frame when the clock reaches its `PresentationTimeMs`. MSE needs no clock: an MP4 that carries the
|
|
8
|
+
* voice plays voice and face together on its own timestamps.
|
|
9
|
+
*
|
|
10
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
11
|
+
*/
|
|
12
|
+
/** Where the voice is: the clock a video player shows frames against, so the face moves with the voice. */
|
|
13
|
+
export interface IPlaybackClock {
|
|
14
|
+
/**
|
|
15
|
+
* The media time, in milliseconds on the stream's timeline, of the audio heard now; `null` while no timed audio plays
|
|
16
|
+
* (nothing is queued, or the audio queued carries no media times).
|
|
17
|
+
*/
|
|
18
|
+
readonly CurrentTimeMs: number | null;
|
|
19
|
+
}
|
|
20
|
+
//# sourceMappingURL=playbackClock.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"playbackClock.d.ts","sourceRoot":"","sources":["../../src/media/playbackClock.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG;AAEH,2GAA2G;AAC3G,MAAM,WAAW,cAAc;IAC3B;;;OAGG;IACH,QAAQ,CAAC,aAAa,EAAE,MAAM,GAAG,IAAI,CAAC;CACzC"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview PLAYBACK CLOCK: where the voice is, so a video player can show each frame when the voice reaches it and
|
|
3
|
+
* the face moves with the voice.
|
|
4
|
+
*
|
|
5
|
+
* The voice is the master clock, as in the meeting bot: a driver that times both its PCM and its video frames on one media
|
|
6
|
+
* timeline gives the player its PCM playback (`RealtimePcmPlayback`) as `VideoPlayoutOptions.Clock`. The chunk and image
|
|
7
|
+
* decoders then show a frame when the clock reaches its `PresentationTimeMs`. MSE needs no clock: an MP4 that carries the
|
|
8
|
+
* voice plays voice and face together on its own timestamps.
|
|
9
|
+
*
|
|
10
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
11
|
+
*/
|
|
12
|
+
export {};
|
|
13
|
+
//# sourceMappingURL=playbackClock.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"playbackClock.js","sourceRoot":"","sources":["../../src/media/playbackClock.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;GAUG"}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview VIDEO FRAME DECODERS: what plays one kind of `RealtimeVideoFrame` into a `<video>` element for
|
|
3
|
+
* {@link VideoPlayout}, and how a decoder is offered to the player.
|
|
4
|
+
*
|
|
5
|
+
* The player keeps one decoder at a time. For each frame it picks, from the {@link VideoFrameDecoderRegistry}, the first
|
|
6
|
+
* registration of the frame's kind that can play its MIME type, and hands the decoder a {@link VideoFrameDecoderContext}:
|
|
7
|
+
* the player's settings and where to report. A decoder plays into the host's element, whatever it decodes with, so the
|
|
8
|
+
* host shows every kind of video the same way.
|
|
9
|
+
*
|
|
10
|
+
* Built in: `'mse-fmp4'` (fragmented MP4 through Media Source Extensions), `'webcodecs'` (encoded chunks through a
|
|
11
|
+
* WebCodecs `VideoDecoder`) and `'image'` (still images through `createImageBitmap`).
|
|
12
|
+
*
|
|
13
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
14
|
+
*/
|
|
15
|
+
import type { RealtimeVideoFrame, RealtimeVideoFrameKind } from '@memberjunction/ai';
|
|
16
|
+
import type { IPlaybackClock } from './playbackClock.js';
|
|
17
|
+
import type { VideoPlayoutProblem } from './videoPlayout.js';
|
|
18
|
+
/** What a decoder plays with and reports through. The player gives one to each decoder it creates. */
|
|
19
|
+
export interface VideoFrameDecoderContext {
|
|
20
|
+
/**
|
|
21
|
+
* The player's configured type (`VideoPlayoutOptions.MimeType`), with its codecs: what a decoder that opens by type
|
|
22
|
+
* (MSE) opens with until a frame says more.
|
|
23
|
+
*/
|
|
24
|
+
readonly MimeType: string;
|
|
25
|
+
/** Seconds of played media a buffering decoder keeps behind the playhead (`VideoPlayoutOptions.BackBufferSeconds`). */
|
|
26
|
+
readonly BackBufferSeconds: number;
|
|
27
|
+
/** Whether the element plays the media's own audio (an avatar MP4's voice). The player keeps it current. */
|
|
28
|
+
readonly CarriesVoice: boolean;
|
|
29
|
+
/**
|
|
30
|
+
* The element hook from `VideoPlayoutOptions.OnElementAttached`: the voice's route into Web Audio. A decoder whose media
|
|
31
|
+
* carries audio calls it with each element it takes over, before playback starts.
|
|
32
|
+
*/
|
|
33
|
+
OnElementAttached?(element: HTMLVideoElement): void;
|
|
34
|
+
/**
|
|
35
|
+
* The voice's playback clock (`VideoPlayoutOptions.Clock`), when the player has one: a decoder that paces its own
|
|
36
|
+
* frames shows each when the clock reaches its `PresentationTimeMs`. A decoder whose media carries the voice ignores it.
|
|
37
|
+
*/
|
|
38
|
+
readonly Clock?: IPlaybackClock;
|
|
39
|
+
/** Reports a problem. The player passes each kind on once. */
|
|
40
|
+
Report(problem: VideoPlayoutProblem, message: string): void;
|
|
41
|
+
/**
|
|
42
|
+
* The decoder can't go on (its browser decoder closed for good, or the browser can't decode the stream's codec). The
|
|
43
|
+
* player disposes it and picks the next decoder that can play the frame's type; out of decoders, frames of that type are
|
|
44
|
+
* dropped.
|
|
45
|
+
*/
|
|
46
|
+
Failed(message: string): void;
|
|
47
|
+
}
|
|
48
|
+
/** Plays one kind of frame into a `<video>` element. The player creates one at a time and moves it between elements. */
|
|
49
|
+
export interface IVideoFrameDecoder {
|
|
50
|
+
/** Takes the element over and shows its video there, keeping the frames it holds and the last one shown. */
|
|
51
|
+
Attach(element: HTMLVideoElement): void;
|
|
52
|
+
/** Lets the element go (the tile moved or closed). The decoder keeps what it holds for the next element. */
|
|
53
|
+
Detach(): void;
|
|
54
|
+
/** Takes one frame of its kind, in the order they arrived. */
|
|
55
|
+
Append(frame: RealtimeVideoFrame): void;
|
|
56
|
+
/** The turn's last frame has arrived: everything that came plays to the end, then the last frame holds. */
|
|
57
|
+
EndOfTurn(): void;
|
|
58
|
+
/** Barge-in: drops what isn't shown yet. The last frame shown stays on screen. */
|
|
59
|
+
Flush(): void;
|
|
60
|
+
/** Whether the decoder's own audio is audibly playing (an MP4 that carries the voice); `false` for decoders without audio. */
|
|
61
|
+
readonly IsPlaying: boolean;
|
|
62
|
+
/**
|
|
63
|
+
* How many of the frames it took are still to play: waiting, being decoded or appended, or buffered ahead of the
|
|
64
|
+
* playhead. A frame it dropped (a barge-in's flush, an overflow, a decode error) or played past is not counted.
|
|
65
|
+
*/
|
|
66
|
+
readonly FramesAhead: number;
|
|
67
|
+
/** Stops, releases the element and frees what it holds. */
|
|
68
|
+
Dispose(): void;
|
|
69
|
+
}
|
|
70
|
+
/** One decoder the registry can create. */
|
|
71
|
+
export interface VideoFrameDecoderRegistration {
|
|
72
|
+
/** Its name, unique in the registry: registering the same name again replaces it. Built in: `'mse-fmp4'`, `'webcodecs'`, `'image'`. */
|
|
73
|
+
Name: string;
|
|
74
|
+
/** The kind of frame it plays. */
|
|
75
|
+
Kind: RealtimeVideoFrameKind;
|
|
76
|
+
/** Among the decoders that can play a type, a higher priority is tried first. The built-ins have 0. */
|
|
77
|
+
Priority: number;
|
|
78
|
+
/**
|
|
79
|
+
* Whether it can play frames of this MIME type in this browser, answered at once. A decoder whose exact answer needs an
|
|
80
|
+
* asynchronous check answers from what it can see now, and calls `Failed` later if the check says no.
|
|
81
|
+
*/
|
|
82
|
+
CanPlay(mimeType: string): boolean;
|
|
83
|
+
/** A new decoder, for one player. */
|
|
84
|
+
Create(context: VideoFrameDecoderContext): IVideoFrameDecoder;
|
|
85
|
+
}
|
|
86
|
+
//# sourceMappingURL=videoFrameDecoder.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoFrameDecoder.d.ts","sourceRoot":"","sources":["../../src/media/videoFrameDecoder.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AACH,OAAO,KAAK,EAAE,kBAAkB,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AACrF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AACtD,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,gBAAgB,CAAC;AAE1D,sGAAsG;AACtG,MAAM,WAAW,wBAAwB;IACrC;;;OAGG;IACH,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,uHAAuH;IACvH,QAAQ,CAAC,iBAAiB,EAAE,MAAM,CAAC;IACnC,4GAA4G;IAC5G,QAAQ,CAAC,YAAY,EAAE,OAAO,CAAC;IAC/B;;;OAGG;IACH,iBAAiB,CAAC,CAAC,OAAO,EAAE,gBAAgB,GAAG,IAAI,CAAC;IACpD;;;OAGG;IACH,QAAQ,CAAC,KAAK,CAAC,EAAE,cAAc,CAAC;IAChC,8DAA8D;IAC9D,MAAM,CAAC,OAAO,EAAE,mBAAmB,EAAE,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;IAC5D;;;;OAIG;IACH,MAAM,CAAC,OAAO,EAAE,MAAM,GAAG,IAAI,CAAC;CACjC;AAED,wHAAwH;AACxH,MAAM,WAAW,kBAAkB;IAC/B,4GAA4G;IAC5G,MAAM,CAAC,OAAO,EAAE,gBAAgB,GAAG,IAAI,CAAC;IACxC,4GAA4G;IAC5G,MAAM,IAAI,IAAI,CAAC;IACf,8DAA8D;IAC9D,MAAM,CAAC,KAAK,EAAE,kBAAkB,GAAG,IAAI,CAAC;IACxC,2GAA2G;IAC3G,SAAS,IAAI,IAAI,CAAC;IAClB,kFAAkF;IAClF,KAAK,IAAI,IAAI,CAAC;IACd,8HAA8H;IAC9H,QAAQ,CAAC,SAAS,EAAE,OAAO,CAAC;IAC5B;;;OAGG;IACH,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,2DAA2D;IAC3D,OAAO,IAAI,IAAI,CAAC;CACnB;AAED,2CAA2C;AAC3C,MAAM,WAAW,6BAA6B;IAC1C,uIAAuI;IACvI,IAAI,EAAE,MAAM,CAAC;IACb,kCAAkC;IAClC,IAAI,EAAE,sBAAsB,CAAC;IAC7B,uGAAuG;IACvG,QAAQ,EAAE,MAAM,CAAC;IACjB;;;OAGG;IACH,OAAO,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC;IACnC,qCAAqC;IACrC,MAAM,CAAC,OAAO,EAAE,wBAAwB,GAAG,kBAAkB,CAAC;CACjE"}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoFrameDecoder.js","sourceRoot":"","sources":["../../src/media/videoFrameDecoder.ts"],"names":[],"mappings":""}
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview VIDEO FRAME DECODER REGISTRY: the page's video frame decoders, which `VideoPlayout` chooses from for each
|
|
3
|
+
* frame type. The three built-in decoders (`'mse-fmp4'`, `'webcodecs'`, `'image'`) are registered when the registry is
|
|
4
|
+
* first used; an app adds its own with {@link VideoFrameDecoderRegistry.Register}, or replaces a built-in by registering
|
|
5
|
+
* the same name.
|
|
6
|
+
*
|
|
7
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
8
|
+
*/
|
|
9
|
+
import { BaseSingleton } from '@memberjunction/global';
|
|
10
|
+
import type { RealtimeVideoFrameKind } from '@memberjunction/ai';
|
|
11
|
+
import type { VideoFrameDecoderRegistration } from './videoFrameDecoder.js';
|
|
12
|
+
/** The page's video frame decoders, by name. */
|
|
13
|
+
export declare class VideoFrameDecoderRegistry extends BaseSingleton<VideoFrameDecoderRegistry> {
|
|
14
|
+
private readonly registrations;
|
|
15
|
+
protected constructor();
|
|
16
|
+
/** The page's registry, with the built-in decoders registered. */
|
|
17
|
+
static get Instance(): VideoFrameDecoderRegistry;
|
|
18
|
+
/**
|
|
19
|
+
* Adds a decoder. One with the same name is replaced; players that already use the old one keep it until they choose a
|
|
20
|
+
* decoder again.
|
|
21
|
+
*
|
|
22
|
+
* @param registration The decoder: its name, frame kind, priority, support check and factory.
|
|
23
|
+
*/
|
|
24
|
+
Register(registration: VideoFrameDecoderRegistration): void;
|
|
25
|
+
/**
|
|
26
|
+
* Removes a decoder by name. Players that already use it keep it until they choose a decoder again.
|
|
27
|
+
*
|
|
28
|
+
* @param name The decoder's name.
|
|
29
|
+
*/
|
|
30
|
+
Unregister(name: string): void;
|
|
31
|
+
/**
|
|
32
|
+
* The decoders that can play frames of `kind` and `mimeType` in this browser, highest priority first (in registration
|
|
33
|
+
* order among equals). A decoder whose support check throws is left out.
|
|
34
|
+
*
|
|
35
|
+
* @param kind The frame kind.
|
|
36
|
+
* @param mimeType The frame's MIME type.
|
|
37
|
+
*/
|
|
38
|
+
Candidates(kind: RealtimeVideoFrameKind, mimeType: string): readonly VideoFrameDecoderRegistration[];
|
|
39
|
+
}
|
|
40
|
+
//# sourceMappingURL=videoFrameDecoderRegistry.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoFrameDecoderRegistry.d.ts","sourceRoot":"","sources":["../../src/media/videoFrameDecoderRegistry.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AACvD,OAAO,KAAK,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC;AACjE,OAAO,KAAK,EAAE,6BAA6B,EAAE,MAAM,qBAAqB,CAAC;AAQzE,gDAAgD;AAChD,qBAAa,yBAA0B,SAAQ,aAAa,CAAC,yBAAyB,CAAC;IACnF,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAoD;IAElF,SAAS;IAOT,kEAAkE;IAClE,WAAkB,QAAQ,IAAI,yBAAyB,CAEtD;IAED;;;;;OAKG;IACI,QAAQ,CAAC,YAAY,EAAE,6BAA6B,GAAG,IAAI;IAIlE;;;;OAIG;IACI,UAAU,CAAC,IAAI,EAAE,MAAM,GAAG,IAAI;IAIrC;;;;;;OAMG;IACI,UAAU,CAAC,IAAI,EAAE,sBAAsB,EAAE,QAAQ,EAAE,MAAM,GAAG,SAAS,6BAA6B,EAAE;CAK9G"}
|
|
@@ -0,0 +1,69 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview VIDEO FRAME DECODER REGISTRY: the page's video frame decoders, which `VideoPlayout` chooses from for each
|
|
3
|
+
* frame type. The three built-in decoders (`'mse-fmp4'`, `'webcodecs'`, `'image'`) are registered when the registry is
|
|
4
|
+
* first used; an app adds its own with {@link VideoFrameDecoderRegistry.Register}, or replaces a built-in by registering
|
|
5
|
+
* the same name.
|
|
6
|
+
*
|
|
7
|
+
* @module @memberjunction/ai-realtime-client/media
|
|
8
|
+
*/
|
|
9
|
+
import { BaseSingleton } from '@memberjunction/global';
|
|
10
|
+
import { IMAGE_FRAME_DECODER } from './decoders/imageFrameDecoder.js';
|
|
11
|
+
import { MSE_FMP4_DECODER } from './decoders/mseFmp4Decoder.js';
|
|
12
|
+
import { WEBCODECS_CHUNK_DECODER } from './decoders/webCodecsChunkDecoder.js';
|
|
13
|
+
/** The decoders every page starts with. */
|
|
14
|
+
const BUILT_IN_DECODERS = [MSE_FMP4_DECODER, WEBCODECS_CHUNK_DECODER, IMAGE_FRAME_DECODER];
|
|
15
|
+
/** The page's video frame decoders, by name. */
|
|
16
|
+
export class VideoFrameDecoderRegistry extends BaseSingleton {
|
|
17
|
+
constructor() {
|
|
18
|
+
super();
|
|
19
|
+
this.registrations = new Map();
|
|
20
|
+
for (const registration of BUILT_IN_DECODERS) {
|
|
21
|
+
this.Register(registration);
|
|
22
|
+
}
|
|
23
|
+
}
|
|
24
|
+
/** The page's registry, with the built-in decoders registered. */
|
|
25
|
+
static get Instance() {
|
|
26
|
+
return super.getInstance();
|
|
27
|
+
}
|
|
28
|
+
/**
|
|
29
|
+
* Adds a decoder. One with the same name is replaced; players that already use the old one keep it until they choose a
|
|
30
|
+
* decoder again.
|
|
31
|
+
*
|
|
32
|
+
* @param registration The decoder: its name, frame kind, priority, support check and factory.
|
|
33
|
+
*/
|
|
34
|
+
Register(registration) {
|
|
35
|
+
this.registrations.set(registration.Name, registration);
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Removes a decoder by name. Players that already use it keep it until they choose a decoder again.
|
|
39
|
+
*
|
|
40
|
+
* @param name The decoder's name.
|
|
41
|
+
*/
|
|
42
|
+
Unregister(name) {
|
|
43
|
+
this.registrations.delete(name);
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* The decoders that can play frames of `kind` and `mimeType` in this browser, highest priority first (in registration
|
|
47
|
+
* order among equals). A decoder whose support check throws is left out.
|
|
48
|
+
*
|
|
49
|
+
* @param kind The frame kind.
|
|
50
|
+
* @param mimeType The frame's MIME type.
|
|
51
|
+
*/
|
|
52
|
+
Candidates(kind, mimeType) {
|
|
53
|
+
return [...this.registrations.values()]
|
|
54
|
+
.filter((registration) => registration.Kind === kind && canPlay(registration, mimeType))
|
|
55
|
+
.sort((a, b) => b.Priority - a.Priority);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
/** A registration's support check, with a check that throws read as "no" (logged). */
|
|
59
|
+
function canPlay(registration, mimeType) {
|
|
60
|
+
try {
|
|
61
|
+
return registration.CanPlay(mimeType);
|
|
62
|
+
}
|
|
63
|
+
catch (error) {
|
|
64
|
+
const reason = error instanceof Error ? error.message : String(error);
|
|
65
|
+
console.warn(`[VideoPlayout] The ${registration.Name} decoder's support check failed for ${mimeType}: ${reason}`);
|
|
66
|
+
return false;
|
|
67
|
+
}
|
|
68
|
+
}
|
|
69
|
+
//# sourceMappingURL=videoFrameDecoderRegistry.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoFrameDecoderRegistry.js","sourceRoot":"","sources":["../../src/media/videoFrameDecoderRegistry.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AACH,OAAO,EAAE,aAAa,EAAE,MAAM,wBAAwB,CAAC;AAGvD,OAAO,EAAE,mBAAmB,EAAE,MAAM,8BAA8B,CAAC;AACnE,OAAO,EAAE,gBAAgB,EAAE,MAAM,2BAA2B,CAAC;AAC7D,OAAO,EAAE,uBAAuB,EAAE,MAAM,kCAAkC,CAAC;AAE3E,2CAA2C;AAC3C,MAAM,iBAAiB,GAA6C,CAAC,gBAAgB,EAAE,uBAAuB,EAAE,mBAAmB,CAAC,CAAC;AAErI,gDAAgD;AAChD,MAAM,OAAO,yBAA0B,SAAQ,aAAwC;IAGnF;QACI,KAAK,EAAE,CAAC;QAHK,kBAAa,GAAG,IAAI,GAAG,EAAyC,CAAC;QAI9E,KAAK,MAAM,YAAY,IAAI,iBAAiB,EAAE,CAAC;YAC3C,IAAI,CAAC,QAAQ,CAAC,YAAY,CAAC,CAAC;QAChC,CAAC;IACL,CAAC;IAED,kEAAkE;IAC3D,MAAM,KAAK,QAAQ;QACtB,OAAO,KAAK,CAAC,WAAW,EAA6B,CAAC;IAC1D,CAAC;IAED;;;;;OAKG;IACI,QAAQ,CAAC,YAA2C;QACvD,IAAI,CAAC,aAAa,CAAC,GAAG,CAAC,YAAY,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC;IAC5D,CAAC;IAED;;;;OAIG;IACI,UAAU,CAAC,IAAY;QAC1B,IAAI,CAAC,aAAa,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;IACpC,CAAC;IAED;;;;;;OAMG;IACI,UAAU,CAAC,IAA4B,EAAE,QAAgB;QAC5D,OAAO,CAAC,GAAG,IAAI,CAAC,aAAa,CAAC,MAAM,EAAE,CAAC;aAClC,MAAM,CAAC,CAAC,YAAY,EAAE,EAAE,CAAC,YAAY,CAAC,IAAI,KAAK,IAAI,IAAI,OAAO,CAAC,YAAY,EAAE,QAAQ,CAAC,CAAC;aACvF,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,GAAG,CAAC,CAAC,QAAQ,CAAC,CAAC;IACjD,CAAC;CACJ;AAED,sFAAsF;AACtF,SAAS,OAAO,CAAC,YAA2C,EAAE,QAAgB;IAC1E,IAAI,CAAC;QACD,OAAO,YAAY,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;IAC1C,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACb,MAAM,MAAM,GAAG,KAAK,YAAY,KAAK,CAAC,CAAC,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QACtE,OAAO,CAAC,IAAI,CAAC,sBAAsB,YAAY,CAAC,IAAI,uCAAuC,QAAQ,KAAK,MAAM,EAAE,CAAC,CAAC;QAClH,OAAO,KAAK,CAAC;IACjB,CAAC;AACL,CAAC"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Frame pacing derived from the NEGOTIATED inbound video rate.
|
|
3
|
+
*
|
|
4
|
+
* The rate a model accepts is per-model data (`MaxInboundVideoRate` in the provider's profile table),
|
|
5
|
+
* carried into the live track descriptor by track negotiation. Every layer that paces frames — the
|
|
6
|
+
* source arbiter, the driver's own backstop — asks THIS module what that rate means in milliseconds, so
|
|
7
|
+
* there is one answer to "how often may a frame go out" rather than a constant per layer.
|
|
8
|
+
*
|
|
9
|
+
* The math itself lives in `@memberjunction/ai` (`realtimeVideoFrames`), shared with the meeting bot that also sends
|
|
10
|
+
* frames to the model; these names are thin wrappers over it.
|
|
11
|
+
*
|
|
12
|
+
* @module @memberjunction/ai-realtime-client
|
|
13
|
+
*/
|
|
14
|
+
/**
|
|
15
|
+
* The share of the nominal frame interval a pacer enforces as a MINIMUM spacing. Pacers upstream of
|
|
16
|
+
* the driver run on timers that jitter; enforcing exactly `1000 / rate` would drop a frame that arrived a
|
|
17
|
+
* few milliseconds early. At 1 fps this is the 750 ms backstop the Gemini driver has always applied.
|
|
18
|
+
*/
|
|
19
|
+
export declare const VIDEO_FRAME_JITTER_HEADROOM = 0.75;
|
|
20
|
+
/** The rate assumed when none was negotiated: 1 frame per second, the Live API ceiling today. */
|
|
21
|
+
export declare const DEFAULT_INBOUND_VIDEO_RATE = 1;
|
|
22
|
+
/**
|
|
23
|
+
* The nominal interval between frames, in milliseconds, for a negotiated rate (frames per second).
|
|
24
|
+
* An absent, zero, negative or non-finite rate falls back to {@link DEFAULT_INBOUND_VIDEO_RATE}.
|
|
25
|
+
*/
|
|
26
|
+
export declare function NominalVideoFrameIntervalMs(rate: number | undefined | null): number;
|
|
27
|
+
/**
|
|
28
|
+
* The minimum spacing, in milliseconds, a pacer should enforce between two frames to the model: the
|
|
29
|
+
* nominal interval less jitter headroom ({@link VIDEO_FRAME_JITTER_HEADROOM}).
|
|
30
|
+
*/
|
|
31
|
+
export declare function MinVideoFrameSpacingMs(rate: number | undefined | null): number;
|
|
32
|
+
//# sourceMappingURL=videoPacing.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoPacing.d.ts","sourceRoot":"","sources":["../../src/media/videoPacing.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AASH;;;;GAIG;AACH,eAAO,MAAM,2BAA2B,OAAuC,CAAC;AAEhF,iGAAiG;AACjG,eAAO,MAAM,0BAA0B,IAAsC,CAAC;AAE9E;;;GAGG;AACH,wBAAgB,2BAA2B,CAAC,IAAI,EAAE,MAAM,GAAG,SAAS,GAAG,IAAI,GAAG,MAAM,CAEnF;AAED;;;GAGG;AACH,wBAAgB,sBAAsB,CAAC,IAAI,EAAE,MAAM,GAAG,SAAS,GAAG,IAAI,GAAG,MAAM,CAE9E"}
|
|
@@ -0,0 +1,37 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @fileoverview Frame pacing derived from the NEGOTIATED inbound video rate.
|
|
3
|
+
*
|
|
4
|
+
* The rate a model accepts is per-model data (`MaxInboundVideoRate` in the provider's profile table),
|
|
5
|
+
* carried into the live track descriptor by track negotiation. Every layer that paces frames — the
|
|
6
|
+
* source arbiter, the driver's own backstop — asks THIS module what that rate means in milliseconds, so
|
|
7
|
+
* there is one answer to "how often may a frame go out" rather than a constant per layer.
|
|
8
|
+
*
|
|
9
|
+
* The math itself lives in `@memberjunction/ai` (`realtimeVideoFrames`), shared with the meeting bot that also sends
|
|
10
|
+
* frames to the model; these names are thin wrappers over it.
|
|
11
|
+
*
|
|
12
|
+
* @module @memberjunction/ai-realtime-client
|
|
13
|
+
*/
|
|
14
|
+
import { REALTIME_DEFAULT_INBOUND_VIDEO_RATE, REALTIME_VIDEO_FRAME_JITTER_HEADROOM, RealtimeMinVideoFrameSpacingMs, RealtimeVideoFrameIntervalMs, } from '@memberjunction/ai';
|
|
15
|
+
/**
|
|
16
|
+
* The share of the nominal frame interval a pacer enforces as a MINIMUM spacing. Pacers upstream of
|
|
17
|
+
* the driver run on timers that jitter; enforcing exactly `1000 / rate` would drop a frame that arrived a
|
|
18
|
+
* few milliseconds early. At 1 fps this is the 750 ms backstop the Gemini driver has always applied.
|
|
19
|
+
*/
|
|
20
|
+
export const VIDEO_FRAME_JITTER_HEADROOM = REALTIME_VIDEO_FRAME_JITTER_HEADROOM;
|
|
21
|
+
/** The rate assumed when none was negotiated: 1 frame per second, the Live API ceiling today. */
|
|
22
|
+
export const DEFAULT_INBOUND_VIDEO_RATE = REALTIME_DEFAULT_INBOUND_VIDEO_RATE;
|
|
23
|
+
/**
|
|
24
|
+
* The nominal interval between frames, in milliseconds, for a negotiated rate (frames per second).
|
|
25
|
+
* An absent, zero, negative or non-finite rate falls back to {@link DEFAULT_INBOUND_VIDEO_RATE}.
|
|
26
|
+
*/
|
|
27
|
+
export function NominalVideoFrameIntervalMs(rate) {
|
|
28
|
+
return RealtimeVideoFrameIntervalMs(rate);
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* The minimum spacing, in milliseconds, a pacer should enforce between two frames to the model: the
|
|
32
|
+
* nominal interval less jitter headroom ({@link VIDEO_FRAME_JITTER_HEADROOM}).
|
|
33
|
+
*/
|
|
34
|
+
export function MinVideoFrameSpacingMs(rate) {
|
|
35
|
+
return RealtimeMinVideoFrameSpacingMs(rate);
|
|
36
|
+
}
|
|
37
|
+
//# sourceMappingURL=videoPacing.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"videoPacing.js","sourceRoot":"","sources":["../../src/media/videoPacing.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,OAAO,EACH,mCAAmC,EACnC,oCAAoC,EACpC,8BAA8B,EAC9B,4BAA4B,GAC/B,MAAM,oBAAoB,CAAC;AAE5B;;;;GAIG;AACH,MAAM,CAAC,MAAM,2BAA2B,GAAG,oCAAoC,CAAC;AAEhF,iGAAiG;AACjG,MAAM,CAAC,MAAM,0BAA0B,GAAG,mCAAmC,CAAC;AAE9E;;;GAGG;AACH,MAAM,UAAU,2BAA2B,CAAC,IAA+B;IACvE,OAAO,4BAA4B,CAAC,IAAI,CAAC,CAAC;AAC9C,CAAC;AAED;;;GAGG;AACH,MAAM,UAAU,sBAAsB,CAAC,IAA+B;IAClE,OAAO,8BAA8B,CAAC,IAAI,CAAC,CAAC;AAChD,CAAC"}
|