Merge branch 'main' into dev

This commit is contained in:
thororen1234 2024-12-09 07:23:37 -05:00
commit 85cb848ff0
2 changed files with 102 additions and 118 deletions

View file

@ -3,19 +3,21 @@
* Copyright (c) 2024 Vendicated and contributors * Copyright (c) 2024 Vendicated and contributors
* SPDX-License-Identifier: GPL-3.0-or-later * SPDX-License-Identifier: GPL-3.0-or-later
*/ */
import { definePluginSettings, Settings } from "@api/Settings";
import { EquicordDevs } from "@utils/constants"; import { addChatBarButton, ChatBarButton, removeChatBarButton } from "@api/ChatButtons";
import definePlugin, { OptionType } from "@utils/types";
import { ApplicationCommandInputType, ApplicationCommandOptionType, findOption, sendBotMessage } from "@api/Commands"; import { ApplicationCommandInputType, ApplicationCommandOptionType, findOption, sendBotMessage } from "@api/Commands";
import { findGroupChildrenByChildId, NavContextMenuPatchCallback } from "@api/ContextMenu"; import { findGroupChildrenByChildId, NavContextMenuPatchCallback } from "@api/ContextMenu";
import { addChatBarButton, ChatBarButton, removeChatBarButton } from "@api/ChatButtons";
import { addPreSendListener, removePreSendListener, SendListener } from "@api/MessageEvents"; import { addPreSendListener, removePreSendListener, SendListener } from "@api/MessageEvents";
import { transferMessage } from "./native"; import { definePluginSettings, Settings } from "@api/Settings";
import { ErrorCard } from "@components/ErrorCard"; import { ErrorCard } from "@components/ErrorCard";
import { Link } from "@components/Link"; import { Link } from "@components/Link";
import { EquicordDevs } from "@utils/constants";
import { Margins } from "@utils/margins"; import { Margins } from "@utils/margins";
import { classes } from "@utils/misc"; import { classes } from "@utils/misc";
import { MessageStore, Menu, React, Forms } from "@webpack/common"; import definePlugin, { OptionType } from "@utils/types";
import { Forms, Menu, MessageStore, React } from "@webpack/common";
import { transferMessage } from "./native";
const furudosettings = definePluginSettings( const furudosettings = definePluginSettings(
{ {
@ -104,7 +106,7 @@ function messageSendListenerFuncs() {
const FurudoSpeakChatToggle: ChatBarButton = ({ isMainChat }) => { const FurudoSpeakChatToggle: ChatBarButton = ({ isMainChat }) => {
const { isEnabled, showIcon } = furudosettings.use(["isEnabled", "showIcon"]); const { isEnabled, showIcon } = furudosettings.use(["isEnabled", "showIcon"]);
const toggle = async () => { const toggle = async () => {
let done = await togglefunc(); const done = await togglefunc();
return done; return done;
}; };
@ -199,7 +201,7 @@ export default definePlugin({
], ],
execute: async (args, ctx) => { execute: async (args, ctx) => {
furudosettings.store.isEnabled = !!findOption(args, "value", !furudosettings.store.isEnabled); furudosettings.store.isEnabled = !!findOption(args, "value", !furudosettings.store.isEnabled);
if (furudosettings.store.isEnabled) { messageSendListenerFuncs(); }; if (furudosettings.store.isEnabled) { messageSendListenerFuncs(); }
sendBotMessage(ctx.channel.id, { sendBotMessage(ctx.channel.id, {
content: furudosettings.store.isEnabled ? "FurudoSpeak enabled!" : "FurudoSpeak disabled!", content: furudosettings.store.isEnabled ? "FurudoSpeak enabled!" : "FurudoSpeak disabled!",
}); });

View file

@ -1,31 +1,16 @@
/* /*
* Vencord, a modification for Discord's desktop app * Vencord, a Discord client mod
* Copyright (c) 2023 Vendicated and contributors * Copyright (c) 2024 Vendicated and contributors
* * SPDX-License-Identifier: GPL-3.0-or-later
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/ */
import { definePluginSettings, Settings } from "@api/Settings"; import { definePluginSettings } from "@api/Settings";
import { ErrorCard } from "@components/ErrorCard";
import { Devs, EquicordDevs } from "@utils/constants"; import { Devs, EquicordDevs } from "@utils/constants";
import { Logger } from "@utils/Logger";
import { Margins } from "@utils/margins"; import { Margins } from "@utils/margins";
import { wordsToTitle } from "@utils/text"; import { wordsToTitle } from "@utils/text";
import definePlugin, { import definePlugin, {
OptionType, OptionType,
PluginOptionsItem, PluginOptionsItem,
ReporterTestable,
} from "@utils/types"; } from "@utils/types";
import { findByPropsLazy } from "@webpack"; import { findByPropsLazy } from "@webpack";
import { import {
@ -61,7 +46,6 @@ const VoiceStateStore = findByPropsLazy(
async function speak( async function speak(
text: string, text: string,
settings: any = Settings.plugins.VcNarrator
) { ) {
if (text.trim().length === 0) return; if (text.trim().length === 0) return;
const response = await fetch( const response = await fetch(
@ -77,7 +61,7 @@ async function speak(
referrerPolicy: "no-referrer", referrerPolicy: "no-referrer",
body: JSON.stringify({ body: JSON.stringify({
text: text, text: text,
voice: Settings.plugins.VcNarratorCustom.customVoice, voice: settings.store.customVoice,
}), }),
} }
); );
@ -94,15 +78,13 @@ async function speak(
const url = URL.createObjectURL(blob); const url = URL.createObjectURL(blob);
const audio = new Audio(url); const audio = new Audio(url);
audio.volume = 0.3; audio.volume = settings.store.volume;
audio.playbackRate = settings.store.rate;
audio.play(); audio.play();
audio.volume = settings.volume;
audio.playbackRate = settings.rate;
} }
function clean(str: string) { function clean(str: string) {
const replacer = Settings.plugins.VcNarrator.latinOnly const replacer = settings.store.latinOnly
? /[^\p{Script=Latin}\p{Number}\p{Punctuation}\s]/gu ? /[^\p{Script=Latin}\p{Number}\p{Punctuation}\s]/gu
: /[^\p{Letter}\p{Number}\p{Punctuation}\s]/gu; : /[^\p{Letter}\p{Number}\p{Punctuation}\s]/gu;
@ -155,9 +137,9 @@ function getTypeAndChannelId(
} }
function playSample(tempSettings: any, type: string) { function playSample(tempSettings: any, type: string) {
const settings = Object.assign( const settingsobj = Object.assign(
{}, {},
Settings.plugins.VcNarrator, settings.store,
tempSettings tempSettings
); );
const currentUser = UserStore.getCurrentUser(); const currentUser = UserStore.getCurrentUser();
@ -165,87 +147,17 @@ function playSample(tempSettings: any, type: string) {
speak( speak(
formatText( formatText(
settings[type + "Message"], settingsobj[type + "Message"],
currentUser.username, currentUser.username,
"general", "general",
(currentUser as any).globalName ?? currentUser.username, (currentUser as any).globalName ?? currentUser.username,
GuildMemberStore.getNick(myGuildId, currentUser.id) ?? GuildMemberStore.getNick(myGuildId, currentUser.id) ??
currentUser.username currentUser.username
),
settings
);
}
export default definePlugin({
name: "VcNarratorCustom",
description:
"Announces when users join, leave, or move voice channels via narrator. TikTok TTS version; speechSynthesis is pretty boring. Ported from https://github.com/Loukious/Vencord",
authors: [Devs.Ven, Devs.Nyako, EquicordDevs.Loukios, EquicordDevs.examplegit],
flux: {
VOICE_STATE_UPDATES({ voiceStates }: { voiceStates: VoiceState[]; }) {
const myGuildId = SelectedGuildStore.getGuildId();
const myChanId = SelectedChannelStore.getVoiceChannelId();
const myId = UserStore.getCurrentUser().id;
if (
ChannelStore.getChannel(myChanId!)?.type ===
13 /* Stage Channel */
) )
return;
for (const state of voiceStates) {
const { userId, channelId, oldChannelId } = state;
const isMe = userId === myId;
if (!isMe) {
if (!myChanId) continue;
if (channelId !== myChanId && oldChannelId !== myChanId)
continue;
}
const [type, id] = getTypeAndChannelId(state, isMe);
if (!type) continue;
const template = Settings.plugins.VcNarrator[type + "Message"];
const user =
isMe && !Settings.plugins.VcNarrator.sayOwnName
? ""
: UserStore.getUser(userId).username;
const displayName =
user &&
((UserStore.getUser(userId) as any).globalName ?? user);
const nickname =
user &&
(GuildMemberStore.getNick(myGuildId, userId) ??
displayName);
const channel = ChannelStore.getChannel(id).name;
speak(
formatText(template, user, channel, displayName, nickname)
); );
} }
},
AUDIO_TOGGLE_SELF_MUTE() { const settings = definePluginSettings({
const chanId = SelectedChannelStore.getVoiceChannelId()!;
const s = VoiceStateStore.getVoiceStateForChannel(
chanId
) as VoiceState;
if (!s) return;
},
AUDIO_TOGGLE_SELF_DEAF() {
const chanId = SelectedChannelStore.getVoiceChannelId()!;
const s = VoiceStateStore.getVoiceStateForChannel(
chanId
) as VoiceState;
if (!s) return;
},
},
optionsCache: null as Record<string, PluginOptionsItem> | null,
settings: definePluginSettings(
{
customVoice: { customVoice: {
type: OptionType.STRING, type: OptionType.STRING,
description: "Custom voice id, currently just tiktok", description: "Custom voice id, currently just tiktok",
@ -316,14 +228,84 @@ export default definePlugin({
description: "Undeafen Message (only self for now)", description: "Undeafen Message (only self for now)",
default: "{{DISPLAY_NAME}} undeafened", default: "{{DISPLAY_NAME}} undeafened",
}, },
},), });
export default definePlugin({
name: "VcNarratorCustom",
description:
"Announces when users join, leave, or move voice channels via narrator. TikTok TTS version; speechSynthesis is pretty boring. Ported from https://github.com/Loukious/Vencord",
authors: [Devs.Ven, Devs.Nyako, EquicordDevs.Loukios, EquicordDevs.examplegit],
flux: {
VOICE_STATE_UPDATES({ voiceStates }: { voiceStates: VoiceState[]; }) {
const myGuildId = SelectedGuildStore.getGuildId();
const myChanId = SelectedChannelStore.getVoiceChannelId();
const myId = UserStore.getCurrentUser().id;
if (
ChannelStore.getChannel(myChanId!)?.type ===
13 /* Stage Channel */
)
return;
for (const state of voiceStates) {
const { userId, channelId, oldChannelId } = state;
const isMe = userId === myId;
if (!isMe) {
if (!myChanId) continue;
if (channelId !== myChanId && oldChannelId !== myChanId)
continue;
}
const [type, id] = getTypeAndChannelId(state, isMe);
if (!type) continue;
const template = settings.store[type + "Message"];
const user =
isMe && !settings.store.sayOwnName
? ""
: UserStore.getUser(userId).username;
const displayName =
user &&
((UserStore.getUser(userId) as any).globalName ?? user);
const nickname =
user &&
(GuildMemberStore.getNick(myGuildId, userId) ??
displayName);
const channel = ChannelStore.getChannel(id).name;
speak(
formatText(template, user, channel, displayName, nickname)
);
}
},
AUDIO_TOGGLE_SELF_MUTE() {
const chanId = SelectedChannelStore.getVoiceChannelId()!;
const s = VoiceStateStore.getVoiceStateForChannel(
chanId
) as VoiceState;
if (!s) return;
},
AUDIO_TOGGLE_SELF_DEAF() {
const chanId = SelectedChannelStore.getVoiceChannelId()!;
const s = VoiceStateStore.getVoiceStateForChannel(
chanId
) as VoiceState;
if (!s) return;
},
},
optionsCache: null as Record<string, PluginOptionsItem> | null,
settings,
settingsAboutComponent({ tempSettings: s }) { settingsAboutComponent({ tempSettings: s }) {
const types = useMemo( const types = useMemo(
() => () =>
Object.keys(Vencord.Plugins.plugins.VcNarrator.options!) Object.keys(settings.store)
.filter((k) => k.endsWith("Message")) .filter(k => k.endsWith("Message"))
.map((k) => k.slice(0, -7)), .map(k => k.slice(0, -7)),
[] []
); );
@ -365,7 +347,7 @@ export default definePlugin({
}} }}
className={"vc-narrator-buttons"} className={"vc-narrator-buttons"}
> >
{types.map((t) => ( {types.map(t => (
<Button key={t} onClick={() => playSample(s, t)}> <Button key={t} onClick={() => playSample(s, t)}>
{wordsToTitle([t])} {wordsToTitle([t])}
</Button> </Button>