Merge branch 'dev'

This commit is contained in:
thororen1234 2025-09-15 15:12:38 -04:00
commit e764358ed5
No known key found for this signature in database
17 changed files with 308 additions and 254 deletions

View file

@ -162,6 +162,7 @@ export const globPlugins = kind => ({
const fileName = file.name;
if (fileName.startsWith("_") || fileName.startsWith(".")) continue;
if (fileName === "index.ts") continue;
if (/\.zip|rar|7z|tar|gz|bz2/.test(fileName)) continue;
const target = getPluginTarget(fileName);

View file

@ -155,7 +155,7 @@ async function init() {
syncSettings();
if (!IS_WEB && !IS_UPDATER_DISABLED || !IS_DEV) {
if (!IS_DEV && !IS_WEB && !IS_UPDATER_DISABLED) {
runUpdateCheck();
// this tends to get really annoying, so only do this if the user has auto-update without notification enabled

View file

@ -50,7 +50,7 @@ export function DonateButton({
{...props}
look={look}
color={color}
onClick={() => VencordNative.native.openExternal("https://ko-fi.com/authenticators")}
onClick={() => VencordNative.native.openExternal("https://github.com/sponsors/thororen1234")}
innerClassName="vc-donate-button"
>
<Heart />

View file

@ -8,7 +8,6 @@ import "./VencordTab.css";
import { openNotificationLogModal } from "@api/Notifications/notificationLog";
import { useSettings } from "@api/Settings";
import { classNameFactory } from "@api/Styles";
import { FolderIcon, GithubIcon, LogIcon, PaintbrushIcon, RestartIcon } from "@components/Icons";
import { openContributorModal, openPluginModal, SettingsTab, wrapTab } from "@components/settings";
import { DonateButton, InviteButton } from "@components/settings/DonateButton";
@ -24,8 +23,6 @@ import BadgeAPI from "plugins/_api/badges";
import { openNotificationSettingsModal } from "./NotificationSettings";
const cl = classNameFactory("vc-settings-");
const DEFAULT_DONATE_IMAGE = "https://cdn.discordapp.com/emojis/1026533090627174460.png";
const SHIGGY_DONATE_IMAGE = "https://i.imgur.com/57ATLZu.png";
@ -339,14 +336,14 @@ function DonateButtonComponent() {
);
}
function isVencordDonor(userId: string): boolean {
const donorBadges = BadgeAPI.getDonorBadges(userId);
return GuildMemberStore.getMember(VC_GUILD_ID, userId)?.roles.includes(VC_DONOR_ROLE_ID) || !!donorBadges;
}
export default wrapTab(EquicordSettings, "Equicord Settings");
export function isEquicordDonor(userId: string): boolean {
const donorBadges = BadgeAPI.getEquicordDonorBadges(userId);
return GuildMemberStore.getMember(GUILD_ID, userId)?.roles.includes(DONOR_ROLE_ID) || !!donorBadges;
}
export default wrapTab(EquicordSettings, "Equicord Settings");
export function isVencordDonor(userId: string): boolean {
const donorBadges = BadgeAPI.getDonorBadges(userId);
return GuildMemberStore.getMember(VC_GUILD_ID, userId)?.roles.includes(VC_DONOR_ROLE_ID) || !!donorBadges;
}

View file

@ -1,80 +0,0 @@
/*
* Vencord, a Discord client mod
* Copyright (c) 2024 Vendicated and contributors
* SPDX-License-Identifier: GPL-3.0-or-later
*/
import { NavContextMenuPatchCallback } from "@api/ContextMenu";
import { EquicordDevs } from "@utils/constants";
import definePlugin from "@utils/types";
import { Menu, ChannelStore, NavigationRouter, FluxDispatcher, MessageActions, MessageStore } from "@webpack/common";
interface ChannelSelectEvent {
type: "CHANNEL_SELECT";
channelId: string | null;
guildId: string | null;
}
let lastChan = "0";
function jumpToPresent(channelId, { limit }: { limit?: number } = {}) {
MessageActions.trackJump(channelId, null, "Present");
const jump = { present: true };
if (MessageStore.hasPresent(channelId)) {
FluxDispatcher.dispatch({
type: "LOAD_MESSAGES_SUCCESS_CACHED",
jump,
channelId,
limit
});
} else {
MessageActions.fetchMessages({
channelId,
limit,
jump
});
}
}
function autoJump(channel: any) {
const guildId = channel.guild_id ?? "@me";
const channelId = channel.id;
if (channelId === lastChan) return;
NavigationRouter.transitionTo(`/channels/${guildId}/${channelId}`);
lastChan = channelId;
jumpToPresent(channelId, { limit: 100 });
}
const MenuPatch: NavContextMenuPatchCallback = (children, { channel }) => {
children.push(
<Menu.MenuItem
id="auto-jump"
label="Jump to Last Message"
action={() => autoJump(channel)}
/>
);
};
export default definePlugin({
name: "AutoJump",
description: "Automatically jumps to the last message in selected channel & adds a context-menu option to jump to the last message.",
authors: [EquicordDevs.omaw],
contextMenus: {
"channel-context": MenuPatch,
"user-context": MenuPatch,
"thread-context": MenuPatch
},
flux: {
async CHANNEL_SELECT({ guildId, channelId }: ChannelSelectEvent) {
if (!guildId || !channelId) return;
const channel = ChannelStore.getChannel(channelId);
if (!channel || lastChan === channel.id) return;
autoJump(channel);
}
}
});

View file

@ -15,6 +15,11 @@ const settings = definePluginSettings({
description: "Automatically fill command with all arguements instead of just required ones",
type: OptionType.BOOLEAN,
default: true,
},
allowNewlinesInCommands: {
description: "Allow newlines in command inputs (Shift + Enter)",
type: OptionType.BOOLEAN,
default: true,
}
});
@ -40,6 +45,26 @@ export default definePlugin({
replace: "true"
},
]
},
{
find: '"italics"),!0;',
predicate: () => settings.store.allowNewlinesInCommands,
replacement: [
{
match: /case (\i\.\i)\.TAB:if\(null!=(\i).selection&&\i\((\i)(?=.{0,300}(\i\.\i\.insertText))/,
replace: (orig, keys, editor, event, insertText) => {
return `case ${keys}.ENTER:
if(${event}.shiftKey){
${event}.preventDefault();
${event}.stopPropagation();
${insertText}(${editor},'\\n');
return true;
}
break;
${orig}`;
}
}
]
}
],
commands: [

View file

@ -1,49 +1,42 @@
/*
* Vencord, a modification for Discord's desktop app
* Copyright (c) 2022 Vendicated and Megumin
*
* 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/>.
*/
* Vencord, a Discord client mod
* Copyright (c) 2025 Vendicated and contributors
* SPDX-License-Identifier: GPL-3.0-or-later
*/
import "@equicordplugins/_misc/styles.css";
import { Devs, EQUICORD_HELPERS, EquicordDevs, GUILD_ID } from "@utils/constants";
import { definePluginSettings, Settings } from "@api/Settings";
import { Devs, EquicordDevs } from "@utils/constants";
import { Logger } from "@utils/Logger";
import definePlugin from "@utils/types";
import { Button, ChannelStore, Flex, Forms, GuildMemberStore, showToast, Toasts } from "@webpack/common";
import { isEquicordGuild, isEquicordSupport } from "@utils/misc";
import definePlugin, { OptionType } from "@utils/types";
import { Button, Flex, showToast, Toasts } from "@webpack/common";
import { JSX } from "react";
import { toggleEnabled } from "./utils";
const settings = definePluginSettings({
disableCreateDMButton: {
type: OptionType.BOOLEAN,
description: "Disables the create dm button",
restartNeeded: true,
default: false,
},
disableDMContextMenu: {
type: OptionType.BOOLEAN,
description: "Disables the DM list context menu in favor of the x button",
restartNeeded: true,
default: false
}
});
export default definePlugin({
name: "EquicordHelper",
description: "Fixes some misc issues with discord",
description: "Used to provide support, fix discord caused crashes, and other misc features.",
authors: [Devs.thororen, EquicordDevs.nyx, EquicordDevs.Naibuu],
settingsAboutComponent: () => <>
<Forms.FormText className="plugin-warning" style={{ textAlign: "left" }}>
This plugin was created to allow us as the Equicord Team & Contributors
to fix miscellaneous issues Discord may run into or cause.
<br />
This includes but is not limited to:
<br />
- Unknown Resolution/FPS Fixed?
<br />
- Whitelists all domains in CSP
</Forms.FormText>
</>,
required: true,
settings,
patches: [
// Fixes Unknown Resolution/FPS Crashing
{
@ -58,47 +51,83 @@ export default definePlugin({
replace: "return $1;"
}
]
}
},
{
find: ".createDMButtonContainer,",
replacement: {
match: /"create-dm"\)/,
replace: "$&&&false"
},
predicate: () => settings.store.disableCreateDMButton
},
{
find: "#{intl::d+e27u::raw}",
replacement: {
match: /\{dotsInsteadOfCloseButton:(\i),rearrangeContextMenu:(\i).*?autoTrackExposure:!0\}\)/,
replace: "$1=false,$2=false"
},
predicate: () => settings.store.disableDMContextMenu
},
],
renderMessageAccessory(props) {
const buttons = [] as JSX.Element[];
const equicordSupport = GuildMemberStore.getMember(GUILD_ID, props.message.author.id)?.roles?.includes(EQUICORD_HELPERS);
const msg = props.message.content?.toLowerCase() ?? "";
const contentWords = (msg.match(/`\w+`/g) ?? []).map(e => e.slice(1, -1));
const matchedPlugins = Object.keys(Vencord.Plugins.plugins).filter(name => contentWords.includes(name.toLowerCase()));
const matchedPlugin = matchedPlugins.sort((a, b) => b.length - a.length)[0];
const pluginData = matchedPlugin && Vencord.Plugins.plugins[matchedPlugin];
const equicordGuild = ChannelStore.getChannel(props.channel.id)?.guild_id === GUILD_ID;
const ableCheck = msg.startsWith("enable") || msg.startsWith("disable");
const shouldAddPluginButtons = equicordGuild && equicordSupport && matchedPlugin && pluginData && ableCheck;
if (shouldAddPluginButtons) {
if (pluginData.required || pluginData.name.endsWith("API")) return;
const isEnabled = Vencord.Plugins.isPluginEnabled(matchedPlugin);
buttons.push(
<Button
key="vc-plugin-toggle"
color={isEnabled ? Button.Colors.RED : Button.Colors.GREEN}
onClick={async () => {
try {
const success = await toggleEnabled(matchedPlugin);
if (success) showToast(`${isEnabled ? "Disabled" : "Enabled"} ${matchedPlugin}`, Toasts.Type.SUCCESS);
} catch (e) {
new Logger(this.name).error("Error while toggling:", e);
showToast(`Failed to toggle ${matchedPlugin}`, Toasts.Type.FAILURE);
}
}}
>
{`${isEnabled ? "Disable" : "Enable"} ${matchedPlugin}`}
</Button>
);
start() {
if (Settings.plugins?.PinDMs?.disableCreateDMButton) {
settings.store.disableCreateDMButton = true;
}
return buttons.length
? <Flex>{buttons}</Flex>
: null;
},
renderMessageAccessory(props) {
return pluginToggleButtons(props);
}
});
function pluginToggleButtons(props) {
const buttons = [] as JSX.Element[];
const msg = props.message.content?.toLowerCase() ?? "";
const contentWords = (msg.match(/`\w+`/g) ?? []).map(e => e.slice(1, -1));
const matchedPlugins = Object.keys(Vencord.Plugins.plugins).filter(name => contentWords.includes(name.toLowerCase()));
const matchedPlugin = matchedPlugins.sort((a, b) => b.length - a.length)[0];
const pluginData = matchedPlugin ? Vencord.Plugins.plugins[matchedPlugin] : null;
const isEquicord = isEquicordGuild(props.channel.id) && isEquicordSupport(props.message.author.id);
const startsWithEnabled = msg.startsWith("enable");
const startsWithDisabled = msg.startsWith("disable");
const shouldAddPluginButtons = pluginData && isEquicord && (startsWithEnabled || startsWithDisabled);
if (shouldAddPluginButtons) {
if (pluginData.required || pluginData.name.endsWith("API")) return;
const isEnabled = Vencord.Plugins.isPluginEnabled(matchedPlugin);
let label = `${matchedPlugin} is already ${isEnabled ? "enabled" : "disabled"}`;
let disabled = true;
if ((startsWithDisabled && isEnabled) || (startsWithEnabled && !isEnabled)) {
label = `${isEnabled ? "Disable" : "Enable"} ${matchedPlugin}`;
disabled = false;
}
buttons.push(
<Button
key="vc-plugin-toggle"
color={disabled ? Button.Colors.PRIMARY : (isEnabled ? Button.Colors.RED : Button.Colors.GREEN)}
disabled={disabled}
size={Button.Sizes.SMALL}
onClick={async () => {
try {
const success = await toggleEnabled(matchedPlugin);
if (success) showToast(`${label}`, Toasts.Type.SUCCESS);
} catch (e) {
new Logger("EquicordHelper").error("Error while toggling:", e);
showToast(`Failed to ${label.toLowerCase()}`, Toasts.Type.FAILURE);
}
}}
>
{label}
</Button>
);
}
return buttons.length
? <Flex>{buttons}</Flex>
: null;
}

View file

@ -1,39 +1,40 @@
/*
* Vencord, a modification for Discord's desktop app
* Copyright (c) 2022 Vendicated and Megumin
*
* 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/>.
*/
* 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 { Devs, EquicordDevs } from "@utils/constants";
import definePlugin from "@utils/types";
import definePlugin, { OptionType } from "@utils/types";
let clickCount = 0;
function play() {
clickCount++;
if (clickCount % 10 === 0) {
const triggerAmount = settings.store.amount;
if (clickCount % triggerAmount === 0) {
const audio = new Audio("https://github.com/Equicord/Equibored/raw/main/sounds/equissant/croissant.mp3");
audio.play();
clickCount = 0;
}
}
const settings = definePluginSettings({
amount: {
type: OptionType.NUMBER,
description: "amount of clicks to trigger crossant",
default: 10,
}
});
export default definePlugin({
name: "Equissant",
description: "Crossant every 10 clicks :trolley:",
description: "Crossant every specified amount of clicks :trolley:",
authors: [EquicordDevs.SomeAspy, Devs.thororen],
settings,
start() {
document.addEventListener("click", play);
},

View file

@ -65,6 +65,19 @@ const settings = definePluginSettings({
description: "Jellyfin user ID obtained from your user profile URL",
type: OptionType.STRING,
},
nameDisplay: {
description: "Choose how the application name should appear in Rich Presence",
type: OptionType.SELECT,
options: [
{ label: "Series/Movie Name", value: "default", default: true },
{ label: "Series - Episode/Track/Movie Name", value: "full" },
{ label: "Custom", value: "custom" },
],
},
customName: {
description: "Custom Rich Presence name (only used if 'Custom' is selected).\nOptions: {name}, {series}, {season}, {episode}, {artist}, {album}, {year}",
type: OptionType.STRING,
},
overrideRichPresenceType: {
description: "Override the rich presence type",
type: OptionType.SELECT,
@ -113,16 +126,27 @@ function setActivity(activity: Activity | null) {
export default definePlugin({
name: "JellyfinRichPresence",
description: "Rich presence for Jellyfin media server",
authors: [EquicordDevs.vmohammad],
authors: [EquicordDevs.vmohammad, EquicordDevs.SerStars],
settingsAboutComponent: () => (
<>
<Forms.FormTitle tag="h3">How to get an API key</Forms.FormTitle>
<Forms.FormText>
An API key is required to fetch your current media. To get one, go to your
Jellyfin dashboard, navigate to Administration {">"} API Keys and
create a new API key. <br /> <br />
Auth token can be found by following these steps:
<ol style={{ marginTop: 8, marginBottom: 8, paddingLeft: 20 }}>
<li>1. Log into your Jellyfin instance</li>
<li>2. Open your browser's Developer Tools (usually F12 or right-click then Inspect)</li>
<li>3. Go to the <b>Network</b> tab in Developer Tools</li>
<li>4. Look for requests to your Jellyfin server</li>
<li>
5. In the request headers, find <code>X-MediaBrowser-Token</code> or <code>Authorization</code>
<br />
<i>
Easiest way: press <b>Ctrl+F</b> in the Developer Tools and search for <code>X-MediaBrowser-Token</code>
</i>
</li>
</ol>
<br />
You'll also need your User ID, which can be found in the url of your user profile page.
</Forms.FormText>
</>
@ -197,6 +221,8 @@ export default definePlugin({
async getActivity(): Promise<Activity | null> {
let richPresenceType;
let appName: string;
const nameSetting = settings.store.nameDisplay || "default";
const mediaData = await this.fetchMediaData();
if (!mediaData) return null;
@ -214,6 +240,40 @@ export default definePlugin({
}
}
const templateReplace = (template: string) => {
return template
.replace(/\{name\}/g, mediaData.name || "")
.replace(/\{series\}/g, mediaData.seriesName || "")
.replace(/\{season\}/g, mediaData.seasonNumber?.toString() || "")
.replace(/\{episode\}/g, mediaData.episodeNumber?.toString() || "")
.replace(/\{artist\}/g, mediaData.artist || "")
.replace(/\{album\}/g, mediaData.album || "")
.replace(/\{year\}/g, mediaData.year?.toString() || "");
};
switch (nameSetting) {
case "full":
if (mediaData.type === "Episode" && mediaData.seriesName) {
appName = `${mediaData.seriesName} - ${mediaData.name}`;
} else if (mediaData.type === "Audio") {
appName = `${mediaData.artist || "Unknown Artist"} - ${mediaData.name}`;
} else {
appName = mediaData.name || "Jellyfin";
}
break;
case "custom":
appName = templateReplace(settings.store.customName || "{name} on Jellyfish");
break;
case "default":
default:
if (mediaData.type === "Episode" && mediaData.seriesName) {
appName = mediaData.seriesName;
} else {
appName = mediaData.name || "Jellyfin";
}
break;
}
const largeImage = mediaData.imageUrl;
const assets: ActivityAssets = {
large_image: largeImage ? await getApplicationAsset(largeImage) : await getApplicationAsset("jellyfin"),
@ -243,8 +303,7 @@ export default definePlugin({
return {
application_id: applicationId,
name: "Jellyfin",
name: appName,
details: getDetails(),
state: getState() || "something",
assets,

View file

@ -0,0 +1,59 @@
/*
* Vencord, a Discord client mod
* Copyright (c) 2024 Vendicated and contributors
* SPDX-License-Identifier: GPL-3.0-or-later
*/
import { NavContextMenuPatchCallback } from "@api/ContextMenu";
import { migratePluginSettings } from "@api/Settings";
import { Devs } from "@utils/constants";
import definePlugin from "@utils/types";
import { Menu, NavigationRouter, RestAPI } from "@webpack/common";
function jumpToFirstMessage(props) {
const guildid = props.guild_id !== null ? props.guild_id : "@me";
const channelid = props.id;
const url = `/channels/${guildid}/${channelid}/0`;
NavigationRouter.transitionTo(url);
}
async function jumpToBottom(props) {
const guildid = props.guild_id ?? "@me";
const channelid = props.id;
const res = await RestAPI.get({
url: `/channels/${channelid}/messages?limit=1`
});
const lastMessageId = res.body?.[0]?.id;
if (!lastMessageId) return;
const url = `/channels/${guildid}/${channelid}/${lastMessageId}`;
NavigationRouter.transitionTo(url);
}
const MenuPatch: NavContextMenuPatchCallback = (children, { channel }) => {
children.push(
<Menu.MenuItem
id="vc-jump-to-first"
label="Jump To First Message"
action={() => jumpToFirstMessage(channel)}
/>,
<Menu.MenuItem
id="vc-jump-to-bottom"
label="Jump To Bottom"
action={() => jumpToBottom(channel)}
/>
);
};
migratePluginSettings("JumpTo", "JumpToStart", "AutoJump");
export default definePlugin({
name: "JumpTo",
description: "Adds context menu options to jump to the start or bottom of a channel/DM",
authors: [Devs.Samwich, Devs.thororen],
contextMenus: {
"channel-context": MenuPatch,
"user-context": MenuPatch,
"thread-context": MenuPatch
}
});

View file

@ -1,41 +0,0 @@
/*
* Vencord, a Discord client mod
* Copyright (c) 2024 Vendicated and contributors
* SPDX-License-Identifier: GPL-3.0-or-later
*/
import { NavContextMenuPatchCallback } from "@api/ContextMenu";
import { Devs } from "@utils/constants";
import definePlugin from "@utils/types";
import { Menu, NavigationRouter } from "@webpack/common";
function jumpToFirstMessage(props) {
const guildid = props.guild_id !== null ? props.guild_id : "@me";
const channelid = props.id;
const url = `/channels/${guildid}/${channelid}/0`;
NavigationRouter.transitionTo(url);
}
const MenuPatch: NavContextMenuPatchCallback = (children, { channel }) => {
children.push(
<Menu.MenuItem
id="vc-jump-to-first"
label="Jump To First Message"
action={() => {
jumpToFirstMessage(channel);
}}
/>
);
};
export default definePlugin({
name: "JumpToStart",
description: "Adds a context menu option to jump to the start of a channel/DM",
authors: [Devs.Samwich],
contextMenus:
{
"channel-context": MenuPatch,
"user-context": MenuPatch,
"thread-context": MenuPatch
}
});

View file

@ -22,11 +22,11 @@ import ErrorBoundary from "@components/ErrorBoundary";
import { Flex } from "@components/Flex";
import { Link } from "@components/Link";
import { openUpdaterModal } from "@components/settings/tabs/updater";
import { CONTRIB_ROLE_ID, Devs, DONOR_ROLE_ID, EQUIBOP_CONTRIB_ROLE_ID, EQUICORD_HELPERS, EQUICORD_TEAM, GUILD_ID, SUPPORT_CHANNEL_ID, SUPPORT_CHANNEL_IDS, VC_CONTRIB_ROLE_ID, VC_DONOR_ROLE_ID, VC_GUILD_ID, VC_REGULAR_ROLE_ID, VC_SUPPORT_CHANNEL_IDS, VENCORD_CONTRIB_ROLE_ID } from "@utils/constants";
import { CONTRIB_ROLE_ID, Devs, DONOR_ROLE_ID, EQUIBOP_CONTRIB_ROLE_ID, EQUICORD_TEAM, GUILD_ID, SUPPORT_CHANNEL_ID, SUPPORT_CHANNEL_IDS, VC_CONTRIB_ROLE_ID, VC_DONOR_ROLE_ID, VC_GUILD_ID, VC_REGULAR_ROLE_ID, VC_SUPPORT_CHANNEL_IDS, VENCORD_CONTRIB_ROLE_ID } from "@utils/constants";
import { sendMessage } from "@utils/discord";
import { Logger } from "@utils/Logger";
import { Margins } from "@utils/margins";
import { isEquicordPluginDev, isPluginDev, tryOrElse } from "@utils/misc";
import { isEquicordGuild, isEquicordPluginDev, isEquicordSupport, isPluginDev, isSupportChannel, tryOrElse } from "@utils/misc";
import { relaunch } from "@utils/native";
import { onlyOnce } from "@utils/onlyOnce";
import { makeCodeblock } from "@utils/text";
@ -183,7 +183,7 @@ function generatePluginList() {
</div>
});
return `${user.username} have more than 100 plugins enabled, please reduce the number of enabled plugins to get support.`;
return `${user.username} has more than 100 plugins enabled, please reduce the number of enabled plugins to get support.`;
}
return content;
@ -219,14 +219,14 @@ export default definePlugin({
name: "equicord-debug",
description: "Send Equicord debug info",
// @ts-ignore
predicate: ctx => isPluginDev(UserStore.getCurrentUser()?.id) || isEquicordPluginDev(UserStore.getCurrentUser()?.id) || GUILD_ID === ctx?.guild?.id,
predicate: ctx => isPluginDev(UserStore.getCurrentUser()?.id) || isEquicordPluginDev(UserStore.getCurrentUser()?.id) || isEquicordGuild(ctx?.guild?.id, true),
execute: async () => ({ content: await generateDebugInfoMessage() })
},
{
name: "equicord-plugins",
description: "Send Equicord plugin list",
// @ts-ignore
predicate: ctx => isPluginDev(UserStore.getCurrentUser()?.id) || isEquicordPluginDev(UserStore.getCurrentUser()?.id) || GUILD_ID === ctx?.guild?.id,
predicate: ctx => isPluginDev(UserStore.getCurrentUser()?.id) || isEquicordPluginDev(UserStore.getCurrentUser()?.id) || isEquicordGuild(ctx?.guild?.id, true),
execute: () => {
const pluginList = generatePluginList();
return { content: typeof pluginList === "string" ? pluginList : "Unable to generate plugin list." };
@ -328,11 +328,11 @@ export default definePlugin({
renderMessageAccessory(props) {
const buttons = [] as JSX.Element[];
const equicordSupport = GuildMemberStore.getMember(GUILD_ID, props.message.author.id)?.roles?.includes(EQUICORD_HELPERS);
const equicordSupport = isEquicordSupport(props.message.author.id);
const shouldAddUpdateButton =
!IS_UPDATER_DISABLED
&& ((props.channel.id === SUPPORT_CHANNEL_ID && equicordSupport))
&& ((isSupportChannel(props.channel.id) && equicordSupport))
&& props.message.content?.includes("update");
if (shouldAddUpdateButton) {
@ -357,7 +357,7 @@ export default definePlugin({
);
}
if (props.channel.id === SUPPORT_CHANNEL_ID && PermissionStore.can(PermissionsBits.SEND_MESSAGES, props.channel)) {
if (isSupportChannel(props.channel.id) && PermissionStore.can(PermissionsBits.SEND_MESSAGES, props.channel)) {
if (props.message.content.includes("/equicord-debug") || props.message.content.includes("/equicord-plugins")) {
buttons.push(
<Button

View file

@ -131,7 +131,7 @@ export default definePlugin({
},
{
match: /case \i\.\i\.DEVELOPER_OPTIONS:return \i;/,
replace: "$&case 'VencordPlugins':return $self.PluginsSubmenu();"
replace: "$&case 'EquicordPlugins':return $self.PluginsSubmenu();"
}
]
},

View file

@ -39,7 +39,7 @@ const settings = definePluginSettings({
},
alwaysPlaySound: {
type: OptionType.BOOLEAN,
description: "Play message sound even when message sound is disabled",
description: "Play the message notification sound even when its disabled",
restartNeeded: true,
default: false
}

View file

@ -62,11 +62,6 @@ export const settings = definePluginSettings({
default: {} as Record<string, Category[]>,
description: "",
},
disableCreateDMButton: {
type: OptionType.BOOLEAN,
description: "Disables the create dm button",
default: true
}
});
export default definePlugin({
@ -159,14 +154,6 @@ export default definePlugin({
replace: "$self.getAllUncollapsedChannels().concat($&.filter(c=>!$self.isPinned(c)))"
}
},
{
find: ".createDMButtonContainer,",
replacement: {
match: /"create-dm"\)/,
replace: "$&&&false"
},
predicate: () => settings.store.disableCreateDMButton
},
],
sections: null as number[] | null,

View file

@ -134,6 +134,7 @@ function getNextMessage(isUp: boolean, isReply: boolean) {
if (m.deleted) return false;
if (!isReply && m.author.id !== meId) return false; // editing only own messages
if (hasNoBlockedMessages && NoBlockedMessagesPlugin.isBlocked(m)) return false;
if (m.type === 6) return false;
return true;
});

View file

@ -16,10 +16,10 @@
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import { Toasts } from "@webpack/common";
import { ChannelStore, GuildMemberStore, Toasts } from "@webpack/common";
import { copyToClipboard } from "./clipboard";
import { EquicordDevsById, VencordDevsById } from "./constants";
import { EQUICORD_HELPERS, EquicordDevsById, GUILD_ID, SUPPORT_CHANNEL_ID, VencordDevsById } from "./constants";
/**
* Calls .join(" ") on the arguments
@ -116,3 +116,19 @@ export function tryOrElse<T>(func: () => T, fallback: T): T {
return fallback;
}
}
export function isEquicordGuild(id: string, isGuildId: boolean = false): boolean {
if (isGuildId) return id === GUILD_ID;
const channel = ChannelStore.getChannel(id);
return channel.guild_id === GUILD_ID;
}
export function isSupportChannel(channelId: string): boolean {
return channelId === SUPPORT_CHANNEL_ID;
}
export function isEquicordSupport(userId: string): boolean {
const member = GuildMemberStore.getMember(GUILD_ID, userId);
return member?.roles?.includes(EQUICORD_HELPERS) || false;
}