INTEGRITY Документация

UI Kit Addons

Набор дополнений UI Kit, которые расширяют возможности готового UI Kit в RealtimeKit за счёт дополнительных интерактивных компонентов и элементов управления, делая встречи более удобными.

Эта страница недоступна для iOS, Android, React Nativeплатформа.

Библиотека addons для UI Kit предоставляет следующие категории компонентов:

Элементы управления организатора

Элементы управления организатора позволяют организаторам встречи управлять правами участников:

Реакции

Функции интерактивного вовлечения участников:

Плитка участника

Настройте интерфейс плитки участника:

Действия вкладки участника

Добавьте пользовательские действия на вкладку участников:

Фон видео

Применение визуальных эффектов к видео участника:

Панель управления

Настройте панель управления встречей:

Установка

npm i @cloudflare/realtimekit-ui-addons
npm i @cloudflare/realtimekit-ui-addons
npm i @cloudflare/realtimekit-ui-addons

Использование

import { useState, useEffect } from "react";
import {
	RealtimeKitProvider,
	useRealtimeKitClient,
} from "@cloudflare/realtimekit-react";
import { RtkMeeting } from "@cloudflare/realtimekit-react-ui";
import { registerAddons, defaultConfig } from "@cloudflare/realtimekit-ui";

// Import addons
import CameraHostControl from "@cloudflare/realtimekit-ui-addons/camera-host-control";
import MicHostControl from "@cloudflare/realtimekit-ui-addons/mic-host-control";
import ChatHostControl from "@cloudflare/realtimekit-ui-addons/chat-host-control";
import HandRaise from "@cloudflare/realtimekit-ui-addons/hand-raise";
import ReactionsManagerAddon from "@cloudflare/realtimekit-ui-addons/reactions-manager";
import ParticipantTileMenu from "@cloudflare/realtimekit-ui-addons/participant-tile-menu";
import ParticipantMenuItem from "@cloudflare/realtimekit-ui-addons/participant-menu-item";
import ParticipantsTabAction from "@cloudflare/realtimekit-ui-addons/participants-tab-action";
import ParticipantsTabToggle from "@cloudflare/realtimekit-ui-addons/participants-tab-toggle";
import RealtimeKitVideoBackground from "@cloudflare/realtimekit-ui-addons/video-background";
import CustomControlbarButton from "@cloudflare/realtimekit-ui-addons/custom-controlbar-button";

