import { ChromecastDevice } from "./ChromecastDevice"; import { FullscreenWindowConfig, FullscreenWindowDevice } from "./FullscreenWindow"; import { LocalAudioDevice } from "./LocalAudioDevice"; export type DeviceConfig = FullscreenWindowConfig; export type Devices = FullscreenWindowDevice | ChromecastDevice; export interface RemoteDeviceManagerOptions { devices: (DeviceConfig)[]; } export interface RemoteDeviceManagerCtx { audioContext: AudioContext; } export class RemoteDeviceManager { private _devices:Devices[] = []; private localAudioDevice: LocalAudioDevice; constructor(private options: RemoteDeviceManagerOptions, private ctx: RemoteDeviceManagerCtx) { for (const device of options.devices) { this.createInstance(device); } this.localAudioDevice = new LocalAudioDevice(ctx.audioContext); } get devices(): Devices[] { return this._devices; } get audioDevices() { return [ ...this._devices.filter(d => d.audioSink), this.localAudioDevice, ]; } private async createInstance(device: DeviceConfig): Promise { if (device.type === 'fullscreen-window') { const deviceInstance = new FullscreenWindowDevice(device, this.ctx); this._devices.push(deviceInstance); return deviceInstance; } } async add(device: DeviceConfig, connect: boolean = false): Promise { console.log('add', device); const instance = await this.createInstance(device); if (!instance) { return; } this.persist(); if (connect) { await instance.connect(); } } removeDevice(device: Devices) { this._devices = this._devices.filter(d => d !== device); this.persist() } async availableDevices(): Promise { return [ ...(await FullscreenWindowDevice.getDevices()), ]; } async connectChromeCast() { new ChromecastDevice(this.ctx) .connect() .then((dev) => { this._devices.push(dev); (this._devices.at(-1) as ChromecastDevice).setup(); }) } get config(): RemoteDeviceManagerOptions { return { ...this.options, devices: this._devices .map(d => { // @ts-ignore return d.config; }) .filter(d => d !== undefined) as DeviceConfig[] }; } persist() { console.log('persist'); localStorage.setItem('remote-devices', JSON.stringify(this.config)); } static restore(ctx: RemoteDeviceManagerCtx): RemoteDeviceManager { const data = localStorage.getItem('remote-devices'); if (data) { return new RemoteDeviceManager(JSON.parse(data), ctx); } return new RemoteDeviceManager({devices: []}, ctx); } }