Compare commits
6 commits
06ceb4b82c
...
7907bf7120
Author | SHA1 | Date | |
---|---|---|---|
7907bf7120 | |||
4deb52028a | |||
f713398070 | |||
056a1b0e1e | |||
66492344a9 | |||
fb940489b0 |
36 changed files with 211 additions and 343 deletions
|
@ -1,7 +1,7 @@
|
||||||
{
|
{
|
||||||
"name": "vencord",
|
"name": "vencord",
|
||||||
"private": "true",
|
"private": "true",
|
||||||
"version": "1.10.7",
|
"version": "1.10.6",
|
||||||
"description": "The cutest Discord client mod",
|
"description": "The cutest Discord client mod",
|
||||||
"homepage": "https://github.com/Vendicated/Vencord#readme",
|
"homepage": "https://github.com/Vendicated/Vencord#readme",
|
||||||
"bugs": {
|
"bugs": {
|
||||||
|
|
|
@ -225,7 +225,7 @@ page.on("console", async e => {
|
||||||
plugin,
|
plugin,
|
||||||
type,
|
type,
|
||||||
id,
|
id,
|
||||||
match: regex.replace(/\(\?:\[A-Za-z_\$\]\[\\w\$\]\*\)/g, "\\i"),
|
match: regex.replace(/\[A-Za-z_\$\]\[\\w\$\]\*/g, "\\i"),
|
||||||
error: await maybeGetError(e.args()[3])
|
error: await maybeGetError(e.args()[3])
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
|
|
||||||
import "./iconStyles.css";
|
import "./iconStyles.css";
|
||||||
|
|
||||||
import { getIntlMessage } from "@utils/discord";
|
import { getIntlMessage, getTheme, Theme } from "@utils/discord";
|
||||||
import { classes } from "@utils/misc";
|
import { classes } from "@utils/misc";
|
||||||
import type { PropsWithChildren } from "react";
|
import type { PropsWithChildren } from "react";
|
||||||
|
|
||||||
|
@ -122,8 +122,8 @@ export function InfoIcon(props: IconProps) {
|
||||||
>
|
>
|
||||||
<path
|
<path
|
||||||
fill="currentColor"
|
fill="currentColor"
|
||||||
fill-rule="evenodd"
|
transform="translate(2 2)"
|
||||||
d="M23 12a11 11 0 1 1-22 0 11 11 0 0 1 22 0Zm-9.5-4.75a1.25 1.25 0 1 1-2.5 0 1.25 1.25 0 0 1 2.5 0Zm-.77 3.96a1 1 0 1 0-1.96-.42l-1.04 4.86a2.77 2.77 0 0 0 4.31 2.83l.24-.17a1 1 0 1 0-1.16-1.62l-.24.17a.77.77 0 0 1-1.2-.79l1.05-4.86Z" clip-rule="evenodd"
|
d="M9,7 L11,7 L11,5 L9,5 L9,7 Z M10,18 C5.59,18 2,14.41 2,10 C2,5.59 5.59,2 10,2 C14.41,2 18,5.59 18,10 C18,14.41 14.41,18 10,18 L10,18 Z M10,4.4408921e-16 C4.4771525,-1.77635684e-15 4.4408921e-16,4.4771525 0,10 C-1.33226763e-15,12.6521649 1.0535684,15.195704 2.92893219,17.0710678 C4.80429597,18.9464316 7.3478351,20 10,20 C12.6521649,20 15.195704,18.9464316 17.0710678,17.0710678 C18.9464316,15.195704 20,12.6521649 20,10 C20,7.3478351 18.9464316,4.80429597 17.0710678,2.92893219 C15.195704,1.0535684 12.6521649,2.22044605e-16 10,0 L10,4.4408921e-16 Z M9,15 L11,15 L11,9 L9,9 L9,15 L9,15 Z"
|
||||||
/>
|
/>
|
||||||
</Icon>
|
</Icon>
|
||||||
);
|
);
|
||||||
|
@ -211,10 +211,9 @@ export function CogWheel(props: IconProps) {
|
||||||
viewBox="0 0 24 24"
|
viewBox="0 0 24 24"
|
||||||
>
|
>
|
||||||
<path
|
<path
|
||||||
|
clipRule="evenodd"
|
||||||
fill="currentColor"
|
fill="currentColor"
|
||||||
fill-rule="evenodd"
|
d="M19.738 10H22V14H19.739C19.498 14.931 19.1 15.798 18.565 16.564L20 18L18 20L16.565 18.564C15.797 19.099 14.932 19.498 14 19.738V22H10V19.738C9.069 19.498 8.203 19.099 7.436 18.564L6 20L4 18L5.436 16.564C4.901 15.799 4.502 14.932 4.262 14H2V10H4.262C4.502 9.068 4.9 8.202 5.436 7.436L4 6L6 4L7.436 5.436C8.202 4.9 9.068 4.502 10 4.262V2H14V4.261C14.932 4.502 15.797 4.9 16.565 5.435L18 3.999L20 5.999L18.564 7.436C19.099 8.202 19.498 9.069 19.738 10ZM12 16C14.2091 16 16 14.2091 16 12C16 9.79086 14.2091 8 12 8C9.79086 8 8 9.79086 8 12C8 14.2091 9.79086 16 12 16Z"
|
||||||
d="M10.56 1.1c-.46.05-.7.53-.64.98.18 1.16-.19 2.2-.98 2.53-.8.33-1.79-.15-2.49-1.1-.27-.36-.78-.52-1.14-.24-.77.59-1.45 1.27-2.04 2.04-.28.36-.12.87.24 1.14.96.7 1.43 1.7 1.1 2.49-.33.8-1.37 1.16-2.53.98-.45-.07-.93.18-.99.64a11.1 11.1 0 0 0 0 2.88c.06.46.54.7.99.64 1.16-.18 2.2.19 2.53.98.33.8-.14 1.79-1.1 2.49-.36.27-.52.78-.24 1.14.59.77 1.27 1.45 2.04 2.04.36.28.87.12 1.14-.24.7-.95 1.7-1.43 2.49-1.1.8.33 1.16 1.37.98 2.53-.07.45.18.93.64.99a11.1 11.1 0 0 0 2.88 0c.46-.06.7-.54.64-.99-.18-1.16.19-2.2.98-2.53.8-.33 1.79.14 2.49 1.1.27.36.78.52 1.14.24.77-.59 1.45-1.27 2.04-2.04.28-.36.12-.87-.24-1.14-.96-.7-1.43-1.7-1.1-2.49.33-.8 1.37-1.16 2.53-.98.45.07.93-.18.99-.64a11.1 11.1 0 0 0 0-2.88c-.06-.46-.54-.7-.99-.64-1.16.18-2.2-.19-2.53-.98-.33-.8.14-1.79 1.1-2.49.36-.27.52-.78.24-1.14a11.07 11.07 0 0 0-2.04-2.04c-.36-.28-.87-.12-1.14.24-.7.96-1.7 1.43-2.49 1.1-.8-.33-1.16-1.37-.98-2.53.07-.45-.18-.93-.64-.99a11.1 11.1 0 0 0-2.88 0ZM16 12a4 4 0 1 1-8 0 4 4 0 0 1 8 0Z"
|
|
||||||
clip-rule="evenodd"
|
|
||||||
/>
|
/>
|
||||||
</Icon>
|
</Icon>
|
||||||
);
|
);
|
||||||
|
@ -407,30 +406,23 @@ export function PencilIcon(props: IconProps) {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function GithubIcon(props: IconProps) {
|
const WebsiteIconDark = "/assets/e1e96d89e192de1997f73730db26e94f.svg";
|
||||||
return (
|
const WebsiteIconLight = "/assets/730f58bcfd5a57a5e22460c445a0c6cf.svg";
|
||||||
<Icon
|
const GithubIconLight = "/assets/3ff98ad75ac94fa883af5ed62d17c459.svg";
|
||||||
{...props}
|
const GithubIconDark = "/assets/6a853b4c87fce386cbfef4a2efbacb09.svg";
|
||||||
viewBox="-3 -3 30 30"
|
|
||||||
>
|
export function GithubIcon(props: ImageProps) {
|
||||||
<path
|
const src = getTheme() === Theme.Light
|
||||||
fill={props.fill || "currentColor"}
|
? GithubIconLight
|
||||||
d="M12 0C5.37 0 0 5.37 0 12c0 5.3 3.438 9.8 8.205 11.385.6.11.82-.26.82-.577v-2.17c-3.338.726-4.042-1.61-4.042-1.61-.546-1.387-1.333-1.757-1.333-1.757-1.09-.745.083-.73.083-.73 1.205.084 1.84 1.237 1.84 1.237 1.07 1.835 2.807 1.305 3.492.998.108-.775.42-1.305.763-1.605-2.665-.3-5.466-1.332-5.466-5.93 0-1.31.467-2.38 1.235-3.22-.123-.303-.535-1.523.117-3.176 0 0 1.008-.322 3.3 1.23.957-.266 1.98-.398 3-.403 1.02.005 2.043.137 3 .403 2.29-1.552 3.297-1.23 3.297-1.23.653 1.653.24 2.873.118 3.176.77.84 1.233 1.91 1.233 3.22 0 4.61-2.803 5.625-5.475 5.92.43.37.823 1.102.823 2.222v3.293c0 .32.218.694.825.577C20.565 21.797 24 17.298 24 12c0-6.63-5.37-12-12-12z"
|
: GithubIconDark;
|
||||||
/>
|
|
||||||
</Icon>
|
return <img {...props} src={src} />;
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export function WebsiteIcon(props: IconProps) {
|
export function WebsiteIcon(props: ImageProps) {
|
||||||
return (
|
const src = getTheme() === Theme.Light
|
||||||
<Icon
|
? WebsiteIconLight
|
||||||
{...props}
|
: WebsiteIconDark;
|
||||||
viewBox="0 0 24 24"
|
|
||||||
>
|
return <img {...props} src={src} />;
|
||||||
<path
|
|
||||||
fill={props.fill || "currentColor"}
|
|
||||||
d="M12 2C6.486 2 2 6.486 2 12s4.486 10 10 10 10-4.486 10-10S17.514 2 12 2zM4 12c0-.899.156-1.762.431-2.569L6 11l2 2v2l2 2 1 1v1.931C7.061 19.436 4 16.072 4 12zm14.33 4.873C17.677 16.347 16.687 16 16 16v-1a2 2 0 0 0-2-2h-4v-3a2 2 0 0 0 2-2V7h1a2 2 0 0 0 2-2v-.411C17.928 5.778 20 8.65 20 12a7.947 7.947 0 0 1-1.67 4.873z"
|
|
||||||
/>
|
|
||||||
</Icon>
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -6,19 +6,16 @@
|
||||||
|
|
||||||
import "./LinkIconButton.css";
|
import "./LinkIconButton.css";
|
||||||
|
|
||||||
import { getTheme, Theme } from "@utils/discord";
|
|
||||||
import { MaskedLink, Tooltip } from "@webpack/common";
|
import { MaskedLink, Tooltip } from "@webpack/common";
|
||||||
|
|
||||||
import { GithubIcon, WebsiteIcon } from "..";
|
import { GithubIcon, WebsiteIcon } from "..";
|
||||||
|
|
||||||
export function GithubLinkIcon() {
|
export function GithubLinkIcon() {
|
||||||
const theme = getTheme() === Theme.Light ? "#000000" : "#FFFFFF";
|
return <GithubIcon aria-hidden className={"vc-settings-modal-link-icon"} />;
|
||||||
return <GithubIcon aria-hidden fill={theme} className={"vc-settings-modal-link-icon"} />;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export function WebsiteLinkIcon() {
|
export function WebsiteLinkIcon() {
|
||||||
const theme = getTheme() === Theme.Light ? "#000000" : "#FFFFFF";
|
return <WebsiteIcon aria-hidden className={"vc-settings-modal-link-icon"} />;
|
||||||
return <WebsiteIcon aria-hidden fill={theme} className={"vc-settings-modal-link-icon"} />;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Props {
|
interface Props {
|
||||||
|
|
|
@ -247,7 +247,7 @@ function FullPatchInput({ setFind, setParsedFind, setMatch, setReplacement }: Fu
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const parsed = (0, eval)(`([${fullPatch}][0])`) as Patch;
|
const parsed = (0, eval)(`(${fullPatch})`) as Patch;
|
||||||
|
|
||||||
if (!parsed.find) throw new Error("No 'find' field");
|
if (!parsed.find) throw new Error("No 'find' field");
|
||||||
if (!parsed.replacement) throw new Error("No 'replacement' field");
|
if (!parsed.replacement) throw new Error("No 'replacement' field");
|
||||||
|
|
|
@ -27,12 +27,7 @@ export async function loadLazyChunks() {
|
||||||
|
|
||||||
const LazyChunkRegex = canonicalizeMatch(/(?:(?:Promise\.all\(\[)?(\i\.e\("?[^)]+?"?\)[^\]]*?)(?:\]\))?)\.then\(\i\.bind\(\i,"?([^)]+?)"?\)\)/g);
|
const LazyChunkRegex = canonicalizeMatch(/(?:(?:Promise\.all\(\[)?(\i\.e\("?[^)]+?"?\)[^\]]*?)(?:\]\))?)\.then\(\i\.bind\(\i,"?([^)]+?)"?\)\)/g);
|
||||||
|
|
||||||
let foundCssDebuggingLoad = false;
|
|
||||||
|
|
||||||
async function searchAndLoadLazyChunks(factoryCode: string) {
|
async function searchAndLoadLazyChunks(factoryCode: string) {
|
||||||
// Workaround to avoid loading the CSS debugging chunk which turns the app pink
|
|
||||||
const hasCssDebuggingLoad = foundCssDebuggingLoad ? false : (foundCssDebuggingLoad = factoryCode.includes(".cssDebuggingEnabled&&"));
|
|
||||||
|
|
||||||
const lazyChunks = factoryCode.matchAll(LazyChunkRegex);
|
const lazyChunks = factoryCode.matchAll(LazyChunkRegex);
|
||||||
const validChunkGroups = new Set<[chunkIds: number[], entryPoint: number]>();
|
const validChunkGroups = new Set<[chunkIds: number[], entryPoint: number]>();
|
||||||
|
|
||||||
|
@ -48,16 +43,6 @@ export async function loadLazyChunks() {
|
||||||
let invalidChunkGroup = false;
|
let invalidChunkGroup = false;
|
||||||
|
|
||||||
for (const id of chunkIds) {
|
for (const id of chunkIds) {
|
||||||
if (hasCssDebuggingLoad) {
|
|
||||||
if (chunkIds.length > 1) {
|
|
||||||
throw new Error("Found multiple chunks in factory that loads the CSS debugging chunk");
|
|
||||||
}
|
|
||||||
|
|
||||||
invalidChunks.add(id);
|
|
||||||
invalidChunkGroup = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (wreq.u(id) == null || wreq.u(id) === "undefined.js") continue;
|
if (wreq.u(id) == null || wreq.u(id) === "undefined.js") continue;
|
||||||
|
|
||||||
const isWorkerAsset = await fetch(wreq.p + wreq.u(id))
|
const isWorkerAsset = await fetch(wreq.p + wreq.u(id))
|
||||||
|
|
|
@ -59,7 +59,15 @@ export default definePlugin({
|
||||||
replace: "$&return;"
|
replace: "$&return;"
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
},
|
||||||
|
{
|
||||||
|
find: ".installedLogHooks)",
|
||||||
|
replacement: {
|
||||||
|
// if getDebugLogging() returns false, the hooks don't get installed.
|
||||||
|
match: "getDebugLogging(){",
|
||||||
|
replace: "getDebugLogging(){return false;"
|
||||||
|
}
|
||||||
|
},
|
||||||
],
|
],
|
||||||
|
|
||||||
startAt: StartAt.Init,
|
startAt: StartAt.Init,
|
||||||
|
|
|
@ -65,7 +65,7 @@ export default definePlugin({
|
||||||
replace: (_, sectionTypes, commaOrSemi, elements, element) => `${commaOrSemi} $self.addSettings(${elements}, ${element}, ${sectionTypes}) ${commaOrSemi}`
|
replace: (_, sectionTypes, commaOrSemi, elements, element) => `${commaOrSemi} $self.addSettings(${elements}, ${element}, ${sectionTypes}) ${commaOrSemi}`
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
match: /({(?=.+?function (\i).{0,160}(\i)=\i\.useMemo.{0,140}return \i\.useMemo\(\(\)=>\i\(\3).+?function\(\){return )\2(?=})/,
|
match: /({(?=.+?function (\i).{0,120}(\i)=\i\.useMemo.{0,60}return \i\.useMemo\(\(\)=>\i\(\3).+?function\(\){return )\2(?=})/,
|
||||||
replace: (_, rest, settingsHook) => `${rest}$self.wrapSettingsHook(${settingsHook})`
|
replace: (_, rest, settingsHook) => `${rest}$self.wrapSettingsHook(${settingsHook})`
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
|
@ -28,18 +28,10 @@ export default definePlugin({
|
||||||
patches: [
|
patches: [
|
||||||
{
|
{
|
||||||
find: 'action:"EXPAND_ROLES"',
|
find: 'action:"EXPAND_ROLES"',
|
||||||
replacement: [
|
replacement: {
|
||||||
{
|
match: /(roles:\i(?=.+?(\i)\(!0\)[,;]\i\({action:"EXPAND_ROLES"}\)).+?\[\i,\2\]=\i\.useState\()!1\)/,
|
||||||
match: /(roles:\i(?=.+?(\i)\(!0\)[,;]\i\({action:"EXPAND_ROLES"}\)).+?\[\i,\2\]=\i\.useState\()!1\)/,
|
replace: (_, rest, setExpandedRoles) => `${rest}!0)`
|
||||||
replace: (_, rest, setExpandedRoles) => `${rest}!0)`
|
}
|
||||||
},
|
|
||||||
{
|
|
||||||
// Fix not calculating non-expanded roles because the above patch makes the default "expanded",
|
|
||||||
// which makes the collapse button never show up and calculation never occur
|
|
||||||
match: /(?<=useLayoutEffect\(\(\)=>{if\()\i/,
|
|
||||||
replace: isExpanded => "false"
|
|
||||||
}
|
|
||||||
]
|
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
});
|
});
|
||||||
|
|
|
@ -275,16 +275,16 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
|
|
||||||
makeGuildsBarGuildListFilter(isBetterFolders: boolean) {
|
makeGuildsBarGuildListFilter(isBetterFolders: boolean) {
|
||||||
|
try {
|
||||||
return child => {
|
return child => {
|
||||||
if (isBetterFolders) {
|
if (isBetterFolders) {
|
||||||
try {
|
return child?.props?.["aria-label"] === getIntlMessage("SERVERS");
|
||||||
return child?.props?.["aria-label"] === getIntlMessage("SERVERS");
|
|
||||||
} catch (e) {
|
|
||||||
console.error(e);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
};
|
};
|
||||||
|
} catch {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
makeGuildsBarTreeFilter(isBetterFolders: boolean) {
|
makeGuildsBarTreeFilter(isBetterFolders: boolean) {
|
||||||
|
|
|
@ -110,7 +110,7 @@ const settings = definePluginSettings({
|
||||||
|
|
||||||
export default definePlugin({
|
export default definePlugin({
|
||||||
name: "ClientTheme",
|
name: "ClientTheme",
|
||||||
authors: [Devs.Nuckyz],
|
authors: [Devs.F53, Devs.Nuckyz],
|
||||||
description: "Recreation of the old client theme experiment. Add a color to your Discord client theme",
|
description: "Recreation of the old client theme experiment. Add a color to your Discord client theme",
|
||||||
settings,
|
settings,
|
||||||
|
|
||||||
|
|
|
@ -147,5 +147,5 @@ export default definePlugin({
|
||||||
replace: "$self.NoopLogger()"
|
replace: "$self.NoopLogger()"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
],
|
||||||
});
|
});
|
||||||
|
|
|
@ -93,7 +93,7 @@ export const useAuthorizationStore = proxyLazy(() => zustandCreate(
|
||||||
} as AuthorizationState),
|
} as AuthorizationState),
|
||||||
{
|
{
|
||||||
name: "decor-auth",
|
name: "decor-auth",
|
||||||
storage: indexedDBStorage,
|
getStorage: () => indexedDBStorage,
|
||||||
partialize: state => ({ tokens: state.tokens }),
|
partialize: state => ({ tokens: state.tokens }),
|
||||||
onRehydrateStorage: () => state => state?.init()
|
onRehydrateStorage: () => state => state?.init()
|
||||||
}
|
}
|
||||||
|
|
|
@ -95,39 +95,24 @@ export const useUsersDecorationsStore = proxyLazy(() => zustandCreate((set: any,
|
||||||
} as UsersDecorationsState)));
|
} as UsersDecorationsState)));
|
||||||
|
|
||||||
export function useUserDecorAvatarDecoration(user?: User): AvatarDecoration | null | undefined {
|
export function useUserDecorAvatarDecoration(user?: User): AvatarDecoration | null | undefined {
|
||||||
try {
|
const [decorAvatarDecoration, setDecorAvatarDecoration] = useState<string | null>(user ? useUsersDecorationsStore.getState().getAsset(user.id) ?? null : null);
|
||||||
const [decorAvatarDecoration, setDecorAvatarDecoration] = useState<string | null>(user ? useUsersDecorationsStore.getState().getAsset(user.id) ?? null : null);
|
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
const destructor = (() => {
|
const destructor = useUsersDecorationsStore.subscribe(
|
||||||
try {
|
state => {
|
||||||
return useUsersDecorationsStore.subscribe(
|
if (!user) return;
|
||||||
state => {
|
const newDecorAvatarDecoration = state.getAsset(user.id);
|
||||||
if (!user) return;
|
if (!newDecorAvatarDecoration) return;
|
||||||
const newDecorAvatarDecoration = state.getAsset(user.id);
|
if (decorAvatarDecoration !== newDecorAvatarDecoration) setDecorAvatarDecoration(newDecorAvatarDecoration);
|
||||||
if (!newDecorAvatarDecoration) return;
|
}
|
||||||
if (decorAvatarDecoration !== newDecorAvatarDecoration) setDecorAvatarDecoration(newDecorAvatarDecoration);
|
);
|
||||||
}
|
|
||||||
);
|
|
||||||
} catch {
|
|
||||||
return () => { };
|
|
||||||
}
|
|
||||||
})();
|
|
||||||
|
|
||||||
try {
|
if (user) {
|
||||||
if (user) {
|
const { fetch: fetchUserDecorAvatarDecoration } = useUsersDecorationsStore.getState();
|
||||||
const { fetch: fetchUserDecorAvatarDecoration } = useUsersDecorationsStore.getState();
|
fetchUserDecorAvatarDecoration(user.id);
|
||||||
fetchUserDecorAvatarDecoration(user.id);
|
}
|
||||||
}
|
return destructor;
|
||||||
} catch { }
|
}, []);
|
||||||
|
|
||||||
return destructor;
|
return decorAvatarDecoration ? { asset: decorAvatarDecoration, skuId: SKU_ID } : null;
|
||||||
}, []);
|
|
||||||
|
|
||||||
return decorAvatarDecoration ? { asset: decorAvatarDecoration, skuId: SKU_ID } : null;
|
|
||||||
} catch (e) {
|
|
||||||
console.error(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -10,7 +10,6 @@ import { openInviteModal } from "@utils/discord";
|
||||||
import { Margins } from "@utils/margins";
|
import { Margins } from "@utils/margins";
|
||||||
import { classes, copyWithToast } from "@utils/misc";
|
import { classes, copyWithToast } from "@utils/misc";
|
||||||
import { closeAllModals, ModalCloseButton, ModalContent, ModalFooter, ModalHeader, ModalProps, ModalRoot, ModalSize, openModal } from "@utils/modal";
|
import { closeAllModals, ModalCloseButton, ModalContent, ModalFooter, ModalHeader, ModalProps, ModalRoot, ModalSize, openModal } from "@utils/modal";
|
||||||
import { Queue } from "@utils/Queue";
|
|
||||||
import { findComponentByCodeLazy } from "@webpack";
|
import { findComponentByCodeLazy } from "@webpack";
|
||||||
import { Alerts, Button, FluxDispatcher, Forms, GuildStore, NavigationRouter, Parser, Text, Tooltip, useEffect, UserStore, UserUtils, useState } from "@webpack/common";
|
import { Alerts, Button, FluxDispatcher, Forms, GuildStore, NavigationRouter, Parser, Text, Tooltip, useEffect, UserStore, UserUtils, useState } from "@webpack/common";
|
||||||
import { User } from "discord-types/general";
|
import { User } from "discord-types/general";
|
||||||
|
@ -50,8 +49,6 @@ interface SectionHeaderProps {
|
||||||
section: Section;
|
section: Section;
|
||||||
}
|
}
|
||||||
|
|
||||||
const fetchAuthorsQueue = new Queue();
|
|
||||||
|
|
||||||
function SectionHeader({ section }: SectionHeaderProps) {
|
function SectionHeader({ section }: SectionHeaderProps) {
|
||||||
const hasSubtitle = typeof section.subtitle !== "undefined";
|
const hasSubtitle = typeof section.subtitle !== "undefined";
|
||||||
const hasAuthorIds = typeof section.authorIds !== "undefined";
|
const hasAuthorIds = typeof section.authorIds !== "undefined";
|
||||||
|
@ -59,18 +56,17 @@ function SectionHeader({ section }: SectionHeaderProps) {
|
||||||
const [authors, setAuthors] = useState<User[]>([]);
|
const [authors, setAuthors] = useState<User[]>([]);
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
fetchAuthorsQueue.push(async () => {
|
(async () => {
|
||||||
if (!section.authorIds) return;
|
if (!section.authorIds) return;
|
||||||
|
|
||||||
for (const authorId of section.authorIds) {
|
for (const authorId of section.authorIds) {
|
||||||
const author = UserStore.getUser(authorId) ?? await UserUtils.getUser(authorId).catch(() => null);
|
const author = UserStore.getUser(authorId) ?? await UserUtils.getUser(authorId);
|
||||||
if (author == null) continue;
|
|
||||||
|
|
||||||
setAuthors(authors => [...authors, author]);
|
setAuthors(authors => [...authors, author]);
|
||||||
}
|
}
|
||||||
});
|
})();
|
||||||
}, [section.authorIds]);
|
}, [section.authorIds]);
|
||||||
|
|
||||||
|
|
||||||
return <div>
|
return <div>
|
||||||
<Flex>
|
<Flex>
|
||||||
<Forms.FormTitle style={{ flexGrow: 1 }}>{section.title}</Forms.FormTitle>
|
<Forms.FormTitle style={{ flexGrow: 1 }}>{section.title}</Forms.FormTitle>
|
||||||
|
|
|
@ -20,7 +20,7 @@ import { AvatarDecorationModalPreview } from "../components";
|
||||||
const FileUpload = findComponentByCodeLazy("fileUploadInput,");
|
const FileUpload = findComponentByCodeLazy("fileUploadInput,");
|
||||||
|
|
||||||
const { HelpMessage, HelpMessageTypes } = mapMangledModuleLazy('POSITIVE=3]="POSITIVE', {
|
const { HelpMessage, HelpMessageTypes } = mapMangledModuleLazy('POSITIVE=3]="POSITIVE', {
|
||||||
HelpMessageTypes: filters.byProps("POSITIVE", "WARNING", "INFO"),
|
HelpMessageTypes: filters.byProps("POSITIVE", "WARNING"),
|
||||||
HelpMessage: filters.byCode(".iconDiv")
|
HelpMessage: filters.byCode(".iconDiv")
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@ -119,8 +119,8 @@ function CreateDecorationModal(props: ModalProps) {
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<HelpMessage messageType={HelpMessageTypes.INFO} className={Margins.bottom8}>
|
<Forms.FormText type="description" className={Margins.bottom16}>
|
||||||
To receive updates on your decoration's review, join <Link
|
<br />You can receive updates on your decoration's review by joining <Link
|
||||||
href={`https://discord.gg/${INVITE_KEY}`}
|
href={`https://discord.gg/${INVITE_KEY}`}
|
||||||
onClick={async e => {
|
onClick={async e => {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
|
@ -138,8 +138,8 @@ function CreateDecorationModal(props: ModalProps) {
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
Decor's Discord server
|
Decor's Discord server
|
||||||
</Link> and allow direct messages.
|
</Link>.
|
||||||
</HelpMessage>
|
</Forms.FormText>
|
||||||
</ErrorBoundary>
|
</ErrorBoundary>
|
||||||
</ModalContent>
|
</ModalContent>
|
||||||
<ModalFooter className={cl("modal-footer")}>
|
<ModalFooter className={cl("modal-footer")}>
|
||||||
|
|
|
@ -310,8 +310,7 @@ function buildMenuItem(type: "Emoji" | "Sticker", fetchData: () => Promisable<Om
|
||||||
}
|
}
|
||||||
|
|
||||||
function isGifUrl(url: string) {
|
function isGifUrl(url: string) {
|
||||||
const u = new URL(url);
|
return new URL(url).pathname.endsWith(".gif");
|
||||||
return u.pathname.endsWith(".gif") || u.searchParams.get("animated") === "true";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const messageContextMenuPatch: NavContextMenuPatchCallback = (children, props) => {
|
const messageContextMenuPatch: NavContextMenuPatchCallback = (children, props) => {
|
||||||
|
|
|
@ -20,11 +20,11 @@ import { addPreEditListener, addPreSendListener, removePreEditListener, removePr
|
||||||
import { definePluginSettings } from "@api/Settings";
|
import { definePluginSettings } from "@api/Settings";
|
||||||
import { Devs } from "@utils/constants";
|
import { Devs } from "@utils/constants";
|
||||||
import { ApngBlendOp, ApngDisposeOp, importApngJs } from "@utils/dependencies";
|
import { ApngBlendOp, ApngDisposeOp, importApngJs } from "@utils/dependencies";
|
||||||
import { getCurrentGuild, getEmojiURL } from "@utils/discord";
|
import { getCurrentGuild } from "@utils/discord";
|
||||||
import { Logger } from "@utils/Logger";
|
import { Logger } from "@utils/Logger";
|
||||||
import definePlugin, { OptionType, Patch } from "@utils/types";
|
import definePlugin, { OptionType, Patch } from "@utils/types";
|
||||||
import { findByCodeLazy, findByPropsLazy, findStoreLazy, proxyLazyWebpack } from "@webpack";
|
import { findByCodeLazy, findByPropsLazy, findStoreLazy, proxyLazyWebpack } from "@webpack";
|
||||||
import { Alerts, ChannelStore, DraftType, EmojiStore, FluxDispatcher, Forms, GuildMemberStore, lodash, Parser, PermissionsBits, PermissionStore, UploadHandler, UserSettingsActionCreators, UserStore } from "@webpack/common";
|
import { Alerts, ChannelStore, DraftType, EmojiStore, FluxDispatcher, Forms, GuildMemberStore, IconUtils, lodash, Parser, PermissionsBits, PermissionStore, UploadHandler, UserSettingsActionCreators, UserStore } from "@webpack/common";
|
||||||
import type { Emoji } from "@webpack/types";
|
import type { Emoji } from "@webpack/types";
|
||||||
import type { Message } from "discord-types/general";
|
import type { Message } from "discord-types/general";
|
||||||
import { applyPalette, GIFEncoder, quantize } from "gifenc";
|
import { applyPalette, GIFEncoder, quantize } from "gifenc";
|
||||||
|
@ -920,7 +920,7 @@ export default definePlugin({
|
||||||
|
|
||||||
const emojiString = `<${emoji.animated ? "a" : ""}:${emoji.originalName || emoji.name}:${emoji.id}>`;
|
const emojiString = `<${emoji.animated ? "a" : ""}:${emoji.originalName || emoji.name}:${emoji.id}>`;
|
||||||
|
|
||||||
const url = new URL(getEmojiURL(emoji.id, emoji.animated, s.emojiSize));
|
const url = new URL(IconUtils.getEmojiURL({ id: emoji.id, animated: emoji.animated, size: s.emojiSize }));
|
||||||
url.searchParams.set("size", s.emojiSize.toString());
|
url.searchParams.set("size", s.emojiSize.toString());
|
||||||
url.searchParams.set("name", emoji.name);
|
url.searchParams.set("name", emoji.name);
|
||||||
|
|
||||||
|
@ -953,7 +953,7 @@ export default definePlugin({
|
||||||
|
|
||||||
hasBypass = true;
|
hasBypass = true;
|
||||||
|
|
||||||
const url = new URL(getEmojiURL(emoji.id, emoji.animated, s.emojiSize));
|
const url = new URL(IconUtils.getEmojiURL({ id: emoji.id, animated: emoji.animated, size: s.emojiSize }));
|
||||||
url.searchParams.set("size", s.emojiSize.toString());
|
url.searchParams.set("size", s.emojiSize.toString());
|
||||||
url.searchParams.set("name", emoji.name);
|
url.searchParams.set("name", emoji.name);
|
||||||
|
|
||||||
|
|
|
@ -28,7 +28,7 @@ import { getIntlMessage } from "@utils/discord";
|
||||||
import { Logger } from "@utils/Logger";
|
import { Logger } from "@utils/Logger";
|
||||||
import { classes } from "@utils/misc";
|
import { classes } from "@utils/misc";
|
||||||
import definePlugin, { OptionType } from "@utils/types";
|
import definePlugin, { OptionType } from "@utils/types";
|
||||||
import { findByPropsLazy } from "@webpack";
|
import { findByCodeLazy, findByPropsLazy } from "@webpack";
|
||||||
import { ChannelStore, FluxDispatcher, Menu, MessageStore, Parser, SelectedChannelStore, Timestamp, UserStore, useStateFromStores } from "@webpack/common";
|
import { ChannelStore, FluxDispatcher, Menu, MessageStore, Parser, SelectedChannelStore, Timestamp, UserStore, useStateFromStores } from "@webpack/common";
|
||||||
import { Message } from "discord-types/general";
|
import { Message } from "discord-types/general";
|
||||||
|
|
||||||
|
@ -43,6 +43,7 @@ interface MLMessage extends Message {
|
||||||
}
|
}
|
||||||
|
|
||||||
const styles = findByPropsLazy("edited", "communicationDisabled", "isSystemMessage");
|
const styles = findByPropsLazy("edited", "communicationDisabled", "isSystemMessage");
|
||||||
|
const getMessage = findByCodeLazy('replace(/^\\n+|\\n+$/g,"")');
|
||||||
|
|
||||||
function addDeleteStyle() {
|
function addDeleteStyle() {
|
||||||
if (Settings.plugins.MessageLogger.deleteStyle === "text") {
|
if (Settings.plugins.MessageLogger.deleteStyle === "text") {
|
||||||
|
@ -311,33 +312,35 @@ export default definePlugin({
|
||||||
);
|
);
|
||||||
},
|
},
|
||||||
|
|
||||||
// DELETED_MESSAGE_COUNT: getMessage("{count, plural, =0 {No deleted messages} one {{count} deleted message} other {{count} deleted messages}}")
|
Messages: {
|
||||||
// TODO: Find a better way to generate intl messages
|
// DELETED_MESSAGE_COUNT: getMessage("{count, plural, =0 {No deleted messages} one {{count} deleted message} other {{count} deleted messages}}")
|
||||||
DELETED_MESSAGE_COUNT: () => ({
|
// TODO: find a better way to generate intl messages
|
||||||
ast: [[
|
DELETED_MESSAGE_COUNT: () => ({
|
||||||
6,
|
ast: [[
|
||||||
"count",
|
6,
|
||||||
{
|
"count",
|
||||||
"=0": ["No deleted messages"],
|
{
|
||||||
one: [
|
"=0": ["No deleted messages"],
|
||||||
[
|
one: [
|
||||||
1,
|
[
|
||||||
"count"
|
1,
|
||||||
|
"count"
|
||||||
|
],
|
||||||
|
" deleted message"
|
||||||
],
|
],
|
||||||
" deleted message"
|
other: [
|
||||||
],
|
[
|
||||||
other: [
|
1,
|
||||||
[
|
"count"
|
||||||
1,
|
],
|
||||||
"count"
|
" deleted messages"
|
||||||
],
|
]
|
||||||
" deleted messages"
|
},
|
||||||
]
|
0,
|
||||||
},
|
"cardinal"
|
||||||
0,
|
]]
|
||||||
"cardinal"
|
})
|
||||||
]]
|
},
|
||||||
}),
|
|
||||||
|
|
||||||
patches: [
|
patches: [
|
||||||
{
|
{
|
||||||
|
@ -528,7 +531,7 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
match: /(\i).type===\i\.\i\.MESSAGE_GROUP_BLOCKED\?.*?:/,
|
match: /(\i).type===\i\.\i\.MESSAGE_GROUP_BLOCKED\?.*?:/,
|
||||||
replace: '$&$1.type==="MESSAGE_GROUP_DELETED"?$self.DELETED_MESSAGE_COUNT:',
|
replace: '$&$1.type==="MESSAGE_GROUP_DELETED"?$self.Messages.DELETED_MESSAGE_COUNT:',
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
predicate: () => Settings.plugins.MessageLogger.collapseDeleted
|
predicate: () => Settings.plugins.MessageLogger.collapseDeleted
|
||||||
|
|
|
@ -28,8 +28,8 @@ import { Message } from "discord-types/general";
|
||||||
const RelationshipStore = findByPropsLazy("getRelationships", "isBlocked");
|
const RelationshipStore = findByPropsLazy("getRelationships", "isBlocked");
|
||||||
|
|
||||||
interface MessageDeleteProps {
|
interface MessageDeleteProps {
|
||||||
// Internal intl message for BLOCKED_MESSAGE_COUNT
|
// i18n message i18n.t["+FcYMz"] if deleted, with args
|
||||||
collapsedReason: () => any;
|
collapsedReason: () => any
|
||||||
}
|
}
|
||||||
|
|
||||||
export default definePlugin({
|
export default definePlugin({
|
||||||
|
|
|
@ -20,7 +20,7 @@ const settings = definePluginSettings({
|
||||||
export default definePlugin({
|
export default definePlugin({
|
||||||
name: "NoMosaic",
|
name: "NoMosaic",
|
||||||
authors: [Devs.AutumnVN],
|
authors: [Devs.AutumnVN],
|
||||||
description: "Removes Discord image mosaic",
|
description: "Removes Discord new image mosaic",
|
||||||
tags: ["image", "mosaic", "media"],
|
tags: ["image", "mosaic", "media"],
|
||||||
|
|
||||||
settings,
|
settings,
|
||||||
|
@ -29,8 +29,8 @@ export default definePlugin({
|
||||||
{
|
{
|
||||||
find: '=>"IMAGE"===',
|
find: '=>"IMAGE"===',
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /=>"IMAGE"===\i\|\|"VIDEO"===\i(?:\|\|("VISUAL_PLACEHOLDER"===\i))?;/,
|
match: /=>"IMAGE"===\i\|\|"VIDEO"===\i;/,
|
||||||
replace: (_, visualPlaceholderPred) => visualPlaceholderPred != null ? `=>${visualPlaceholderPred};` : "=>false;"
|
replace: "=>false;"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
|
|
@ -87,7 +87,7 @@ export default definePlugin({
|
||||||
{
|
{
|
||||||
find: "trackAnnouncementMessageLinkClicked({",
|
find: "trackAnnouncementMessageLinkClicked({",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /function (\i\(\i,\i\)\{)(?=.{0,150}trusted:)/,
|
match: /function (\i\(\i,\i\)\{)(?=.{0,100}trusted:)/,
|
||||||
replace: "async function $1 if(await $self.handleLink(...arguments)) return;"
|
replace: "async function $1 if(await $self.handleLink(...arguments)) return;"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
|
@ -30,10 +30,10 @@ export default definePlugin({
|
||||||
{
|
{
|
||||||
find: ".removeMosaicItemHoverButton),",
|
find: ".removeMosaicItemHoverButton),",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /\.nonMediaMosaicItem\]:.{0,40}children:\[(?<=showDownload:(\i).+?isVisualMediaType:(\i).+?)/,
|
match: /\.nonMediaMosaicItem\]:!(\i).{0,50}?children:\[\S,(\S)/,
|
||||||
replace: "$&$1&&$2&&$self.renderPiPButton(),"
|
replace: "$&,$1&&$2&&$self.renderPiPButton(),"
|
||||||
}
|
},
|
||||||
}
|
},
|
||||||
],
|
],
|
||||||
|
|
||||||
renderPiPButton: ErrorBoundary.wrap(() => {
|
renderPiPButton: ErrorBoundary.wrap(() => {
|
||||||
|
|
|
@ -50,8 +50,6 @@ async function runMigrations() {
|
||||||
|
|
||||||
export async function syncAndRunChecks() {
|
export async function syncAndRunChecks() {
|
||||||
await runMigrations();
|
await runMigrations();
|
||||||
if (UserStore.getCurrentUser() == null) return;
|
|
||||||
|
|
||||||
const [oldGuilds, oldGroups, oldFriends] = await DataStore.getMany([
|
const [oldGuilds, oldGroups, oldFriends] = await DataStore.getMany([
|
||||||
guildsKey(),
|
guildsKey(),
|
||||||
groupsKey(),
|
groupsKey(),
|
||||||
|
|
|
@ -20,7 +20,6 @@ import { definePluginSettings } from "@api/Settings";
|
||||||
import ErrorBoundary from "@components/ErrorBoundary";
|
import ErrorBoundary from "@components/ErrorBoundary";
|
||||||
import { makeRange } from "@components/PluginSettings/components";
|
import { makeRange } from "@components/PluginSettings/components";
|
||||||
import { Devs } from "@utils/constants";
|
import { Devs } from "@utils/constants";
|
||||||
import { Logger } from "@utils/Logger";
|
|
||||||
import definePlugin, { OptionType } from "@utils/types";
|
import definePlugin, { OptionType } from "@utils/types";
|
||||||
import { findByCodeLazy } from "@webpack";
|
import { findByCodeLazy } from "@webpack";
|
||||||
import { ChannelStore, GuildMemberStore, GuildStore } from "@webpack/common";
|
import { ChannelStore, GuildMemberStore, GuildStore } from "@webpack/common";
|
||||||
|
@ -52,12 +51,6 @@ const settings = definePluginSettings({
|
||||||
description: "Show role colors in the reactors list",
|
description: "Show role colors in the reactors list",
|
||||||
restartNeeded: true
|
restartNeeded: true
|
||||||
},
|
},
|
||||||
pollResults: {
|
|
||||||
type: OptionType.BOOLEAN,
|
|
||||||
default: true,
|
|
||||||
description: "Show role colors in the poll results",
|
|
||||||
restartNeeded: true
|
|
||||||
},
|
|
||||||
colorChatMessages: {
|
colorChatMessages: {
|
||||||
type: OptionType.BOOLEAN,
|
type: OptionType.BOOLEAN,
|
||||||
default: false,
|
default: false,
|
||||||
|
@ -69,15 +62,14 @@ const settings = definePluginSettings({
|
||||||
description: "Intensity of message coloring.",
|
description: "Intensity of message coloring.",
|
||||||
markers: makeRange(0, 100, 10),
|
markers: makeRange(0, 100, 10),
|
||||||
default: 30
|
default: 30
|
||||||
}
|
},
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
export default definePlugin({
|
export default definePlugin({
|
||||||
name: "RoleColorEverywhere",
|
name: "RoleColorEverywhere",
|
||||||
authors: [Devs.KingFish, Devs.lewisakura, Devs.AutumnVN, Devs.Kyuuhachi, Devs.jamesbt365],
|
authors: [Devs.KingFish, Devs.lewisakura, Devs.AutumnVN, Devs.Kyuuhachi],
|
||||||
description: "Adds the top role color anywhere possible",
|
description: "Adds the top role color anywhere possible",
|
||||||
settings,
|
|
||||||
|
|
||||||
patches: [
|
patches: [
|
||||||
// Chat Mentions
|
// Chat Mentions
|
||||||
{
|
{
|
||||||
|
@ -85,131 +77,82 @@ export default definePlugin({
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
match: /onContextMenu:\i,color:\i,\.\.\.\i(?=,children:)(?<=user:(\i),channel:(\i).{0,500}?)/,
|
match: /onContextMenu:\i,color:\i,\.\.\.\i(?=,children:)(?<=user:(\i),channel:(\i).{0,500}?)/,
|
||||||
replace: "$&,color:$self.getColorInt($1?.id,$2?.id)"
|
replace: "$&,color:$self.getUserColor($1?.id,{channelId:$2?.id})"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
predicate: () => settings.store.chatMentions
|
predicate: () => settings.store.chatMentions,
|
||||||
},
|
},
|
||||||
// Slate
|
// Slate
|
||||||
{
|
{
|
||||||
find: ".userTooltip,children",
|
find: ".userTooltip,children",
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
match: /let\{id:(\i),guildId:\i,channelId:(\i)[^}]*\}.*?\.\i,{(?=children)/,
|
match: /let\{id:(\i),guildId:(\i)[^}]*\}.*?\.\i,{(?=children)/,
|
||||||
replace: "$&color:$self.getColorInt($1,$2),"
|
replace: "$&color:$self.getUserColor($1,{guildId:$2}),"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
predicate: () => settings.store.chatMentions
|
predicate: () => settings.store.chatMentions,
|
||||||
},
|
},
|
||||||
// Member List Role Headers
|
|
||||||
{
|
{
|
||||||
find: 'tutorialId:"whos-online',
|
find: 'tutorialId:"whos-online',
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
match: /null,\i," — ",\i\]/,
|
match: /null,\i," — ",\i\]/,
|
||||||
replace: "null,$self.RoleGroupColor(arguments[0])]"
|
replace: "null,$self.roleGroupColor(arguments[0])]"
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
predicate: () => settings.store.memberList
|
predicate: () => settings.store.memberList,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
find: "#{intl::THREAD_BROWSER_PRIVATE}",
|
find: "#{intl::THREAD_BROWSER_PRIVATE}",
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
match: /children:\[\i," — ",\i\]/,
|
match: /children:\[\i," — ",\i\]/,
|
||||||
replace: "children:[$self.RoleGroupColor(arguments[0])]"
|
replace: "children:[$self.roleGroupColor(arguments[0])]"
|
||||||
},
|
},
|
||||||
],
|
],
|
||||||
predicate: () => settings.store.memberList
|
predicate: () => settings.store.memberList,
|
||||||
},
|
},
|
||||||
// Voice Users
|
|
||||||
{
|
{
|
||||||
find: "renderPrioritySpeaker(){",
|
find: "renderPrioritySpeaker",
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
match: /renderName\(\){.+?usernameSpeaking\]:.+?(?=children)/,
|
match: /renderName\(\){.+?usernameSpeaking\]:.+?(?=children)/,
|
||||||
replace: "$&style:$self.getColorStyle(this?.props?.user?.id,this?.props?.guildId),"
|
replace: "$&...$self.getVoiceProps(this.props),"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
predicate: () => settings.store.voiceUsers
|
predicate: () => settings.store.voiceUsers,
|
||||||
},
|
},
|
||||||
// Reaction List
|
|
||||||
{
|
{
|
||||||
find: ".reactorDefault",
|
find: ".reactorDefault",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /,onContextMenu:\i=>.{0,15}\((\i),(\i),(\i)\).{0,250}tag:"strong"/,
|
match: /,onContextMenu:e=>.{0,15}\((\i),(\i),(\i)\).{0,250}tag:"strong"/,
|
||||||
replace: "$&,style:$self.getColorStyle($2?.id,$1?.channel?.id)"
|
replace: "$&,style:{color:$self.getColor($2?.id,$1)}"
|
||||||
},
|
},
|
||||||
predicate: () => settings.store.reactorsList,
|
predicate: () => settings.store.reactorsList,
|
||||||
},
|
},
|
||||||
// Poll Results
|
|
||||||
{
|
|
||||||
find: ",reactionVoteCounts",
|
|
||||||
replacement: {
|
|
||||||
match: /\.nickname,(?=children:)/,
|
|
||||||
replace: "$&style:$self.getColorStyle(arguments[0]?.user?.id,arguments[0]?.channel?.id),"
|
|
||||||
},
|
|
||||||
predicate: () => settings.store.pollResults
|
|
||||||
},
|
|
||||||
// Messages
|
|
||||||
{
|
{
|
||||||
find: "#{intl::MESSAGE_EDITED}",
|
find: "#{intl::MESSAGE_EDITED}",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /(?<=isUnsupported\]:(\i)\.isUnsupported\}\),)(?=children:\[)/,
|
match: /(?<=isUnsupported\]:(\i)\.isUnsupported\}\),)(?=children:\[)/,
|
||||||
replace: "style:$self.useMessageColorsStyle($1),"
|
replace: "style:{color:$self.useMessageColor($1)},"
|
||||||
},
|
},
|
||||||
predicate: () => settings.store.colorChatMessages
|
predicate: () => settings.store.colorChatMessages,
|
||||||
}
|
},
|
||||||
],
|
],
|
||||||
|
settings,
|
||||||
|
|
||||||
getColorString(userId: string, channelOrGuildId: string) {
|
getColor(userId: string, { channelId, guildId }: { channelId?: string; guildId?: string; }) {
|
||||||
try {
|
if (!(guildId ??= ChannelStore.getChannel(channelId!)?.guild_id)) return null;
|
||||||
const guildId = ChannelStore.getChannel(channelOrGuildId)?.guild_id ?? GuildStore.getGuild(channelOrGuildId)?.id;
|
return GuildMemberStore.getMember(guildId, userId)?.colorString ?? null;
|
||||||
if (guildId == null) return null;
|
|
||||||
|
|
||||||
return GuildMemberStore.getMember(guildId, userId)?.colorString ?? null;
|
|
||||||
} catch (e) {
|
|
||||||
new Logger("RoleColorEverywhere").error("Failed to get color string", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
},
|
},
|
||||||
|
|
||||||
getColorInt(userId: string, channelOrGuildId: string) {
|
getUserColor(userId: string, ids: { channelId?: string; guildId?: string; }) {
|
||||||
const colorString = this.getColorString(userId, channelOrGuildId);
|
const colorString = this.getColor(userId, ids);
|
||||||
return colorString && parseInt(colorString.slice(1), 16);
|
return colorString && parseInt(colorString.slice(1), 16);
|
||||||
},
|
},
|
||||||
|
|
||||||
getColorStyle(userId: string, channelOrGuildId: string) {
|
roleGroupColor: ErrorBoundary.wrap(({ id, count, title, guildId, label }: { id: string; count: number; title: string; guildId: string; label: string; }) => {
|
||||||
const colorString = this.getColorString(userId, channelOrGuildId);
|
|
||||||
|
|
||||||
return colorString && {
|
|
||||||
color: colorString
|
|
||||||
};
|
|
||||||
},
|
|
||||||
|
|
||||||
useMessageColorsStyle(message: any) {
|
|
||||||
try {
|
|
||||||
const { messageSaturation } = settings.use(["messageSaturation"]);
|
|
||||||
const author = useMessageAuthor(message);
|
|
||||||
|
|
||||||
if (author.colorString != null && messageSaturation !== 0) {
|
|
||||||
const value = `color-mix(in oklab, ${author.colorString} ${messageSaturation}%, var({DEFAULT}))`;
|
|
||||||
|
|
||||||
return {
|
|
||||||
color: value.replace("{DEFAULT}", "--text-normal"),
|
|
||||||
"--header-primary": value.replace("{DEFAULT}", "--header-primary"),
|
|
||||||
"--text-muted": value.replace("{DEFAULT}", "--text-muted")
|
|
||||||
};
|
|
||||||
}
|
|
||||||
} catch (e) {
|
|
||||||
new Logger("RoleColorEverywhere").error("Failed to get message color", e);
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
},
|
|
||||||
|
|
||||||
RoleGroupColor: ErrorBoundary.wrap(({ id, count, title, guildId, label }: { id: string; count: number; title: string; guildId: string; label: string; }) => {
|
|
||||||
const role = GuildStore.getRole(guildId, id);
|
const role = GuildStore.getRole(guildId, id);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
@ -221,5 +164,25 @@ export default definePlugin({
|
||||||
{title ?? label} — {count}
|
{title ?? label} — {count}
|
||||||
</span>
|
</span>
|
||||||
);
|
);
|
||||||
}, { noop: true })
|
}, { noop: true }),
|
||||||
|
|
||||||
|
getVoiceProps({ user: { id: userId }, guildId }: { user: { id: string; }; guildId: string; }) {
|
||||||
|
return {
|
||||||
|
style: {
|
||||||
|
color: this.getColor(userId, { guildId })
|
||||||
|
}
|
||||||
|
};
|
||||||
|
},
|
||||||
|
|
||||||
|
useMessageColor(message: any) {
|
||||||
|
try {
|
||||||
|
const { messageSaturation } = settings.use(["messageSaturation"]);
|
||||||
|
const author = useMessageAuthor(message);
|
||||||
|
if (author.colorString !== undefined && messageSaturation !== 0)
|
||||||
|
return `color-mix(in oklab, ${author.colorString} ${messageSaturation}%, var(--text-normal))`;
|
||||||
|
} catch (e) {
|
||||||
|
console.error("[RCE] failed to get message color", e);
|
||||||
|
}
|
||||||
|
return undefined;
|
||||||
|
},
|
||||||
});
|
});
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
/*
|
/*
|
||||||
* Vencord, a modification for Discord's desktop app
|
* Vencord, a modification for Discord's desktop app
|
||||||
* Copyright (c) 2024 Vendicated and contributors
|
* Copyright (c) 2022 Vendicated and contributors
|
||||||
*
|
*
|
||||||
* This program is free software: you can redistribute it and/or modify
|
* 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
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
@ -18,9 +18,9 @@
|
||||||
|
|
||||||
import { IShikiTheme } from "@vap/shiki";
|
import { IShikiTheme } from "@vap/shiki";
|
||||||
|
|
||||||
export const SHIKI_REPO = "shikijs/textmate-grammars-themes";
|
export const SHIKI_REPO = "shikijs/shiki";
|
||||||
export const SHIKI_REPO_COMMIT = "2d87559c7601a928b9f7e0f0dda243d2fb6d4499";
|
export const SHIKI_REPO_COMMIT = "0b28ad8ccfbf2615f2d9d38ea8255416b8ac3043";
|
||||||
export const shikiRepoTheme = (name: string) => `https://raw.githubusercontent.com/${SHIKI_REPO}/${SHIKI_REPO_COMMIT}/packages/tm-themes/themes/${name}.json`;
|
export const shikiRepoTheme = (name: string) => `https://raw.githubusercontent.com/${SHIKI_REPO}/${SHIKI_REPO_COMMIT}/packages/shiki/themes/${name}.json`;
|
||||||
|
|
||||||
export const themes = {
|
export const themes = {
|
||||||
// Default
|
// Default
|
||||||
|
@ -30,59 +30,33 @@ export const themes = {
|
||||||
MaterialCandy: "https://raw.githubusercontent.com/millsp/material-candy/master/material-candy.json",
|
MaterialCandy: "https://raw.githubusercontent.com/millsp/material-candy/master/material-candy.json",
|
||||||
|
|
||||||
// More from Shiki repo
|
// More from Shiki repo
|
||||||
Andromeeda: shikiRepoTheme("andromeeda"),
|
|
||||||
AuroraX: shikiRepoTheme("aurora-x"),
|
|
||||||
AyuDark: shikiRepoTheme("ayu-dark"),
|
|
||||||
CatppuccinLatte: shikiRepoTheme("catppuccin-latte"),
|
|
||||||
CatppuccinFrappe: shikiRepoTheme("catppuccin-frappe"),
|
|
||||||
CatppuccinMacchiato: shikiRepoTheme("catppuccin-macchiato"),
|
|
||||||
CatppuccinMocha: shikiRepoTheme("catppuccin-mocha"),
|
|
||||||
DraculaSoft: shikiRepoTheme("dracula-soft"),
|
DraculaSoft: shikiRepoTheme("dracula-soft"),
|
||||||
Dracula: shikiRepoTheme("dracula"),
|
Dracula: shikiRepoTheme("dracula"),
|
||||||
EverforestDark: shikiRepoTheme("everforest-dark"),
|
|
||||||
EverforestLight: shikiRepoTheme("everforest-light"),
|
|
||||||
GithubDarkDefault: shikiRepoTheme("github-dark-default"),
|
|
||||||
GithubDarkDimmed: shikiRepoTheme("github-dark-dimmed"),
|
GithubDarkDimmed: shikiRepoTheme("github-dark-dimmed"),
|
||||||
GithubDarkHighContrast: shikiRepoTheme("github-dark-high-contrast"),
|
|
||||||
GithubDark: shikiRepoTheme("github-dark"),
|
GithubDark: shikiRepoTheme("github-dark"),
|
||||||
GithubLightDefault: shikiRepoTheme("github-light-default"),
|
|
||||||
GithubLightHighContrast: shikiRepoTheme("github-light-high-contrast"),
|
|
||||||
GithubLight: shikiRepoTheme("github-light"),
|
GithubLight: shikiRepoTheme("github-light"),
|
||||||
Houston: shikiRepoTheme("houston"),
|
|
||||||
KanagawaDragon: shikiRepoTheme("kanagawa-dragon"),
|
|
||||||
KanagawaLotus: shikiRepoTheme("kanagawa-lotus"),
|
|
||||||
KanagawaWave: shikiRepoTheme("kanagawa-wave"),
|
|
||||||
LaserWave: shikiRepoTheme("laserwave"),
|
|
||||||
LightPlus: shikiRepoTheme("light-plus"),
|
LightPlus: shikiRepoTheme("light-plus"),
|
||||||
MaterialDarker: shikiRepoTheme("material-theme-darker"),
|
MaterialDarker: shikiRepoTheme("material-darker"),
|
||||||
MaterialDefault: shikiRepoTheme("material-theme"),
|
MaterialDefault: shikiRepoTheme("material-default"),
|
||||||
MaterialLighter: shikiRepoTheme("material-theme-lighter"),
|
MaterialLighter: shikiRepoTheme("material-lighter"),
|
||||||
MaterialOcean: shikiRepoTheme("material-theme-ocean"),
|
MaterialOcean: shikiRepoTheme("material-ocean"),
|
||||||
MaterialPalenight: shikiRepoTheme("material-theme-palenight"),
|
MaterialPalenight: shikiRepoTheme("material-palenight"),
|
||||||
MinDark: shikiRepoTheme("min-dark"),
|
MinDark: shikiRepoTheme("min-dark"),
|
||||||
MinLight: shikiRepoTheme("min-light"),
|
MinLight: shikiRepoTheme("min-light"),
|
||||||
Monokai: shikiRepoTheme("monokai"),
|
Monokai: shikiRepoTheme("monokai"),
|
||||||
NightOwl: shikiRepoTheme("night-owl"),
|
|
||||||
Nord: shikiRepoTheme("nord"),
|
Nord: shikiRepoTheme("nord"),
|
||||||
OneDarkPro: shikiRepoTheme("one-dark-pro"),
|
OneDarkPro: shikiRepoTheme("one-dark-pro"),
|
||||||
OneLight: shikiRepoTheme("one-light"),
|
|
||||||
Plastic: shikiRepoTheme("plastic"),
|
|
||||||
Poimandres: shikiRepoTheme("poimandres"),
|
Poimandres: shikiRepoTheme("poimandres"),
|
||||||
Red: shikiRepoTheme("red"),
|
|
||||||
RosePineDawn: shikiRepoTheme("rose-pine-dawn"),
|
RosePineDawn: shikiRepoTheme("rose-pine-dawn"),
|
||||||
RosePineMoon: shikiRepoTheme("rose-pine-moon"),
|
RosePineMoon: shikiRepoTheme("rose-pine-moon"),
|
||||||
RosePine: shikiRepoTheme("rose-pine"),
|
RosePine: shikiRepoTheme("rose-pine"),
|
||||||
SlackDark: shikiRepoTheme("slack-dark"),
|
SlackDark: shikiRepoTheme("slack-dark"),
|
||||||
SlackOchin: shikiRepoTheme("slack-ochin"),
|
SlackOchin: shikiRepoTheme("slack-ochin"),
|
||||||
SnazzyLight: shikiRepoTheme("snazzy-light"),
|
|
||||||
SolarizedDark: shikiRepoTheme("solarized-dark"),
|
SolarizedDark: shikiRepoTheme("solarized-dark"),
|
||||||
SolarizedLight: shikiRepoTheme("solarized-light"),
|
SolarizedLight: shikiRepoTheme("solarized-light"),
|
||||||
Synthwave84: shikiRepoTheme("synthwave-84"),
|
|
||||||
TokyoNight: shikiRepoTheme("tokyo-night"),
|
|
||||||
Vesper: shikiRepoTheme("vesper"),
|
|
||||||
VitesseBlack: shikiRepoTheme("vitesse-black"),
|
|
||||||
VitesseDark: shikiRepoTheme("vitesse-dark"),
|
VitesseDark: shikiRepoTheme("vitesse-dark"),
|
||||||
VitesseLight: shikiRepoTheme("vitesse-light"),
|
VitesseLight: shikiRepoTheme("vitesse-light"),
|
||||||
|
CssVariables: shikiRepoTheme("css-variables"),
|
||||||
};
|
};
|
||||||
|
|
||||||
export const themeCache = new Map<string, IShikiTheme>();
|
export const themeCache = new Map<string, IShikiTheme>();
|
||||||
|
|
|
@ -103,7 +103,7 @@ export default definePlugin({
|
||||||
replacement: [
|
replacement: [
|
||||||
{
|
{
|
||||||
// Do not show confirmation to join a voice channel when already connected to another if clicking on a hidden voice channel
|
// Do not show confirmation to join a voice channel when already connected to another if clicking on a hidden voice channel
|
||||||
match: /(?<=getIgnoredUsersForVoiceChannel\((\i)\.id\);return\()/,
|
match: /(?<=getBlockedUsersForVoiceChannel\((\i)\.id\);return\()/,
|
||||||
replace: (_, channel) => `!$self.isHiddenChannel(${channel})&&`
|
replace: (_, channel) => `!$self.isHiddenChannel(${channel})&&`
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
|
|
@ -107,7 +107,7 @@ export default definePlugin({
|
||||||
predicate: () => settings.store.disableDisallowedDiscoveryFilters,
|
predicate: () => settings.store.disableDisallowedDiscoveryFilters,
|
||||||
all: true,
|
all: true,
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /\i\.\i\.get\(\{url:\i\.\i\.GUILD_DISCOVERY_VALID_TERM,query:\{term:\i\},oldFormErrors:!0,rejectWithError:!1\}\)/g,
|
match: /\i\.\i\.get\(\{url:\i\.\i\.GUILD_DISCOVERY_VALID_TERM,query:\{term:\i\},oldFormErrors:!0\}\)/g,
|
||||||
replace: "Promise.resolve({ body: { valid: true } })"
|
replace: "Promise.resolve({ body: { valid: true } })"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,7 +24,7 @@ import { Devs } from "@utils/constants";
|
||||||
import { getIntlMessage } from "@utils/discord";
|
import { getIntlMessage } from "@utils/discord";
|
||||||
import definePlugin, { OptionType } from "@utils/types";
|
import definePlugin, { OptionType } from "@utils/types";
|
||||||
import { findComponentByCodeLazy, findExportedComponentLazy, findStoreLazy } from "@webpack";
|
import { findComponentByCodeLazy, findExportedComponentLazy, findStoreLazy } from "@webpack";
|
||||||
import { GuildMemberStore, RelationshipStore, SelectedChannelStore, Tooltip, UserStore, useStateFromStores } from "@webpack/common";
|
import { ChannelStore, GuildMemberStore, RelationshipStore, SelectedChannelStore, Tooltip, UserStore, useStateFromStores } from "@webpack/common";
|
||||||
|
|
||||||
import { buildSeveralUsers } from "../typingTweaks";
|
import { buildSeveralUsers } from "../typingTweaks";
|
||||||
|
|
||||||
|
@ -44,7 +44,7 @@ function getDisplayName(guildId: string, userId: string) {
|
||||||
return GuildMemberStore.getNick(guildId, userId) ?? (user as any).globalName ?? user.username;
|
return GuildMemberStore.getNick(guildId, userId) ?? (user as any).globalName ?? user.username;
|
||||||
}
|
}
|
||||||
|
|
||||||
function TypingIndicator({ channelId, guildId }: { channelId: string; guildId: string; }) {
|
function TypingIndicator({ channelId }: { channelId: string; }) {
|
||||||
const typingUsers: Record<string, number> = useStateFromStores(
|
const typingUsers: Record<string, number> = useStateFromStores(
|
||||||
[TypingStore],
|
[TypingStore],
|
||||||
() => ({ ...TypingStore.getTypingUsers(channelId) as Record<string, number> }),
|
() => ({ ...TypingStore.getTypingUsers(channelId) as Record<string, number> }),
|
||||||
|
@ -57,6 +57,7 @@ function TypingIndicator({ channelId, guildId }: { channelId: string; guildId: s
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
const currentChannelId: string = useStateFromStores([SelectedChannelStore], () => SelectedChannelStore.getChannelId());
|
const currentChannelId: string = useStateFromStores([SelectedChannelStore], () => SelectedChannelStore.getChannelId());
|
||||||
|
const guildId = ChannelStore.getChannel(channelId).guild_id;
|
||||||
|
|
||||||
if (!settings.store.includeMutedChannels) {
|
if (!settings.store.includeMutedChannels) {
|
||||||
const isChannelMuted = UserGuildSettingsStore.isChannelMuted(guildId, channelId);
|
const isChannelMuted = UserGuildSettingsStore.isChannelMuted(guildId, channelId);
|
||||||
|
@ -164,7 +165,7 @@ export default definePlugin({
|
||||||
find: "UNREAD_IMPORTANT:",
|
find: "UNREAD_IMPORTANT:",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /\.name\),.{0,120}\.children.+?:null(?<=,channel:(\i).+?)/,
|
match: /\.name\),.{0,120}\.children.+?:null(?<=,channel:(\i).+?)/,
|
||||||
replace: "$&,$self.TypingIndicator($1.id,$1.getGuildId())"
|
replace: "$&,$self.TypingIndicator($1.id)"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
// Theads
|
// Theads
|
||||||
|
@ -173,14 +174,14 @@ export default definePlugin({
|
||||||
find: "M11 9H4C2.89543 9 2 8.10457 2 7V1C2 0.447715 1.55228 0 1 0C0.447715 0 0 0.447715 0 1V7C0 9.20914 1.79086 11 4 11H11C11.5523 11 12 10.5523 12 10C12 9.44771 11.5523 9 11 9Z",
|
find: "M11 9H4C2.89543 9 2 8.10457 2 7V1C2 0.447715 1.55228 0 1 0C0.447715 0 0 0.447715 0 1V7C0 9.20914 1.79086 11 4 11H11C11.5523 11 12 10.5523 12 10C12 9.44771 11.5523 9 11 9Z",
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /mentionsCount:\i.+?null(?<=channel:(\i).+?)/,
|
match: /mentionsCount:\i.+?null(?<=channel:(\i).+?)/,
|
||||||
replace: "$&,$self.TypingIndicator($1.id,$1.getGuildId())"
|
replace: "$&,$self.TypingIndicator($1.id)"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
|
|
||||||
TypingIndicator: (channelId: string, guildId: string) => (
|
TypingIndicator: (channelId: string) => (
|
||||||
<ErrorBoundary noop>
|
<ErrorBoundary noop>
|
||||||
<TypingIndicator channelId={channelId} guildId={guildId} />
|
<TypingIndicator channelId={channelId} />
|
||||||
</ErrorBoundary>
|
</ErrorBoundary>
|
||||||
),
|
),
|
||||||
});
|
});
|
||||||
|
|
|
@ -129,22 +129,14 @@ export default definePlugin({
|
||||||
buildSeveralUsers,
|
buildSeveralUsers,
|
||||||
|
|
||||||
mutateChildren(props: any, users: User[], children: any) {
|
mutateChildren(props: any, users: User[], children: any) {
|
||||||
try {
|
if (!Array.isArray(children)) return children;
|
||||||
if (!Array.isArray(children)) {
|
|
||||||
return children;
|
|
||||||
}
|
|
||||||
|
|
||||||
let element = 0;
|
let element = 0;
|
||||||
|
|
||||||
return children.map(c =>
|
return children.map(c =>
|
||||||
c.type === "strong" || (typeof c !== "string" && !React.isValidElement(c))
|
c.type === "strong"
|
||||||
? <TypingUser {...props} user={users[element++]} />
|
? <TypingUser {...props} user={users[element++]} />
|
||||||
: c
|
: c
|
||||||
);
|
);
|
||||||
} catch (e) {
|
|
||||||
console.error(e);
|
|
||||||
}
|
|
||||||
|
|
||||||
return children;
|
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
@ -209,11 +209,10 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
// Group DMs top small & large icon
|
// Group DMs top small & large icon
|
||||||
{
|
{
|
||||||
find: '["aria-hidden"],"aria-label":',
|
find: /\.recipients\.length>=2(?!<isMultiUserDM.{0,50})/,
|
||||||
replacement: {
|
replacement: {
|
||||||
match: /null==\i\.icon\?.+?src:(\(0,\i\.\i\).+?\))(?=[,}])/,
|
match: /null==\i\.icon\?.+?src:(\(0,\i\.\i\).+?\))(?=[,}])/,
|
||||||
// We have to check that icon is not an unread GDM in the server bar
|
replace: (m, iconUrl) => `${m},onClick:()=>$self.openAvatar(${iconUrl})`
|
||||||
replace: (m, iconUrl) => `${m},onClick:()=>arguments[0]?.size!=="SIZE_48"&&$self.openAvatar(${iconUrl})`
|
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
// User DMs top small icon
|
// User DMs top small icon
|
||||||
|
|
|
@ -155,7 +155,6 @@ export default definePlugin({
|
||||||
"guild-context": MakeContextCallback("Guild"),
|
"guild-context": MakeContextCallback("Guild"),
|
||||||
"channel-context": MakeContextCallback("Channel"),
|
"channel-context": MakeContextCallback("Channel"),
|
||||||
"thread-context": MakeContextCallback("Channel"),
|
"thread-context": MakeContextCallback("Channel"),
|
||||||
"gdm-context": MakeContextCallback("Channel"),
|
|
||||||
"user-context": MakeContextCallback("User")
|
"user-context": MakeContextCallback("User")
|
||||||
},
|
},
|
||||||
|
|
||||||
|
|
|
@ -267,6 +267,10 @@ export const Devs = /* #__PURE__*/ Object.freeze({
|
||||||
name: "arHSM",
|
name: "arHSM",
|
||||||
id: 841509053422632990n
|
id: 841509053422632990n
|
||||||
},
|
},
|
||||||
|
F53: {
|
||||||
|
name: "Cassie (Code)",
|
||||||
|
id: 280411966126948353n
|
||||||
|
},
|
||||||
AutumnVN: {
|
AutumnVN: {
|
||||||
name: "AutumnVN",
|
name: "AutumnVN",
|
||||||
id: 393694671383166998n
|
id: 393694671383166998n
|
||||||
|
@ -516,8 +520,8 @@ export const Devs = /* #__PURE__*/ Object.freeze({
|
||||||
id: 721717126523781240n,
|
id: 721717126523781240n,
|
||||||
},
|
},
|
||||||
nyx: {
|
nyx: {
|
||||||
name: "verticalsync.",
|
name: "verticalsync",
|
||||||
id: 1207087393929171095n
|
id: 328165170536775680n
|
||||||
},
|
},
|
||||||
nekohaxx: {
|
nekohaxx: {
|
||||||
name: "nekohaxx",
|
name: "nekohaxx",
|
||||||
|
@ -571,14 +575,10 @@ export const Devs = /* #__PURE__*/ Object.freeze({
|
||||||
name: "RamziAH",
|
name: "RamziAH",
|
||||||
id: 1279957227612147747n,
|
id: 1279957227612147747n,
|
||||||
},
|
},
|
||||||
SomeAspy: {
|
SomeAspy: {
|
||||||
name: "SomeAspy",
|
name: "SomeAspy",
|
||||||
id: 516750892372852754n,
|
id: 516750892372852754n,
|
||||||
},
|
},
|
||||||
jamesbt365: {
|
|
||||||
name: "jamesbt365",
|
|
||||||
id: 158567567487795200n,
|
|
||||||
},
|
|
||||||
} satisfies Record<string, Dev>);
|
} satisfies Record<string, Dev>);
|
||||||
|
|
||||||
// iife so #__PURE__ works correctly
|
// iife so #__PURE__ works correctly
|
||||||
|
|
|
@ -19,7 +19,7 @@
|
||||||
import "./discord.css";
|
import "./discord.css";
|
||||||
|
|
||||||
import { MessageObject } from "@api/MessageEvents";
|
import { MessageObject } from "@api/MessageEvents";
|
||||||
import { ChannelStore, ComponentDispatch, Constants, FluxDispatcher, GuildStore, i18n, IconUtils, InviteActions, MessageActions, PrivateChannelsStore, RestAPI, SelectedChannelStore, SelectedGuildStore, UserProfileActions, UserProfileStore, UserSettingsActionCreators, UserUtils } from "@webpack/common";
|
import { ChannelStore, ComponentDispatch, Constants, FluxDispatcher, GuildStore, i18n, InviteActions, MessageActions, PrivateChannelsStore, RestAPI, SelectedChannelStore, SelectedGuildStore, UserProfileActions, UserProfileStore, UserSettingsActionCreators, UserUtils } from "@webpack/common";
|
||||||
import { Channel, Guild, Message, User } from "discord-types/general";
|
import { Channel, Guild, Message, User } from "discord-types/general";
|
||||||
import { Except } from "type-fest";
|
import { Except } from "type-fest";
|
||||||
|
|
||||||
|
@ -212,14 +212,3 @@ export async function fetchUserProfile(id: string, options?: FetchUserProfileOpt
|
||||||
export function getUniqueUsername(user: User) {
|
export function getUniqueUsername(user: User) {
|
||||||
return user.discriminator === "0" ? user.username : user.tag;
|
return user.discriminator === "0" ? user.username : user.tag;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Get the URL for an emoji. This function always returns a gif URL for animated emojis, instead of webp
|
|
||||||
* @param id The emoji id
|
|
||||||
* @param animated Whether the emoji is animated
|
|
||||||
* @param size The size for the emoji
|
|
||||||
*/
|
|
||||||
export function getEmojiURL(id: string, animated: boolean, size: number) {
|
|
||||||
const url = IconUtils.getEmojiURL({ id, animated, size });
|
|
||||||
return animated ? url.replace(".webp", ".gif") : url;
|
|
||||||
}
|
|
||||||
|
|
|
@ -21,8 +21,8 @@ import { Patch, PatchReplacement, ReplaceFn } from "./types";
|
||||||
|
|
||||||
export function canonicalizeMatch<T extends RegExp | string>(match: T): T {
|
export function canonicalizeMatch<T extends RegExp | string>(match: T): T {
|
||||||
let partialCanon = typeof match === "string" ? match : match.source;
|
let partialCanon = typeof match === "string" ? match : match.source;
|
||||||
partialCanon = partialCanon.replaceAll(/#{intl::([\w$+/]*)(?:::(\w+))?}/g, (_, key, modifier) => {
|
partialCanon = partialCanon.replaceAll(/#{intl::([A-Za-z_$][\w$]*)}/g, (_, key) => {
|
||||||
const hashed = modifier === "raw" ? key : runtimeHashMessageKey(key);
|
const hashed = runtimeHashMessageKey(key);
|
||||||
|
|
||||||
const isString = typeof match === "string";
|
const isString = typeof match === "string";
|
||||||
const hasSpecialChars = !Number.isNaN(Number(hashed[0])) || hashed.includes("+") || hashed.includes("/");
|
const hasSpecialChars = !Number.isNaN(Number(hashed[0])) || hashed.includes("+") || hashed.includes("/");
|
||||||
|
@ -40,7 +40,7 @@ export function canonicalizeMatch<T extends RegExp | string>(match: T): T {
|
||||||
return partialCanon as T;
|
return partialCanon as T;
|
||||||
}
|
}
|
||||||
|
|
||||||
const canonSource = partialCanon.replaceAll("\\i", String.raw`(?:[A-Za-z_$][\w$]*)`);
|
const canonSource = partialCanon.replaceAll(String.raw`\i`, String.raw`(?:[A-Za-z_$][\w$]*)`);
|
||||||
return new RegExp(canonSource, match.flags) as T;
|
return new RegExp(canonSource, match.flags) as T;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -163,13 +163,9 @@ waitFor(["open", "saveAccountChanges"], m => SettingsRouter = m);
|
||||||
|
|
||||||
export const PermissionsBits: t.PermissionsBits = findLazy(m => typeof m.ADMINISTRATOR === "bigint");
|
export const PermissionsBits: t.PermissionsBits = findLazy(m => typeof m.ADMINISTRATOR === "bigint");
|
||||||
|
|
||||||
export const { zustandCreate } = mapMangledModuleLazy(["useSyncExternalStoreWithSelector:", "Object.assign"], {
|
export const zustandCreate = findByCodeLazy("will be removed in v4");
|
||||||
zustandCreate: filters.byCode(/=>(\i)\?\i\(\1/)
|
|
||||||
});
|
|
||||||
|
|
||||||
export const { zustandPersist } = mapMangledModuleLazy(".onRehydrateStorage)?", {
|
export const zustandPersist = findByCodeLazy("[zustand persist middleware]");
|
||||||
zustandPersist: filters.byCode(/(\(\i,\i\))=>.+?\i\1/)
|
|
||||||
});
|
|
||||||
|
|
||||||
export const MessageActions = findByPropsLazy("editMessage", "sendMessage");
|
export const MessageActions = findByPropsLazy("editMessage", "sendMessage");
|
||||||
export const MessageCache = findByPropsLazy("clearCache", "_channelMessages");
|
export const MessageCache = findByPropsLazy("clearCache", "_channelMessages");
|
||||||
|
@ -185,7 +181,7 @@ export const ExpressionPickerStore: t.ExpressionPickerStore = mapMangledModuleLa
|
||||||
toggleExpressionPicker: filters.byCode(/getState\(\)\.activeView===\i\?\i\(\):\i\(/),
|
toggleExpressionPicker: filters.byCode(/getState\(\)\.activeView===\i\?\i\(\):\i\(/),
|
||||||
setExpressionPickerView: filters.byCode(/setState\({activeView:\i,lastActiveView:/),
|
setExpressionPickerView: filters.byCode(/setState\({activeView:\i,lastActiveView:/),
|
||||||
setSearchQuery: filters.byCode("searchQuery:"),
|
setSearchQuery: filters.byCode("searchQuery:"),
|
||||||
useExpressionPickerStore: filters.byCode(/\(\i,\i=\i\)=>/)
|
useExpressionPickerStore: filters.byCode("Object.is")
|
||||||
});
|
});
|
||||||
|
|
||||||
export const PopoutActions: t.PopoutActions = mapMangledModuleLazy('type:"POPOUT_WINDOW_OPEN"', {
|
export const PopoutActions: t.PopoutActions = mapMangledModuleLazy('type:"POPOUT_WINDOW_OPEN"', {
|
||||||
|
|
Loading…
Reference in a new issue