function App() {
	const [meeting, initMeeting] = useRealtimeKitClient();
	const [authToken, setAuthToken] = useState("<participant_auth_token>");
	const [config, setConfig] = useState(defaultConfig);

	useEffect(() => {
		if (authToken) {
			initMeeting({
				authToken: authToken,
			});
		}
	}, [authToken]);

	useEffect(() => {
		const initializeAddons = async () => {
			if (!meeting) return;

			// Initialize addons
			const cameraHostControl = await CameraHostControl.init({
				meeting,
				hostPresets: ["webinar_presenter"],
				targetPresets: ["webinar_viewer"],
				addActionInParticipantMenu: true,
			});

			const micHostControl = await MicHostControl.init({
				meeting,
				hostPresets: ["webinar_presenter"],
				targetPresets: ["webinar_viewer"],
				addActionInParticipantMenu: true,
			});

			const chatHostControl = await ChatHostControl.init({
				meeting,
				hostPresets: ["webinar_presenter"],
				targetPresets: ["webinar_viewer"],
				addActionInParticipantMenu: true,
			});

			const handRaise = await HandRaise.init({
				meeting,
				canRaiseHand: true,
				canManageRaisedHand: true,
				handRaiseIcon:
					'<svg fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path d="M4 12.02c0 1.06.2 2.1.6 3.08l.6 1.42c.22.55.64 1.01 1.17 1.29.27.14.56.21.86.21h2.55c.77 0 1.49-.41 1.87-1.08.5-.87 1.02-1.7 1.72-2.43l1.32-1.39c.44-.46.97-.84 1.49-1.23l.59-.45a.6.6 0 0 0 .23-.47c0-.75-.54-1.57-1.22-1.79a3.34 3.34 0 0 0-2.78.29V4.5a1.5 1.5 0 0 0-2.05-1.4 1.5 1.5 0 0 0-2.9 0A1.5 1.5 0 0 0 6 4.5v.09A1.5 1.5 0 0 0 4 6v6.02ZM8 4.5v4a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0v5a.5.5 0 0 0 1 0v-4a.5.5 0 0 1 1 0v6a.5.5 0 0 0 .85.37h.01c.22-.22.44-.44.72-.58.7-.35 2.22-.57 2.4.5l-.53.4c-.52.4-1.04.78-1.48 1.24l-1.33 1.38c-.75.79-1.31 1.7-1.85 2.63-.21.36-.6.58-1.01.58H7.23a.87.87 0 0 1-.4-.1 1.55 1.55 0 0 1-.71-.78l-.59-1.42a7.09 7.09 0 0 1-.53-2.7V6a.5.5 0 0 1 1 0v3.5a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0Z" fill="#ff0000"></path></svg>',
			});

			const CUSTOM_REACTIONS = [
				{ emoji: "🔥", label: "fire" },
				{ emoji: "😢", label: "sad" },
				{ emoji: "👍", label: "thumbs up" },
				{ emoji: "👎", label: "thumbs down" },
				{ emoji: "❤️", label: "heart" },
				{ emoji: "😂", label: "laugh" },
				{ emoji: "👏", label: "clap" },
				{ emoji: "🎉", label: "celebrate" },
			];

			const reactionsAddon = await ReactionsManagerAddon.init({
				meeting,
				reactions: CUSTOM_REACTIONS,
				canSendReactions: true,
			});

			const participantTileMenu = new ParticipantTileMenu(
				[
					{
						label: "Custom Toggle",
						onClick: (participantId) => {
							console.log("Clicked on custom toggle for ", participantId);
						},
					},
				],
				"top-right",
			);

			const rightTickSVG =
				"<svg xmlns='http://www.w3.org/2000/svg' width='24' height='24'><path d='M4 12l6 6 10-14' fill='none' stroke='currentColor' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'/></svg>";

			const participantMenuItem = new ParticipantMenuItem({
				label: "Custom Menu Item",
				icon: rightTickSVG,
				styles: "rtk-icon { color: green !important; }",
				onClick: () => {
					alert("Participant Menu Item clicked");
				},
			});

			const participantsTabAction = new ParticipantsTabAction({
				onClick: () => {
					alert("Clicked!");
				},
				label: "Click me",
				position: "start",
			});

			const participantsTabToggle = new ParticipantsTabToggle({
				onEnabled: () => {
					alert("toggled true!");
				},
				onDisabled: () => {
					alert("toggled false!");
				},
				label: "Click me",
				initialValue: () => true,
				position: "start",
			});

			const videoBackground = await RealtimeKitVideoBackground.init({
				modes: ["blur", "virtual", "random"],
				blurStrength: 30,
				meeting,
				images: [
					"https://images.unsplash.com/photo-1487088678257-3a541e6e3922?q=80&w=2874&auto=format&fit=crop&ixlib=rb-4.0.3",
					"https://images.unsplash.com/photo-1496715976403-7e36dc43f17b?q=80&w=2848&auto=format&fit=crop&ixlib=rb-4.0.3",
					"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
				],
				randomCount: 10,
				onVideoBackgroundUpdate: ({ backgroundMode, backgroundURL }) => {
					console.log("videoBackgroundUpdated => ", {
						backgroundMode,
						backgroundURL,
					});
				},
			});

			const customControlBarButton = new CustomControlbarButton({
				position: "left",
				icon: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none"><path d="M12 17.75a1.25 1.25 0 1 1 0 2.5a1.25 1.25 0 0 1 0-2.5zM12 14c0-2.5 4-2.5 4-6a4 4 0 1 0-8 0" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" /></svg>',
				label: "Click Me!",
				onClick: () => alert("Custom Control Bar Button Clicked"),
			});

			// Register addons
			const newConfig = registerAddons(
				[
					cameraHostControl,
					micHostControl,
					chatHostControl,
					handRaise,
					reactionsAddon,
					participantTileMenu,
					participantMenuItem,
					participantsTabAction,
					participantsTabToggle,
					videoBackground,
					customControlBarButton,
				],
				meeting,
			);

			setConfig(newConfig);
		};

		initializeAddons();
	}, [meeting]);

	return (
		<RealtimeKitProvider value={meeting}>
			<RtkMeeting showSetupScreen={true} meeting={meeting} config={config} />
		</RealtimeKitProvider>
	);
}

