diff --git a/src/equicordplugins/instantScreenshare/index.tsx b/src/equicordplugins/instantScreenshare/index.tsx index 4a97276c..931d62ae 100644 --- a/src/equicordplugins/instantScreenshare/index.tsx +++ b/src/equicordplugins/instantScreenshare/index.tsx @@ -4,60 +4,31 @@ * SPDX-License-Identifier: GPL-3.0-or-later */ -import { definePluginSettings } from "@api/Settings"; import { Devs, EquicordDevs } from "@utils/constants"; -import definePlugin, { OptionType } from "@utils/types"; -import { findByCode, findByProps } from "@webpack"; +import definePlugin from "@utils/types"; +import { findByCodeLazy } from "@webpack"; import { ChannelStore, PermissionsBits, PermissionStore, SelectedChannelStore, UserStore } from "@webpack/common"; import { VoiceState } from "@webpack/types"; -const settings = definePluginSettings({ - streamType: { - description: "Stream screen or window", - type: OptionType.SELECT, - options: [ - { label: "Screen", value: "screen" }, - { label: "Window", value: "window" } - ], - default: "screen" - }, - streamWindowKeyword: { - description: "Keyword to search for in window title", - type: OptionType.STRING, - default: "", - placeholder: "Enter keyword" - } -}); +import { getCurrentMedia, settings } from "./utils"; + +const startStream = findByCodeLazy('type:"STREAM_START"'); let hasStreamed; -let sources; -let source; -async function startStream() { - const startStream = findByCode('type:"STREAM_START"'); - const mediaEngine = findByProps("getMediaEngine").getMediaEngine(); - const getDesktopSources = findByCode("desktop sources"); +async function autoStartStream() { const selected = SelectedChannelStore.getVoiceChannelId(); if (!selected) return; const channel = ChannelStore.getChannel(selected); if (channel.type === 13 || !PermissionStore.can(PermissionsBits.STREAM, channel)) return; - if (settings.store.streamType === "screen") { - sources = await getDesktopSources(mediaEngine, ["screen"], null); - source = sources[0]; - } else if (settings.store.streamType === "window") { - const keyword = settings.store.streamWindowKeyword?.toLowerCase(); - sources = await getDesktopSources(mediaEngine, ["window", "application"], null); - source = sources.find(s => s.name?.toLowerCase().includes(keyword)); - } - - if (!source) return; + const streamMedia = await getCurrentMedia(); startStream(channel.guild_id, selected, { "pid": null, - "sourceId": source.id, - "sourceName": source.name, + "sourceId": streamMedia.id, + "sourceName": streamMedia.name, "audioSourceId": null, "sound": true, "previewDisabled": false @@ -78,7 +49,7 @@ export default definePlugin({ if (channelId && !hasStreamed) { hasStreamed = true; - await startStream(); + await autoStartStream(); } if (!channelId) { diff --git a/src/equicordplugins/instantScreenshare/utils.tsx b/src/equicordplugins/instantScreenshare/utils.tsx new file mode 100644 index 00000000..cfb69580 --- /dev/null +++ b/src/equicordplugins/instantScreenshare/utils.tsx @@ -0,0 +1,102 @@ +/* + * Vencord, a Discord client mod + * Copyright (c) 2025 Vendicated and contributors + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +import { definePluginSettings } from "@api/Settings"; +import { Logger } from "@utils/Logger"; +import { OptionType } from "@utils/types"; +import { findByCodeLazy, findByPropsLazy } from "@webpack"; +import { Forms, SearchableSelect, useEffect, useState } from "@webpack/common"; + +interface PickerProps { + streamMediaSelection: any[]; + streamMedia: any[]; +} + +const mediaEngine = findByPropsLazy("getMediaEngine"); +const getDesktopSources = findByCodeLazy("desktop sources"); + +export const settings = definePluginSettings({ + streamMedia: { + description: "Media source to stream resets to main screen if not found", + type: OptionType.COMPONENT, + component: SettingSection, + }, +}); + +export async function getCurrentMedia() { + const media = mediaEngine.getMediaEngine(); + const sources = [ + ...(await getDesktopSources(media, ["screen"], null) ?? []), + ...(await getDesktopSources(media, ["window", "application"], null) ?? []) + ]; + const streamMedia = sources.find(screen => screen.id === settings.store.streamMedia); + console.log(sources); + + if (streamMedia) return streamMedia; + + new Logger("InstantScreenShare").error(`Stream Media "${settings.store.streamMedia}" not found. Resetting to default.`); + + settings.store.streamMedia = sources[0]; + return sources[0]; +} + +function StreamSimplePicker({ streamMediaSelection, streamMedia }: PickerProps) { + const options = streamMediaSelection.map(screen => ({ + label: screen.name, + value: screen.id, + default: streamMediaSelection[0], + })); + + return ( + o.value === streamMedia)} + onChange={v => settings.store.streamMedia = v} + closeOnSelect + /> + ); +} + +function ScreenSetting() { + const { streamMedia } = settings.use(["streamMedia"]); + const media = mediaEngine.getMediaEngine(); + const [streamMediaSelection, setStreamMediaSelection] = useState([]); + const [loading, setLoading] = useState(true); + + useEffect(() => { + let active = true; + async function fetchMedia() { + setLoading(true); + const sources = [ + ...(await getDesktopSources(media, ["screen"], null) ?? []), + ...(await getDesktopSources(media, ["window", "application"], null) ?? []) + ]; + + if (active) { + setStreamMediaSelection(sources); + setLoading(false); + } + } + fetchMedia(); + return () => { active = false; }; + }, []); + + if (loading) return Loading media sources...; + if (!streamMediaSelection.length) return No Media found.; + + return ; +} + +function SettingSection() { + return ( + + Stream Media + + + ); +}