Добавьте библиотеку UI Kit в ваш HTML:

<script type="module">
	import { defineCustomElements } from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui@latest/loader/index.es2017.js";
	defineCustomElements();
</script>

Разместите rtk-meeting компонент в вашем HTML-файле:

<body>
	<rtk-meeting></rtk-meeting>
</body>

Инициализируйте встречу и настройте дополнения в своем скрипте:

<script type="module">
	import RealtimeKitClient from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit@latest/dist/index.es.js";
	import { registerAddons } from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui@latest/dist/index.es.js";

	// Import addons
	import CameraHostControl from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/camera-host-control/index.js";
	import MicHostControl from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/mic-host-control/index.js";
	import ChatHostControl from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/chat-host-control/index.js";
	import HandRaise from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/hand-raise/index.js";
	import ReactionsManagerAddon from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/reactions-manager/index.js";
	import ParticipantTileMenu from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/participant-tile-menu/index.js";
	import ParticipantMenuItem from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/participant-menu-item/index.js";
	import ParticipantsTabAction from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/participants-tab-action/index.js";
	import ParticipantsTabToggle from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/participants-tab-toggle/index.js";
	import RealtimeKitVideoBackground from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/video-background/index.js";
	import CustomControlbarButton from "https://cdn.jsdelivr.net/npm/@cloudflare/realtimekit-ui-addons@latest/custom-controlbar-button/index.js";

	// Initialize meeting
	const meeting = await RealtimeKitClient.init({
		authToken: "<participant_auth_token>",
	});

	// Initialize addons
	// Host controls
	const cameraHostControl = await CameraHostControl.init({
		meeting,
		hostPresets: ["webinar_presenter"],
		targetPresets: ["webinar_viewer"],
		addActionInParticipantMenu: true,
	});

	const micHostControl = await MicHostControl.init({
		meeting,
		hostPresets: ["webinar_presenter"],
		targetPresets: ["webinar_viewer"],
		addActionInParticipantMenu: true,
	});

	const chatHostControl = await ChatHostControl.init({
		meeting,
		hostPresets: ["webinar_presenter"],
		targetPresets: ["webinar_viewer"],
		addActionInParticipantMenu: true,
	});

	// Reactions
	const handRaise = await HandRaise.init({
		meeting,
		canRaiseHand: true,
		canManageRaisedHand: true,
		handRaiseIcon:
			'<svg fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path d="M4 12.02c0 1.06.2 2.1.6 3.08l.6 1.42c.22.55.64 1.01 1.17 1.29.27.14.56.21.86.21h2.55c.77 0 1.49-.41 1.87-1.08.5-.87 1.02-1.7 1.72-2.43l1.32-1.39c.44-.46.97-.84 1.49-1.23l.59-.45a.6.6 0 0 0 .23-.47c0-.75-.54-1.57-1.22-1.79a3.34 3.34 0 0 0-2.78.29V4.5a1.5 1.5 0 0 0-2.05-1.4 1.5 1.5 0 0 0-2.9 0A1.5 1.5 0 0 0 6 4.5v.09A1.5 1.5 0 0 0 4 6v6.02ZM8 4.5v4a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0v5a.5.5 0 0 0 1 0v-4a.5.5 0 0 1 1 0v6a.5.5 0 0 0 .85.37h.01c.22-.22.44-.44.72-.58.7-.35 2.22-.57 2.4.5l-.53.4c-.52.4-1.04.78-1.48 1.24l-1.33 1.38c-.75.79-1.31 1.7-1.85 2.63-.21.36-.6.58-1.01.58H7.23a.87.87 0 0 1-.4-.1 1.55 1.55 0 0 1-.71-.78l-.59-1.42a7.09 7.09 0 0 1-.53-2.7V6a.5.5 0 0 1 1 0v3.5a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0Z" fill="#ff0000"></path></svg>',
	});

	const CUSTOM_REACTIONS = [
		{ emoji: "🔥", label: "fire" },
		{ emoji: "😢", label: "sad" },
		{ emoji: "👍", label: "thumbs up" },
		{ emoji: "👎", label: "thumbs down" },
		{ emoji: "❤️", label: "heart" },
		{ emoji: "😂", label: "laugh" },
		{ emoji: "👏", label: "clap" },
		{ emoji: "🎉", label: "celebrate" },
	];

	const reactionsAddon = await ReactionsManagerAddon.init({
		meeting,
		reactions: CUSTOM_REACTIONS,
		canSendReactions: true,
	});

	// Participant Tile
	const participantTileMenu = new ParticipantTileMenu(
		[
			{
				label: "Custom Toggle",
				onClick: (participantId) => {
					console.log("Clicked on custom toggle for ", participantId);
				},
			},
		],
		"top-right",
	);

	// Participant Tab Actions
	const rightTickSVG =
		"<svg xmlns='http://www.w3.org/2000/svg' width='24' height='24'><path d='M4 12l6 6 10-14' fill='none' stroke='currentColor' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'/></svg>";

	const participantMenuItem = new ParticipantMenuItem({
		label: "Custom Menu Item",
		icon: rightTickSVG,
		styles: "rtk-icon { color: green !important; }",
		onClick: () => {
			alert("Participant Menu Item clicked");
		},
	});

	const participantsTabAction = new ParticipantsTabAction({
		onClick: () => {
			alert("Clicked!");
		},
		label: "Click me",
		position: "start",
	});

	const participantsTabToggle = new ParticipantsTabToggle({
		onEnabled: () => {
			alert("toggled true!");
		},
		onDisabled: () => {
			alert("toggled false!");
		},
		label: "Click me",
		initialValue: () => true,
		position: "start",
	});

	// Video Background (Effects)
	const videoBackground = await RealtimeKitVideoBackground.init({
		modes: ["blur", "virtual", "random"],
		blurStrength: 30, // 0 - 100 for opacity
		meeting,
		images: [
			"https://images.unsplash.com/photo-1487088678257-3a541e6e3922?q=80&w=2874&auto=format&fit=crop&ixlib=rb-4.0.3",
			"https://images.unsplash.com/photo-1496715976403-7e36dc43f17b?q=80&w=2848&auto=format&fit=crop&ixlib=rb-4.0.3",
			"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
		],
		randomCount: 10,
		onVideoBackgroundUpdate: ({ backgroundMode, backgroundURL }) => {
			console.log("videoBackgroundUpdated => ", {
				backgroundMode,
				backgroundURL,
			});
		},
	});

	// Control Bar
	const customControlBarButton = new CustomControlbarButton({
		position: "left",
		icon: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none"><path d="M12 17.75a1.25 1.25 0 1 1 0 2.5a1.25 1.25 0 0 1 0-2.5zM12 14c0-2.5 4-2.5 4-6a4 4 0 1 0-8 0" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" /></svg>',
		label: "Click Me!",
		onClick: () => alert("Custom Control Bar Button Clicked"),
	});

	// Register addons
	const newConfig = registerAddons(
		[
			cameraHostControl,
			micHostControl,
			chatHostControl,
			handRaise,
			reactionsAddon,
			participantTileMenu,
			participantMenuItem,
			participantsTabAction,
			participantsTabToggle,
			videoBackground,
			customControlBarButton,
		],
		meeting,
	);

	// Apply config to meeting component
	document.querySelector("rtk-meeting").showSetupScreen = true;
	document.querySelector("rtk-meeting").meeting = meeting;
	document.querySelector("rtk-meeting").config = newConfig;
</script>

В шаблоне вашего компонента добавьте компонент встречи:

<rtk-meeting [meeting]="meeting" [config]="config"></rtk-meeting>

В файле TypeScript вашего компонента:

import { Component, OnInit } from "@angular/core";
import RealtimeKitClient from "@cloudflare/realtimekit";
import { registerAddons, defaultConfig } from "@cloudflare/realtimekit-ui";

// Import addons
import CameraHostControl from "@cloudflare/realtimekit-ui-addons/camera-host-control";
import MicHostControl from "@cloudflare/realtimekit-ui-addons/mic-host-control";
import ChatHostControl from "@cloudflare/realtimekit-ui-addons/chat-host-control";
import HandRaise from "@cloudflare/realtimekit-ui-addons/hand-raise";
import ReactionsManagerAddon from "@cloudflare/realtimekit-ui-addons/reactions-manager";
import ParticipantTileMenu from "@cloudflare/realtimekit-ui-addons/participant-tile-menu";
import ParticipantMenuItem from "@cloudflare/realtimekit-ui-addons/participant-menu-item";
import ParticipantsTabAction from "@cloudflare/realtimekit-ui-addons/participants-tab-action";
import ParticipantsTabToggle from "@cloudflare/realtimekit-ui-addons/participants-tab-toggle";
import RealtimeKitVideoBackground from "@cloudflare/realtimekit-ui-addons/video-background";
import CustomControlbarButton from "@cloudflare/realtimekit-ui-addons/custom-controlbar-button";

@Component({
	selector: "app-meeting",
	templateUrl: "./meeting.component.html",
})
export class MeetingComponent implements OnInit {
	meeting: any;
	config: any = defaultConfig;

	async ngOnInit() {
		// Initialize meeting
		this.meeting = await RealtimeKitClient.init({
			authToken: "<participant_auth_token>",
		});

		// Initialize addons
		const cameraHostControl = await CameraHostControl.init({
			meeting: this.meeting,
			hostPresets: ["webinar_presenter"],
			targetPresets: ["webinar_viewer"],
			addActionInParticipantMenu: true,
		});

		const micHostControl = await MicHostControl.init({
			meeting: this.meeting,
			hostPresets: ["webinar_presenter"],
			targetPresets: ["webinar_viewer"],
			addActionInParticipantMenu: true,
		});

		const chatHostControl = await ChatHostControl.init({
			meeting: this.meeting,
			hostPresets: ["webinar_presenter"],
			targetPresets: ["webinar_viewer"],
			addActionInParticipantMenu: true,
		});

		const handRaise = await HandRaise.init({
			meeting: this.meeting,
			canRaiseHand: true,
			canManageRaisedHand: true,
			handRaiseIcon:
				'<svg fill="currentColor" viewBox="0 0 20 20" xmlns="http://www.w3.org/2000/svg"><path d="M4 12.02c0 1.06.2 2.1.6 3.08l.6 1.42c.22.55.64 1.01 1.17 1.29.27.14.56.21.86.21h2.55c.77 0 1.49-.41 1.87-1.08.5-.87 1.02-1.7 1.72-2.43l1.32-1.39c.44-.46.97-.84 1.49-1.23l.59-.45a.6.6 0 0 0 .23-.47c0-.75-.54-1.57-1.22-1.79a3.34 3.34 0 0 0-2.78.29V4.5a1.5 1.5 0 0 0-2.05-1.4 1.5 1.5 0 0 0-2.9 0A1.5 1.5 0 0 0 6 4.5v.09A1.5 1.5 0 0 0 4 6v6.02ZM8 4.5v4a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0v5a.5.5 0 0 0 1 0v-4a.5.5 0 0 1 1 0v6a.5.5 0 0 0 .85.37h.01c.22-.22.44-.44.72-.58.7-.35 2.22-.57 2.4.5l-.53.4c-.52.4-1.04.78-1.48 1.24l-1.33 1.38c-.75.79-1.31 1.7-1.85 2.63-.21.36-.6.58-1.01.58H7.23a.87.87 0 0 1-.4-.1 1.55 1.55 0 0 1-.71-.78l-.59-1.42a7.09 7.09 0 0 1-.53-2.7V6a.5.5 0 0 1 1 0v3.5a.5.5 0 0 0 1 0v-5a.5.5 0 0 1 1 0Z" fill="#ff0000"></path></svg>',
		});

		const CUSTOM_REACTIONS = [
			{ emoji: "🔥", label: "fire" },
			{ emoji: "😢", label: "sad" },
			{ emoji: "👍", label: "thumbs up" },
			{ emoji: "👎", label: "thumbs down" },
			{ emoji: "❤️", label: "heart" },
			{ emoji: "😂", label: "laugh" },
			{ emoji: "👏", label: "clap" },
			{ emoji: "🎉", label: "celebrate" },
		];

		const reactionsAddon = await ReactionsManagerAddon.init({
			meeting: this.meeting,
			reactions: CUSTOM_REACTIONS,
			canSendReactions: true,
		});

		const participantTileMenu = new ParticipantTileMenu(
			[
				{
					label: "Custom Toggle",
					onClick: (participantId: string) => {
						console.log("Clicked on custom toggle for ", participantId);
					},
				},
			],
			"top-right",
		);

		const rightTickSVG =
			"<svg xmlns='http://www.w3.org/2000/svg' width='24' height='24'><path d='M4 12l6 6 10-14' fill='none' stroke='currentColor' stroke-width='3' stroke-linecap='round' stroke-linejoin='round'/></svg>";

		const participantMenuItem = new ParticipantMenuItem({
			label: "Custom Menu Item",
			icon: rightTickSVG,
			styles: "rtk-icon { color: green !important; }",
			onClick: () => {
				alert("Participant Menu Item clicked");
			},
		});

		const participantsTabAction = new ParticipantsTabAction({
			onClick: () => {
				alert("Clicked!");
			},
			label: "Click me",
			position: "start",
		});

		const participantsTabToggle = new ParticipantsTabToggle({
			onEnabled: () => {
				alert("toggled true!");
			},
			onDisabled: () => {
				alert("toggled false!");
			},
			label: "Click me",
			initialValue: () => true,
			position: "start",
		});

		const videoBackground = await RealtimeKitVideoBackground.init({
			modes: ["blur", "virtual", "random"],
			blurStrength: 30,
			meeting: this.meeting,
			images: [
				"https://images.unsplash.com/photo-1487088678257-3a541e6e3922?q=80&w=2874&auto=format&fit=crop&ixlib=rb-4.0.3",
				"https://images.unsplash.com/photo-1496715976403-7e36dc43f17b?q=80&w=2848&auto=format&fit=crop&ixlib=rb-4.0.3",
				"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
			],
			randomCount: 10,
			onVideoBackgroundUpdate: ({ backgroundMode, backgroundURL }: any) => {
				console.log("videoBackgroundUpdated => ", {
					backgroundMode,
					backgroundURL,
				});
			},
		});

		const customControlBarButton = new CustomControlbarButton({
			position: "left",
			icon: '<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none"><path d="M12 17.75a1.25 1.25 0 1 1 0 2.5a1.25 1.25 0 0 1 0-2.5zM12 14c0-2.5 4-2.5 4-6a4 4 0 1 0-8 0" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" /></svg>',
			label: "Click Me!",
			onClick: () => alert("Custom Control Bar Button Clicked"),
		});

		// Register addons
		this.config = registerAddons(
			[
				cameraHostControl,
				micHostControl,
				chatHostControl,
				handRaise,
				reactionsAddon,
				participantTileMenu,
				participantMenuItem,
				participantsTabAction,
				participantsTabToggle,
				videoBackground,
				customControlBarButton,
			],
			this.meeting,
		);
	}
}

Программное управление

Некоторые дополнения поддерживают программное управление для динамических изменений во время встречи.

Фон видео

Фоны видео можно применять, заменять или удалять программно:

// Apply a virtual background
await videoBackground.applyVirtualBackground(
	"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
);

// Apply a blur background
await videoBackground.applyBlurBackground();

// Remove background (return to normal video)
await videoBackground.removeBackground();

Некоторые дополнения поддерживают программное управление для динамических изменений во время встречи.

Фон видео

Фоны видео можно применять, заменять или удалять программно:

// Apply a virtual background
await videoBackground.applyVirtualBackground(
	"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
);

// Apply a blur background
await videoBackground.applyBlurBackground();

// Remove background (return to normal video)
await videoBackground.removeBackground();

Некоторые дополнения поддерживают программное управление для динамических изменений во время встречи.

Фон видео

Фоны видео можно применять, заменять или удалять программно:

// Apply a virtual background
await videoBackground.applyVirtualBackground(
	"https://images.unsplash.com/photo-1600431521340-491eca880813?q=80&w=2938&auto=format&fit=crop&ixlib=rb-4.0.3",
);

// Apply a blur background
await videoBackground.applyBlurBackground();

// Remove background (return to normal video)
await videoBackground.removeBackground();