mirror of
https://github.com/Vendicated/Vencord.git
synced 2024-09-20 06:30:35 +00:00
chore: update eslint to 9.7.0 and stylelint to 16.7.0
This commit is contained in:
parent
99d7ed0c08
commit
0c8e91b716
96 changed files with 689 additions and 1932 deletions
|
@ -58,6 +58,7 @@
|
||||||
"@typescript-eslint/no-non-null-asserted-optional-chain": "error",
|
"@typescript-eslint/no-non-null-asserted-optional-chain": "error",
|
||||||
"@typescript-eslint/no-unnecessary-condition": "error",
|
"@typescript-eslint/no-unnecessary-condition": "error",
|
||||||
"@typescript-eslint/no-unnecessary-type-assertion": "error",
|
"@typescript-eslint/no-unnecessary-type-assertion": "error",
|
||||||
|
"@typescript-eslint/no-unused-expressions": "error",
|
||||||
"@typescript-eslint/non-nullable-type-assertion-style": "error",
|
"@typescript-eslint/non-nullable-type-assertion-style": "error",
|
||||||
"@typescript-eslint/prefer-as-const": "error",
|
"@typescript-eslint/prefer-as-const": "error",
|
||||||
"@typescript-eslint/require-await": "error",
|
"@typescript-eslint/require-await": "error",
|
||||||
|
|
|
@ -1,7 +1,13 @@
|
||||||
{
|
{
|
||||||
"extends": "stylelint-config-standard",
|
"extends": [
|
||||||
|
"stylelint-config-standard",
|
||||||
|
"@stylistic/stylelint-config"
|
||||||
|
],
|
||||||
|
"plugins": [
|
||||||
|
"@stylistic/stylelint-plugin"
|
||||||
|
],
|
||||||
"rules": {
|
"rules": {
|
||||||
"indentation": 4,
|
"@stylistic/indentation": 4,
|
||||||
"selector-class-pattern": [
|
"selector-class-pattern": [
|
||||||
"^[a-z][a-zA-Z0-9]*(-[a-z0-9][a-zA-Z0-9]*)*$",
|
"^[a-z][a-zA-Z0-9]*(-[a-z0-9][a-zA-Z0-9]*)*$",
|
||||||
{
|
{
|
||||||
|
|
133
eslint.config.mjs
Normal file
133
eslint.config.mjs
Normal file
|
@ -0,0 +1,133 @@
|
||||||
|
import stylistic from "@stylistic/eslint-plugin";
|
||||||
|
import pathAlias from "eslint-plugin-path-alias";
|
||||||
|
import simpleHeader from "eslint-plugin-simple-header";
|
||||||
|
import simpleImportSort from "eslint-plugin-simple-import-sort";
|
||||||
|
import unusedImports from "eslint-plugin-unused-imports";
|
||||||
|
import tseslint from "typescript-eslint";
|
||||||
|
|
||||||
|
export default tseslint.config(
|
||||||
|
{ ignores: ["browser", "dist", "packages", "src/**/*.?(c|m)js?(x)", "eslint.config.mjs"] },
|
||||||
|
{
|
||||||
|
files: ["**/*.?(c|m)[jt]s?(x)"],
|
||||||
|
languageOptions: {
|
||||||
|
parser: tseslint.parser,
|
||||||
|
parserOptions: {
|
||||||
|
projectService: true,
|
||||||
|
warnOnUnsupportedTypeScriptVersion: false
|
||||||
|
}
|
||||||
|
},
|
||||||
|
plugins: {
|
||||||
|
"@stylistic": stylistic,
|
||||||
|
"@typescript-eslint": tseslint.plugin,
|
||||||
|
"path-alias": pathAlias,
|
||||||
|
"simple-header": simpleHeader,
|
||||||
|
"simple-import-sort": simpleImportSort,
|
||||||
|
"unused-imports": unusedImports,
|
||||||
|
},
|
||||||
|
rules: {
|
||||||
|
// Since it's only been a month and Vencord has already been stolen
|
||||||
|
// by random skids who rebranded it to "AlphaCord" and erased all license
|
||||||
|
// information
|
||||||
|
"simple-header/header": ["error", {
|
||||||
|
files: ["scripts/header-new.txt", "scripts/header-old.txt"],
|
||||||
|
templates: { author: [".*", "Vendicated and contributors"] }
|
||||||
|
}],
|
||||||
|
"@stylistic/arrow-parens": ["error", "as-needed"],
|
||||||
|
"@stylistic/block-spacing": "error",
|
||||||
|
"@stylistic/eol-last": "error",
|
||||||
|
"@stylistic/func-call-spacing": "error",
|
||||||
|
"@stylistic/indent": ["error", 4, {
|
||||||
|
// Allow both flat and indented ternary expressions
|
||||||
|
ignoredNodes: [".consequent, .alternate, .trueType, .falseType"],
|
||||||
|
SwitchCase: 1
|
||||||
|
}],
|
||||||
|
"@stylistic/jsx-quotes": "error",
|
||||||
|
"@stylistic/linebreak-style": "error",
|
||||||
|
"@stylistic/member-delimiter-style": ["error", { singleline: { requireLast: true } }],
|
||||||
|
"@stylistic/no-extra-semi": "error",
|
||||||
|
"@stylistic/no-mixed-spaces-and-tabs": "error",
|
||||||
|
"@stylistic/no-multi-spaces": "error",
|
||||||
|
"@stylistic/no-trailing-spaces": "error",
|
||||||
|
"@stylistic/no-whitespace-before-property": "error",
|
||||||
|
"@stylistic/object-curly-spacing": ["error", "always"],
|
||||||
|
"@stylistic/quotes": ["error", "double", { avoidEscape: true }],
|
||||||
|
"@stylistic/semi": "error",
|
||||||
|
"@stylistic/semi-spacing": "error",
|
||||||
|
"@stylistic/semi-style": "error",
|
||||||
|
"@stylistic/space-before-function-paren": ["error", { named: "never" }],
|
||||||
|
"@stylistic/space-in-parens": "error",
|
||||||
|
"@stylistic/spaced-comment": ["error", "always", { markers: ["!"] }],
|
||||||
|
"@typescript-eslint/array-type": "error",
|
||||||
|
"@typescript-eslint/await-thenable": "error",
|
||||||
|
"@typescript-eslint/consistent-generic-constructors": "error",
|
||||||
|
"@typescript-eslint/consistent-type-assertions": ["error", {
|
||||||
|
assertionStyle: "as",
|
||||||
|
objectLiteralTypeAssertions: "allow-as-parameter"
|
||||||
|
}],
|
||||||
|
"@typescript-eslint/consistent-type-exports": ["error", {
|
||||||
|
fixMixedExportsWithInlineTypeSpecifier: true
|
||||||
|
}],
|
||||||
|
"@typescript-eslint/consistent-type-imports": ["error", {
|
||||||
|
disallowTypeAnnotations: false,
|
||||||
|
fixStyle: "inline-type-imports"
|
||||||
|
}],
|
||||||
|
"@typescript-eslint/no-confusing-void-expression": "error",
|
||||||
|
"@typescript-eslint/no-empty-object-type": "error",
|
||||||
|
"@typescript-eslint/no-extra-non-null-assertion": "error",
|
||||||
|
"@typescript-eslint/no-import-type-side-effects": "error",
|
||||||
|
"@typescript-eslint/no-loss-of-precision": "error",
|
||||||
|
"@typescript-eslint/no-non-null-asserted-nullish-coalescing": "error",
|
||||||
|
"@typescript-eslint/no-non-null-asserted-optional-chain": "error",
|
||||||
|
"@typescript-eslint/no-unnecessary-condition": "error",
|
||||||
|
"@typescript-eslint/no-unnecessary-type-assertion": "error",
|
||||||
|
"@typescript-eslint/no-unsafe-function-type": "error",
|
||||||
|
"@typescript-eslint/no-unused-expressions": "error",
|
||||||
|
"@typescript-eslint/no-wrapper-object-types": "error",
|
||||||
|
"@typescript-eslint/non-nullable-type-assertion-style": "error",
|
||||||
|
"@typescript-eslint/prefer-as-const": "error",
|
||||||
|
"@typescript-eslint/prefer-destructuring": "error",
|
||||||
|
"@typescript-eslint/require-await": "error",
|
||||||
|
"@typescript-eslint/return-await": "error",
|
||||||
|
"dot-notation": "error",
|
||||||
|
"eqeqeq": ["error", "always", { null: "ignore" }],
|
||||||
|
"for-direction": "error",
|
||||||
|
"no-async-promise-executor": "error",
|
||||||
|
"no-cond-assign": "error",
|
||||||
|
"no-constant-condition": ["error", { checkLoops: "none" }],
|
||||||
|
"no-dupe-else-if": "error",
|
||||||
|
"no-duplicate-case": "error",
|
||||||
|
"no-duplicate-imports": "error",
|
||||||
|
"no-fallthrough": "error",
|
||||||
|
"no-invalid-regexp": "error",
|
||||||
|
"no-irregular-whitespace": "error",
|
||||||
|
"no-misleading-character-class": "error",
|
||||||
|
"no-prototype-builtins": "error",
|
||||||
|
"no-regex-spaces": "error",
|
||||||
|
"no-restricted-globals": ["error", "_", "Diff", "JSX", "React", "ReactDOM"],
|
||||||
|
"no-restricted-imports": ["error", {
|
||||||
|
patterns: [{
|
||||||
|
regex: "^discord-types(/|$)",
|
||||||
|
message: "Use @vencord/discord-types instead."
|
||||||
|
}]
|
||||||
|
}],
|
||||||
|
"no-restricted-syntax": ["error", "[operator=void]"],
|
||||||
|
"no-shadow-restricted-names": "error",
|
||||||
|
"no-unexpected-multiline": "error",
|
||||||
|
"no-unneeded-ternary": ["error", { defaultAssignment: false }],
|
||||||
|
"no-unsafe-optional-chaining": "error",
|
||||||
|
"no-useless-backreference": "error",
|
||||||
|
"no-useless-computed-key": "error",
|
||||||
|
"no-useless-escape": ["error", { extra: "i" }],
|
||||||
|
"operator-assignment": "error",
|
||||||
|
"path-alias/no-relative": "error",
|
||||||
|
"prefer-const": "error",
|
||||||
|
"prefer-object-spread": "error",
|
||||||
|
"prefer-spread": "error",
|
||||||
|
"simple-import-sort/exports": "error",
|
||||||
|
"simple-import-sort/imports": "error",
|
||||||
|
"unused-imports/no-unused-imports": "error",
|
||||||
|
"use-isnan": "error",
|
||||||
|
"yoda": "error",
|
||||||
|
}
|
||||||
|
},
|
||||||
|
);
|
28
package.json
28
package.json
|
@ -26,8 +26,8 @@
|
||||||
"generateTypes": "tspc --emitDeclarationOnly --declaration --outDir packages/vencord-types",
|
"generateTypes": "tspc --emitDeclarationOnly --declaration --outDir packages/vencord-types",
|
||||||
"inject": "node scripts/runInstaller.mjs",
|
"inject": "node scripts/runInstaller.mjs",
|
||||||
"uninject": "node scripts/runInstaller.mjs",
|
"uninject": "node scripts/runInstaller.mjs",
|
||||||
"lint": "eslint . --ext .mjs,.js,.jsx,.mts,.ts,.tsx --ignore-pattern src/userplugins",
|
"lint": "eslint . --ignore-pattern src/userplugins",
|
||||||
"lint-styles": "stylelint \"src/**/*.css\" --ignore-pattern src/userplugins --quiet-deprecation-warnings",
|
"lint-styles": "stylelint \"src/**/*.css\" --ignore-pattern src/userplugins",
|
||||||
"lint:fix": "pnpm lint --fix",
|
"lint:fix": "pnpm lint --fix",
|
||||||
"test": "pnpm buildStandalone && pnpm lint && pnpm lint-styles && pnpm testTsc && pnpm generatePluginJson",
|
"test": "pnpm buildStandalone && pnpm lint && pnpm lint-styles && pnpm testTsc && pnpm generatePluginJson",
|
||||||
"testWeb": "pnpm lint && pnpm buildWeb && pnpm testTsc",
|
"testWeb": "pnpm lint && pnpm buildWeb && pnpm testTsc",
|
||||||
|
@ -45,6 +45,9 @@
|
||||||
"virtual-merge": "^1.0.1"
|
"virtual-merge": "^1.0.1"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
"@stylistic/eslint-plugin": "^2.3.0",
|
||||||
|
"@stylistic/stylelint-config": "^1.0.1",
|
||||||
|
"@stylistic/stylelint-plugin": "^2.1.2",
|
||||||
"@types/chrome": "^0.0.268",
|
"@types/chrome": "^0.0.268",
|
||||||
"@types/diff": "^5.2.1",
|
"@types/diff": "^5.2.1",
|
||||||
"@types/html-minifier-terser": "^7.0.2",
|
"@types/html-minifier-terser": "^7.0.2",
|
||||||
|
@ -53,28 +56,26 @@
|
||||||
"@types/react": "~18.2.79",
|
"@types/react": "~18.2.79",
|
||||||
"@types/react-dom": "~18.2.25",
|
"@types/react-dom": "~18.2.25",
|
||||||
"@types/yazl": "^2.4.5",
|
"@types/yazl": "^2.4.5",
|
||||||
"@typescript-eslint/eslint-plugin": "^7.16.1",
|
|
||||||
"@typescript-eslint/parser": "^7.16.1",
|
|
||||||
"@vencord/discord-types": "workspace:^",
|
"@vencord/discord-types": "workspace:^",
|
||||||
"diff": "^5.2.0",
|
"diff": "^5.2.0",
|
||||||
"discord-types": "^1.3.3",
|
"discord-types": "^1.3.3",
|
||||||
"esbuild": "^0.23.0",
|
"esbuild": "^0.23.0",
|
||||||
"eslint": "^8.57.0",
|
"eslint": "^9.7.0",
|
||||||
"eslint-import-resolver-alias": "^1.1.2",
|
|
||||||
"eslint-plugin-path-alias": "^2.1.0",
|
"eslint-plugin-path-alias": "^2.1.0",
|
||||||
"eslint-plugin-simple-import-sort": "^12.1.1",
|
"eslint-plugin-simple-import-sort": "^12.1.1",
|
||||||
"eslint-plugin-unused-imports": "^3.2.0",
|
"eslint-plugin-unused-imports": "^4.0.0",
|
||||||
"highlight.js": "11.8.0",
|
"highlight.js": "11.8.0",
|
||||||
"html-minifier-terser": "^7.2.0",
|
"html-minifier-terser": "^7.2.0",
|
||||||
"moment": "2.22.2",
|
"moment": "2.22.2",
|
||||||
"puppeteer-core": "^22.13.0",
|
"puppeteer-core": "^22.13.0",
|
||||||
"standalone-electron-types": "^1.0.0",
|
"standalone-electron-types": "^1.0.0",
|
||||||
"stylelint": "^15.11.0",
|
"stylelint": "^16.7.0",
|
||||||
"stylelint-config-standard": "^33.0.0",
|
"stylelint-config-standard": "^36.0.1",
|
||||||
"ts-patch": "^3.2.1",
|
"ts-patch": "^3.2.1",
|
||||||
"tsx": "^4.16.2",
|
"tsx": "^4.16.2",
|
||||||
"type-fest": "^4.21.0",
|
"type-fest": "^4.21.0",
|
||||||
"typescript": "^5.5.3",
|
"typescript": "^5.5.3",
|
||||||
|
"typescript-eslint": "^8.0.0-alpha.44",
|
||||||
"typescript-transform-paths": "^3.4.7",
|
"typescript-transform-paths": "^3.4.7",
|
||||||
"zip-local": "^0.3.5"
|
"zip-local": "^0.3.5"
|
||||||
},
|
},
|
||||||
|
@ -82,13 +83,12 @@
|
||||||
"pnpm": {
|
"pnpm": {
|
||||||
"patchedDependencies": {
|
"patchedDependencies": {
|
||||||
"eslint-plugin-path-alias@2.1.0": "patches/eslint-plugin-path-alias@2.1.0.patch",
|
"eslint-plugin-path-alias@2.1.0": "patches/eslint-plugin-path-alias@2.1.0.patch",
|
||||||
"eslint@8.57.0": "patches/eslint@8.57.0.patch"
|
"eslint@9.7.0": "patches/eslint@9.7.0.patch"
|
||||||
},
|
},
|
||||||
"peerDependencyRules": {
|
"peerDependencyRules": {
|
||||||
"ignoreMissing": [
|
"allowedVersions": {
|
||||||
"eslint-plugin-import",
|
"eslint": "9"
|
||||||
"eslint"
|
}
|
||||||
]
|
|
||||||
},
|
},
|
||||||
"allowedDeprecatedVersions": {
|
"allowedDeprecatedVersions": {
|
||||||
"source-map-resolve": "*",
|
"source-map-resolve": "*",
|
||||||
|
|
|
@ -158,7 +158,7 @@ export default tseslint.config(
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
files: ["**/*"],
|
files: ["**/*"],
|
||||||
ignores: ["src/**/*"],
|
ignores: ["src/**"],
|
||||||
rules: {
|
rules: {
|
||||||
"simple-import-sort/imports": ["error", {
|
"simple-import-sort/imports": ["error", {
|
||||||
groups: [
|
groups: [
|
||||||
|
@ -169,7 +169,7 @@ export default tseslint.config(
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
files: ["scripts/**/*", "src/**/*"],
|
files: ["scripts/**", "src/**"],
|
||||||
rules: {
|
rules: {
|
||||||
"headers/header-format": ["error", {
|
"headers/header-format": ["error", {
|
||||||
source: "string",
|
source: "string",
|
||||||
|
@ -188,7 +188,7 @@ export default tseslint.config(
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
files: ["src/**/*"],
|
files: ["src/**"],
|
||||||
rules: {
|
rules: {
|
||||||
"@typescript-eslint/member-ordering": ["error", {
|
"@typescript-eslint/member-ordering": ["error", {
|
||||||
default: {
|
default: {
|
||||||
|
@ -243,7 +243,7 @@ export default tseslint.config(
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
// https://github.com/import-js/eslint-plugin-import/issues/2414
|
// https://github.com/import-js/eslint-plugin-import/issues/2414
|
||||||
files: ["src/**/*"],
|
files: ["src/**"],
|
||||||
ignores: ["src/**/index.ts"],
|
ignores: ["src/**/index.ts"],
|
||||||
rules: {
|
rules: {
|
||||||
"import/no-unused-modules": ["error", { missingExports: true }],
|
"import/no-unused-modules": ["error", { missingExports: true }],
|
||||||
|
|
1919
pnpm-lock.yaml
1919
pnpm-lock.yaml
File diff suppressed because it is too large
Load diff
|
@ -18,9 +18,7 @@
|
||||||
|
|
||||||
/* eslint-disable no-fallthrough */
|
/* eslint-disable no-fallthrough */
|
||||||
|
|
||||||
// eslint-disable-next-line spaced-comment
|
|
||||||
/// <reference types="../src/globals.d.ts" />
|
/// <reference types="../src/globals.d.ts" />
|
||||||
// eslint-disable-next-line spaced-comment
|
|
||||||
/// <reference types="../src/modules.d.ts" />
|
/// <reference types="../src/modules.d.ts" />
|
||||||
|
|
||||||
import { readFileSync } from "fs";
|
import { readFileSync } from "fs";
|
||||||
|
|
|
@ -12,7 +12,6 @@
|
||||||
"checkJs": true,
|
"checkJs": true,
|
||||||
|
|
||||||
"allowSyntheticDefaultImports": true,
|
"allowSyntheticDefaultImports": true,
|
||||||
"esModuleInterop": true,
|
|
||||||
|
|
||||||
"target": "ESNext"
|
"target": "ESNext"
|
||||||
},
|
},
|
||||||
|
|
|
@ -85,9 +85,10 @@ export function _getBadges(args: BadgeUserArgs) {
|
||||||
})
|
})
|
||||||
: [{ ...badge, ...args }];
|
: [{ ...badge, ...args }];
|
||||||
|
|
||||||
badge.position === BadgePosition.START
|
if (badge.position === BadgePosition.START)
|
||||||
? badges.unshift(...b)
|
badges.unshift(...b);
|
||||||
: badges.push(...b);
|
else
|
||||||
|
badges.push(...b);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const donorBadges = (Plugins.BadgeAPI as unknown as typeof import("../plugins/_api/badges").default).getDonorBadges(args.userId);
|
const donorBadges = (Plugins.BadgeAPI as unknown as typeof import("../plugins/_api/badges").default).getDonorBadges(args.userId);
|
||||||
|
|
|
@ -14,7 +14,7 @@ import { Button, ButtonLooks, ButtonWrapperClasses, Tooltip } from "@webpack/com
|
||||||
import type { HTMLProps, JSX, MouseEventHandler, ReactNode } from "react";
|
import type { HTMLProps, JSX, MouseEventHandler, ReactNode } from "react";
|
||||||
|
|
||||||
let ChannelTextAreaClasses: Record<"button" | "buttonContainer", string> | undefined;
|
let ChannelTextAreaClasses: Record<"button" | "buttonContainer", string> | undefined;
|
||||||
waitFor(["buttonContainer", "channelTextArea"], m => ChannelTextAreaClasses = m);
|
waitFor(["buttonContainer", "channelTextArea"], m => { ChannelTextAreaClasses = m; });
|
||||||
|
|
||||||
export interface ChatBarProps {
|
export interface ChatBarProps {
|
||||||
channel: ChannelRecord;
|
channel: ChannelRecord;
|
||||||
|
@ -24,52 +24,52 @@ export interface ChatBarProps {
|
||||||
analyticsName: string;
|
analyticsName: string;
|
||||||
attachments: boolean;
|
attachments: boolean;
|
||||||
autocomplete: {
|
autocomplete: {
|
||||||
addReactionShortcut: boolean,
|
addReactionShortcut: boolean;
|
||||||
forceChatLayer: boolean,
|
forceChatLayer: boolean;
|
||||||
reactions: boolean;
|
reactions: boolean;
|
||||||
},
|
};
|
||||||
commands: {
|
commands: {
|
||||||
enabled: boolean;
|
enabled: boolean;
|
||||||
},
|
};
|
||||||
drafts: {
|
drafts: {
|
||||||
type: number,
|
type: number;
|
||||||
commandType: number,
|
commandType: number;
|
||||||
autoSave: boolean;
|
autoSave: boolean;
|
||||||
},
|
};
|
||||||
emojis: {
|
emojis: {
|
||||||
button: boolean;
|
button: boolean;
|
||||||
},
|
};
|
||||||
gifs: {
|
gifs: {
|
||||||
button: boolean,
|
button: boolean;
|
||||||
allowSending: boolean;
|
allowSending: boolean;
|
||||||
},
|
};
|
||||||
gifts: {
|
gifts: {
|
||||||
button: boolean;
|
button: boolean;
|
||||||
},
|
};
|
||||||
permissions: {
|
permissions: {
|
||||||
requireSendMessages: boolean;
|
requireSendMessages: boolean;
|
||||||
},
|
};
|
||||||
showThreadPromptOnReply: boolean,
|
showThreadPromptOnReply: boolean;
|
||||||
stickers: {
|
stickers: {
|
||||||
button: boolean,
|
button: boolean;
|
||||||
allowSending: boolean,
|
allowSending: boolean;
|
||||||
autoSuggest: boolean;
|
autoSuggest: boolean;
|
||||||
},
|
};
|
||||||
users: {
|
users: {
|
||||||
allowMentioning: boolean;
|
allowMentioning: boolean;
|
||||||
},
|
};
|
||||||
submit: {
|
submit: {
|
||||||
button: boolean,
|
button: boolean;
|
||||||
ignorePreference: boolean,
|
ignorePreference: boolean;
|
||||||
disableEnterToSubmit: boolean,
|
disableEnterToSubmit: boolean;
|
||||||
clearOnSubmit: boolean,
|
clearOnSubmit: boolean;
|
||||||
useDisabledStylesOnSubmit: boolean;
|
useDisabledStylesOnSubmit: boolean;
|
||||||
},
|
};
|
||||||
uploadLongMessages: boolean,
|
uploadLongMessages: boolean;
|
||||||
upsellLongMessages: {
|
upsellLongMessages: {
|
||||||
iconOnly: boolean;
|
iconOnly: boolean;
|
||||||
},
|
};
|
||||||
showCharacterCount: boolean,
|
showCharacterCount: boolean;
|
||||||
sedReplace: boolean;
|
sedReplace: boolean;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -42,7 +42,7 @@ interface DecoratorProps {
|
||||||
export type Decorator = (props: DecoratorProps) => JSX.Element | null;
|
export type Decorator = (props: DecoratorProps) => JSX.Element | null;
|
||||||
type OnlyIn = "guilds" | "dms";
|
type OnlyIn = "guilds" | "dms";
|
||||||
|
|
||||||
export const decorators = new Map<string, { decorator: Decorator, onlyIn?: OnlyIn; }>();
|
export const decorators = new Map<string, { decorator: Decorator; onlyIn?: OnlyIn; }>();
|
||||||
|
|
||||||
export function addDecorator(identifier: string, decorator: Decorator, onlyIn?: OnlyIn) {
|
export function addDecorator(identifier: string, decorator: Decorator, onlyIn?: OnlyIn) {
|
||||||
decorators.set(identifier, { decorator, onlyIn });
|
decorators.set(identifier, { decorator, onlyIn });
|
||||||
|
|
|
@ -24,7 +24,7 @@ import type { Promisable } from "type-fest";
|
||||||
const MessageEventsLogger = new Logger("MessageEvents", "#e5c890");
|
const MessageEventsLogger = new Logger("MessageEvents", "#e5c890");
|
||||||
|
|
||||||
export interface MessageObject {
|
export interface MessageObject {
|
||||||
content: string,
|
content: string;
|
||||||
validNonShortcutEmojis: GuildEmoji[];
|
validNonShortcutEmojis: GuildEmoji[];
|
||||||
invalidEmojis: any[];
|
invalidEmojis: any[];
|
||||||
tts: boolean;
|
tts: boolean;
|
||||||
|
|
|
@ -19,7 +19,7 @@
|
||||||
import { waitFor } from "@webpack";
|
import { waitFor } from "@webpack";
|
||||||
|
|
||||||
let NoticesModule: any;
|
let NoticesModule: any;
|
||||||
waitFor(m => m.show && m.dismiss && !m.suppressAll, m => NoticesModule = m);
|
waitFor(m => m.show && m.dismiss && !m.suppressAll, m => { NoticesModule = m; });
|
||||||
|
|
||||||
export const noticesQueue: any[] = [];
|
export const noticesQueue: any[] = [];
|
||||||
export let currentNotice: any = null;
|
export let currentNotice: any = null;
|
||||||
|
|
|
@ -136,7 +136,7 @@ function NotificationEntry({ data }: { data: PersistentNotificationData; }) {
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
export function NotificationLog({ log, pending }: { log: PersistentNotificationData[], pending: boolean; }) {
|
export function NotificationLog({ log, pending }: { log: PersistentNotificationData[]; pending: boolean; }) {
|
||||||
if (!log.length && !pending)
|
if (!log.length && !pending)
|
||||||
return (
|
return (
|
||||||
<div className={cl("container")}>
|
<div className={cl("container")}>
|
||||||
|
|
|
@ -30,7 +30,7 @@ import plugins from "~plugins";
|
||||||
const logger = new Logger("Settings");
|
const logger = new Logger("Settings");
|
||||||
export interface Settings {
|
export interface Settings {
|
||||||
autoUpdate: boolean;
|
autoUpdate: boolean;
|
||||||
autoUpdateNotification: boolean,
|
autoUpdateNotification: boolean;
|
||||||
useQuickCss: boolean;
|
useQuickCss: boolean;
|
||||||
enableReactDevtools: boolean;
|
enableReactDevtools: boolean;
|
||||||
themeLinks: string[];
|
themeLinks: string[];
|
||||||
|
@ -250,11 +250,12 @@ export function definePluginSettings<
|
||||||
type UseSettings<T extends object> = ResolveUseSettings<T>[keyof T];
|
type UseSettings<T extends object> = ResolveUseSettings<T>[keyof T];
|
||||||
|
|
||||||
type ResolveUseSettings<T extends object> = {
|
type ResolveUseSettings<T extends object> = {
|
||||||
[Key in keyof T]:
|
[Key in keyof T]: Key extends string
|
||||||
Key extends string
|
? T[Key] extends Record<string, unknown>
|
||||||
? T[Key] extends Record<string, unknown>
|
? UseSettings<T[Key]> extends string
|
||||||
// @ts-ignore "Type instantiation is excessively deep and possibly infinite"
|
// @ts-ignore "Type instantiation is excessively deep and possibly infinite"
|
||||||
? UseSettings<T[Key]> extends string ? `${Key}.${UseSettings<T[Key]>}` : never
|
? `${Key}.${UseSettings<T[Key]>}`
|
||||||
: Key
|
: never
|
||||||
: never;
|
: Key
|
||||||
|
: never;
|
||||||
};
|
};
|
||||||
|
|
|
@ -12,7 +12,7 @@ const CodeContainerClasses: Record<string, string> = findByPropsLazy("markup", "
|
||||||
/**
|
/**
|
||||||
* Renders code in a Discord codeblock
|
* Renders code in a Discord codeblock
|
||||||
*/
|
*/
|
||||||
export const CodeBlock = (props: { content?: string, lang: string; }) => (
|
export const CodeBlock = (props: { content?: string; lang: string; }) => (
|
||||||
<div className={CodeContainerClasses.markup}>
|
<div className={CodeContainerClasses.markup}>
|
||||||
{MarkupUtils.defaultRules.codeBlock!.react(props, null, {})}
|
{MarkupUtils.defaultRules.codeBlock!.react(props, null, {})}
|
||||||
</div>
|
</div>
|
||||||
|
|
|
@ -30,7 +30,7 @@ interface Props<T = any> {
|
||||||
/** Fallback component to render if an error occurs */
|
/** Fallback component to render if an error occurs */
|
||||||
fallback?: ComponentType<PropsWithChildren<{ error: any; message: string; stack: string; }>>;
|
fallback?: ComponentType<PropsWithChildren<{ error: any; message: string; stack: string; }>>;
|
||||||
/** called when an error occurs. The props property is only available if using .wrap */
|
/** called when an error occurs. The props property is only available if using .wrap */
|
||||||
onError?(data: { error: Error, errorInfo: ErrorInfo, props: T; }): void;
|
onError?(data: { error: Error; errorInfo: ErrorInfo; props: T; }): void;
|
||||||
/** Custom error message */
|
/** Custom error message */
|
||||||
message?: string;
|
message?: string;
|
||||||
|
|
||||||
|
|
|
@ -3,7 +3,7 @@
|
||||||
width: 32px;
|
width: 32px;
|
||||||
border-radius: 50%;
|
border-radius: 50%;
|
||||||
border: 4px solid var(--background-tertiary);
|
border: 4px solid var(--background-tertiary);
|
||||||
box-sizing: border-box
|
box-sizing: border-box;
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-settings-modal-links {
|
.vc-settings-modal-links {
|
||||||
|
|
|
@ -190,7 +190,12 @@ function ReplacementInput({ replacement, setReplacement, replacementError }: Rep
|
||||||
}
|
}
|
||||||
|
|
||||||
useEffect(
|
useEffect(
|
||||||
() => { (isFunc ? onChange(replacement) : setError(undefined)); },
|
() => {
|
||||||
|
if (isFunc)
|
||||||
|
onChange(replacement);
|
||||||
|
else
|
||||||
|
setError(undefined);
|
||||||
|
},
|
||||||
[isFunc]
|
[isFunc]
|
||||||
);
|
);
|
||||||
|
|
||||||
|
|
|
@ -134,8 +134,10 @@ const ThemeCard = ({ theme, enabled, onChange, onDelete }: ThemeCardProps) => (
|
||||||
href={`https://discord.gg/${theme.invite}`}
|
href={`https://discord.gg/${theme.invite}`}
|
||||||
onClick={e => {
|
onClick={e => {
|
||||||
e.preventDefault();
|
e.preventDefault();
|
||||||
theme.invite != null && openInviteModal(theme.invite)
|
if (theme.invite != null)
|
||||||
.catch(() => { showToast("Invalid or expired invite"); });
|
openInviteModal(theme.invite).catch(() => {
|
||||||
|
showToast("Invalid or expired invite");
|
||||||
|
});
|
||||||
}}
|
}}
|
||||||
>
|
>
|
||||||
Discord Server
|
Discord Server
|
||||||
|
|
|
@ -77,7 +77,7 @@ interface CommonProps {
|
||||||
repoPending: boolean;
|
repoPending: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
const HashLink = ({ repo, hash, disabled = false }: { repo: string, hash: string, disabled?: boolean; }) => (
|
const HashLink = ({ repo, hash, disabled = false }: { repo: string; hash: string; disabled?: boolean; }) => (
|
||||||
<Link href={`${repo}/commit/${hash}`} disabled={disabled}>
|
<Link href={`${repo}/commit/${hash}`} disabled={disabled}>
|
||||||
{hash}
|
{hash}
|
||||||
</Link>
|
</Link>
|
||||||
|
|
|
@ -51,7 +51,7 @@ if (!IS_VANILLA) {
|
||||||
const originalBuild = Menu.buildFromTemplate;
|
const originalBuild = Menu.buildFromTemplate;
|
||||||
Menu.buildFromTemplate = function (template) {
|
Menu.buildFromTemplate = function (template) {
|
||||||
if (template[0]?.label === "&File") {
|
if (template[0]?.label === "&File") {
|
||||||
const { submenu } = template[0];
|
const [{ submenu }] = template;
|
||||||
if (Array.isArray(submenu)) {
|
if (Array.isArray(submenu)) {
|
||||||
submenu.push({
|
submenu.push({
|
||||||
label: "Quit (Hidden)",
|
label: "Quit (Hidden)",
|
||||||
|
|
1
src/modules.d.ts
vendored
1
src/modules.d.ts
vendored
|
@ -16,7 +16,6 @@
|
||||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// eslint-disable-next-line spaced-comment
|
|
||||||
/// <reference types="standalone-electron-types"/>
|
/// <reference types="standalone-electron-types"/>
|
||||||
|
|
||||||
declare module "~plugins" {
|
declare module "~plugins" {
|
||||||
|
|
|
@ -49,9 +49,9 @@ interface RemoteData {
|
||||||
artistArtwork?: string;
|
artistArtwork?: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
let cachedRemoteData: { id: string, data: RemoteData; } | { id: string, failures: number; } | null = null;
|
let cachedRemoteData: { id: string; data: RemoteData; } | { id: string; failures: number; } | null = null;
|
||||||
|
|
||||||
async function fetchRemoteData({ id, name, artist, album }: { id: string, name: string, artist: string, album: string; }) {
|
async function fetchRemoteData({ id, name, artist, album }: { id: string; name: string; artist: string; album: string; }) {
|
||||||
if (id === cachedRemoteData?.id) {
|
if (id === cachedRemoteData?.id) {
|
||||||
if ("data" in cachedRemoteData) return cachedRemoteData.data;
|
if ("data" in cachedRemoteData) return cachedRemoteData.data;
|
||||||
if ("failures" in cachedRemoteData && cachedRemoteData.failures >= 5) return null;
|
if ("failures" in cachedRemoteData && cachedRemoteData.failures >= 5) return null;
|
||||||
|
|
|
@ -11,7 +11,7 @@ import type { Dispatch, SetStateAction } from "react";
|
||||||
import type { Session } from "../types";
|
import type { Session } from "../types";
|
||||||
import { RenameModal } from "./RenameModal";
|
import { RenameModal } from "./RenameModal";
|
||||||
|
|
||||||
export const RenameButton = ({ session, state }: { session: Session, state: [string, Dispatch<SetStateAction<string>>]; }) => (
|
export const RenameButton = ({ session, state }: { session: Session; state: [string, Dispatch<SetStateAction<string>>]; }) => (
|
||||||
<Button
|
<Button
|
||||||
look={Button.Looks.LINK}
|
look={Button.Looks.LINK}
|
||||||
color={Button.Colors.LINK}
|
color={Button.Colors.LINK}
|
||||||
|
|
|
@ -23,7 +23,7 @@ import type { Dispatch, KeyboardEvent, SetStateAction } from "react";
|
||||||
import type { Session } from "../types";
|
import type { Session } from "../types";
|
||||||
import { getDefaultName, savedSessionsCache, saveSessionsToDataStore } from "../utils";
|
import { getDefaultName, savedSessionsCache, saveSessionsToDataStore } from "../utils";
|
||||||
|
|
||||||
export function RenameModal({ props, session, state }: { props: ModalProps, session: Session, state: [string, Dispatch<SetStateAction<string>>]; }) {
|
export function RenameModal({ props, session, state }: { props: ModalProps; session: Session; state: [string, Dispatch<SetStateAction<string>>]; }) {
|
||||||
const [title, setTitle] = state;
|
const [title, setTitle] = state;
|
||||||
const [value, setValue] = useState(savedSessionsCache.get(session.id_hash)?.name ?? "");
|
const [value, setValue] = useState(savedSessionsCache.get(session.id_hash)?.name ?? "");
|
||||||
|
|
||||||
|
|
|
@ -107,7 +107,7 @@ export default definePlugin({
|
||||||
);
|
);
|
||||||
}, { noop: true }),
|
}, { noop: true }),
|
||||||
|
|
||||||
renderTimestamp: ErrorBoundary.wrap(({ session, timeLabel }: { session: Session, timeLabel: string; }) => (
|
renderTimestamp: ErrorBoundary.wrap(({ session, timeLabel }: { session: Session; timeLabel: string; }) => (
|
||||||
<Tooltip
|
<Tooltip
|
||||||
text={session.approx_last_used_time.toLocaleString()}
|
text={session.approx_last_used_time.toLocaleString()}
|
||||||
tooltipClassName={TimestampClasses.timestampTooltip}
|
tooltipClassName={TimestampClasses.timestampTooltip}
|
||||||
|
@ -120,7 +120,7 @@ export default definePlugin({
|
||||||
</Tooltip>
|
</Tooltip>
|
||||||
), { noop: true }),
|
), { noop: true }),
|
||||||
|
|
||||||
renderIcon: ErrorBoundary.wrap(({ session, DeviceIcon }: { session: Session, DeviceIcon: ComponentType<any>; }) => {
|
renderIcon: ErrorBoundary.wrap(({ session, DeviceIcon }: { session: Session; DeviceIcon: ComponentType<any>; }) => {
|
||||||
const PlatformIcon = GetPlatformIcon(session.client_info.platform);
|
const PlatformIcon = GetPlatformIcon(session.client_info.platform);
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|
|
@ -25,7 +25,7 @@ export interface SessionInfo {
|
||||||
platform: string;
|
platform: string;
|
||||||
location: string;
|
location: string;
|
||||||
};
|
};
|
||||||
},
|
};
|
||||||
current?: boolean;
|
current?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -17,7 +17,7 @@ type SettingsEntry = { section: string; label: string; };
|
||||||
|
|
||||||
const cl = classNameFactory("");
|
const cl = classNameFactory("");
|
||||||
let Classes: Record<string, string>;
|
let Classes: Record<string, string>;
|
||||||
waitFor(["animating", "baseLayer", "bg", "layer", "layers"], m => Classes = m);
|
waitFor(["animating", "baseLayer", "bg", "layer", "layers"], m => { Classes = m; });
|
||||||
|
|
||||||
const settings = definePluginSettings({
|
const settings = definePluginSettings({
|
||||||
disableFade: {
|
disableFade: {
|
||||||
|
|
|
@ -36,14 +36,14 @@ export interface Stream extends ApplicationStream {
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface RTCStream {
|
export interface RTCStream {
|
||||||
region: string,
|
region: string;
|
||||||
streamKey: string,
|
streamKey: string;
|
||||||
viewerIds: string[];
|
viewerIds: string[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface StreamMetadata {
|
export interface StreamMetadata {
|
||||||
id: string | null,
|
id: string | null;
|
||||||
pid: number | null,
|
pid: number | null;
|
||||||
sourceName: string | null;
|
sourceName: string | null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -26,7 +26,7 @@
|
||||||
.client-theme-contrast-warning {
|
.client-theme-contrast-warning {
|
||||||
background-color: var(--background-primary);
|
background-color: var(--background-primary);
|
||||||
padding: 0.5rem;
|
padding: 0.5rem;
|
||||||
border-radius: .5rem;
|
border-radius: 0.5rem;
|
||||||
display: flex;
|
display: flex;
|
||||||
flex-direction: row;
|
flex-direction: row;
|
||||||
justify-content: space-between;
|
justify-content: space-between;
|
||||||
|
|
|
@ -55,7 +55,7 @@ export default definePlugin({
|
||||||
settings,
|
settings,
|
||||||
|
|
||||||
contextMenus: {
|
contextMenus: {
|
||||||
"expression-picker"(children, { target }: { target: Target }) {
|
"expression-picker"(children, { target }: { target: Target; }) {
|
||||||
if (target.dataset.type !== "emoji") return;
|
if (target.dataset.type !== "emoji") return;
|
||||||
|
|
||||||
children.push(
|
children.push(
|
||||||
|
|
|
@ -2,7 +2,8 @@
|
||||||
filter: grayscale(1);
|
filter: grayscale(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-dearrow-toggle-on, .vc-dearrow-toggle-off {
|
.vc-dearrow-toggle-on,
|
||||||
|
.vc-dearrow-toggle-off {
|
||||||
all: unset;
|
all: unset;
|
||||||
display: inline;
|
display: inline;
|
||||||
cursor: pointer;
|
cursor: pointer;
|
||||||
|
|
|
@ -31,7 +31,7 @@ interface UsersDecorationsState {
|
||||||
|
|
||||||
export const useUsersDecorationsStore: {
|
export const useUsersDecorationsStore: {
|
||||||
(): UsersDecorationsState;
|
(): UsersDecorationsState;
|
||||||
getState: () => UsersDecorationsState
|
getState: () => UsersDecorationsState;
|
||||||
subscribe: (handler: (state: UsersDecorationsState) => void) => () => void;
|
subscribe: (handler: (state: UsersDecorationsState) => void) => () => void;
|
||||||
} = proxyLazy(() => zustandCreate((set: any, get: any): UsersDecorationsState => ({
|
} = proxyLazy(() => zustandCreate((set: any, get: any): UsersDecorationsState => ({
|
||||||
usersDecorations: new Map<string, UserDecorationData>(),
|
usersDecorations: new Map<string, UserDecorationData>(),
|
||||||
|
|
|
@ -10,8 +10,8 @@ import { React } from "@webpack/common";
|
||||||
import type { ComponentType, HTMLProps, PropsWithChildren } from "react";
|
import type { ComponentType, HTMLProps, PropsWithChildren } from "react";
|
||||||
|
|
||||||
type DecorationGridItemComponent = ComponentType<PropsWithChildren<HTMLProps<HTMLDivElement>> & {
|
type DecorationGridItemComponent = ComponentType<PropsWithChildren<HTMLProps<HTMLDivElement>> & {
|
||||||
onSelect: () => void,
|
onSelect: () => void;
|
||||||
isSelected: boolean,
|
isSelected: boolean;
|
||||||
}>;
|
}>;
|
||||||
|
|
||||||
export let DecorationGridItem: DecorationGridItemComponent;
|
export let DecorationGridItem: DecorationGridItemComponent;
|
||||||
|
@ -24,8 +24,8 @@ export const AvatarDecorationModalPreview = LazyComponentWebpack(() => {
|
||||||
|
|
||||||
type DecorationGridDecorationComponent = ComponentType<HTMLProps<HTMLDivElement> & {
|
type DecorationGridDecorationComponent = ComponentType<HTMLProps<HTMLDivElement> & {
|
||||||
avatarDecoration: AvatarDecorationData;
|
avatarDecoration: AvatarDecorationData;
|
||||||
onSelect: () => void,
|
onSelect: () => void;
|
||||||
isSelected: boolean,
|
isSelected: boolean;
|
||||||
}>;
|
}>;
|
||||||
|
|
||||||
export let DecorationGridDecoration: DecorationGridDecorationComponent;
|
export let DecorationGridDecoration: DecorationGridDecorationComponent;
|
||||||
|
|
|
@ -98,11 +98,12 @@ function initWs(isManual = false) {
|
||||||
|
|
||||||
logger.info("Connected to WebSocket");
|
logger.info("Connected to WebSocket");
|
||||||
|
|
||||||
(settings.store.notifyOnAutoConnect || isManual) && showNotification({
|
if (settings.store.notifyOnAutoConnect || isManual)
|
||||||
title: "Dev Companion Connected",
|
showNotification({
|
||||||
body: "Connected to WebSocket",
|
title: "Dev Companion Connected",
|
||||||
noPersist: true
|
body: "Connected to WebSocket",
|
||||||
});
|
noPersist: true
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
ws.addEventListener("error", e => {
|
ws.addEventListener("error", e => {
|
||||||
|
|
|
@ -153,7 +153,7 @@ async function doClone(guildId: string, data: Data) {
|
||||||
} catch (e: any) {
|
} catch (e: any) {
|
||||||
let message = "Something went wrong (check console!)";
|
let message = "Something went wrong (check console!)";
|
||||||
try {
|
try {
|
||||||
message = JSON.parse(e.text).message;
|
({ message } = JSON.parse(e.text));
|
||||||
} catch { }
|
} catch { }
|
||||||
|
|
||||||
new Logger("EmoteCloner").error("Failed to clone", data.name, "to", guildId, e);
|
new Logger("EmoteCloner").error("Failed to clone", data.name, "to", guildId, e);
|
||||||
|
|
|
@ -426,8 +426,8 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
|
|
||||||
handleGradientThemeSelect(backgroundGradientPresetId: number | undefined, theme: number, original: () => void) {
|
handleGradientThemeSelect(backgroundGradientPresetId: number | undefined, theme: number, original: () => void) {
|
||||||
const premiumType = UserStore.getCurrentUser()?.premiumType ?? 0;
|
const premiumType = UserStore.getCurrentUser()?.premiumType;
|
||||||
if (premiumType === 2 || backgroundGradientPresetId == null) {
|
if (premiumType === UserPremiumType.TIER_2 || backgroundGradientPresetId == null) {
|
||||||
original();
|
original();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -466,37 +466,41 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
|
|
||||||
trimContent(content: any[]) {
|
trimContent(content: any[]) {
|
||||||
const firstContent = content[0];
|
const [firstContent] = content;
|
||||||
if (typeof firstContent === "string") {
|
if (typeof firstContent === "string") {
|
||||||
content[0] = firstContent.trimStart();
|
content[0] = firstContent.trimStart();
|
||||||
content[0] || content.shift();
|
if (!content[0]) content.shift();
|
||||||
} else if (typeof firstContent?.props?.children === "string") {
|
} else if (typeof firstContent?.props?.children === "string") {
|
||||||
firstContent.props.children = firstContent.props.children.trimStart();
|
firstContent.props.children = firstContent.props.children.trimStart();
|
||||||
firstContent.props.children || content.shift();
|
if (!firstContent.props.children) content.shift();
|
||||||
}
|
}
|
||||||
|
|
||||||
const lastIndex = content.length - 1;
|
const lastIndex = content.length - 1;
|
||||||
const lastContent = content[lastIndex];
|
const lastContent = content[lastIndex];
|
||||||
if (typeof lastContent === "string") {
|
if (typeof lastContent === "string") {
|
||||||
content[lastIndex] = lastContent.trimEnd();
|
content[lastIndex] = lastContent.trimEnd();
|
||||||
content[lastIndex] || content.pop();
|
if (!content[lastIndex]) content.pop();
|
||||||
} else if (typeof lastContent?.props?.children === "string") {
|
} else if (typeof lastContent?.props?.children === "string") {
|
||||||
lastContent.props.children = lastContent.props.children.trimEnd();
|
lastContent.props.children = lastContent.props.children.trimEnd();
|
||||||
lastContent.props.children || content.pop();
|
if (!lastContent.props.children) content.pop();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
clearEmptyArrayItems(array: any[]) {
|
clearEmptyArrayItems<T>(array: T[]) {
|
||||||
return array.filter(item => item != null);
|
return array.filter(item => item != null);
|
||||||
},
|
},
|
||||||
|
|
||||||
ensureChildrenIsArray(child: ReactElement) {
|
ensureChildrenIsArray(child: ReactElement) {
|
||||||
if (!Array.isArray(child.props.children)) child.props.children = [child.props.children];
|
if (!Array.isArray(child.props.children))
|
||||||
|
child.props.children = [child.props.children];
|
||||||
},
|
},
|
||||||
|
|
||||||
patchFakeNitroEmojisOrRemoveStickersLinks(content: any[], inline: boolean) {
|
patchFakeNitroEmojisOrRemoveStickersLinks(content: any[], inline: boolean) {
|
||||||
// If content has more than one child or it's a single ReactElement like a header, list or span
|
// If content has more than one child or it's a single ReactElement like a header, list or span
|
||||||
if ((content.length > 1 || typeof content[0]?.type === "string") && !settings.store.transformCompoundSentence) return content;
|
if (
|
||||||
|
(content.length > 1 || typeof content[0]?.type === "string")
|
||||||
|
&& !settings.store.transformCompoundSentence
|
||||||
|
) return content;
|
||||||
|
|
||||||
let nextIndex = content.length;
|
let nextIndex = content.length;
|
||||||
|
|
||||||
|
@ -509,7 +513,8 @@ export default definePlugin({
|
||||||
url = new URL(child.props.href);
|
url = new URL(child.props.href);
|
||||||
} catch { }
|
} catch { }
|
||||||
|
|
||||||
const emojiName = EmojiStore.getCustomEmojiById(fakeNitroMatch[1])?.name ?? url?.searchParams.get("name") ?? "FakeNitroEmoji";
|
const emojiName = EmojiStore.getCustomEmojiById(fakeNitroMatch[1])?.name
|
||||||
|
?? url?.searchParams.get("name") ?? "FakeNitroEmoji";
|
||||||
|
|
||||||
return MarkupUtils.defaultRules.customEmoji!.react({
|
return MarkupUtils.defaultRules.customEmoji!.react({
|
||||||
jumboable: !inline && content.length === 1 && typeof content[0].type !== "string",
|
jumboable: !inline && content.length === 1 && typeof content[0].type !== "string",
|
||||||
|
@ -603,10 +608,16 @@ export default definePlugin({
|
||||||
if (settings.store.transformCompoundSentence) itemsToMaybePush.push(...contentItems);
|
if (settings.store.transformCompoundSentence) itemsToMaybePush.push(...contentItems);
|
||||||
else if (contentItems.length === 1) itemsToMaybePush.push(contentItems[0]!);
|
else if (contentItems.length === 1) itemsToMaybePush.push(contentItems[0]!);
|
||||||
|
|
||||||
itemsToMaybePush.push(...message.attachments.filter(attachment => attachment.content_type === "image/gif").map(attachment => attachment.url));
|
itemsToMaybePush.push(...message.attachments
|
||||||
|
.filter(attachment => attachment.content_type === "image/gif")
|
||||||
|
.map(attachment => attachment.url));
|
||||||
|
|
||||||
for (const item of itemsToMaybePush) {
|
for (const item of itemsToMaybePush) {
|
||||||
if (!settings.store.transformCompoundSentence && !item.startsWith("http") && !hyperLinkRegex.test(item)) continue;
|
if (
|
||||||
|
!settings.store.transformCompoundSentence
|
||||||
|
&& !item.startsWith("http")
|
||||||
|
&& !hyperLinkRegex.test(item)
|
||||||
|
) continue;
|
||||||
|
|
||||||
const imgMatch = item.match(fakeNitroStickerRegex);
|
const imgMatch = item.match(fakeNitroStickerRegex);
|
||||||
if (imgMatch) {
|
if (imgMatch) {
|
||||||
|
@ -615,7 +626,8 @@ export default definePlugin({
|
||||||
url = new URL(item);
|
url = new URL(item);
|
||||||
} catch { }
|
} catch { }
|
||||||
|
|
||||||
const stickerName = StickerStore.getStickerById(imgMatch[1]!)?.name ?? url?.searchParams.get("name") ?? "FakeNitroSticker";
|
const stickerName = StickerStore.getStickerById(imgMatch[1]!)?.name
|
||||||
|
?? url?.searchParams.get("name") ?? "FakeNitroSticker";
|
||||||
stickers.push({
|
stickers.push({
|
||||||
format_type: StickerFormat.PNG,
|
format_type: StickerFormat.PNG,
|
||||||
id: imgMatch[1],
|
id: imgMatch[1],
|
||||||
|
@ -693,19 +705,19 @@ export default definePlugin({
|
||||||
return link.target && fakeNitroEmojiRegex.test(link.target);
|
return link.target && fakeNitroEmojiRegex.test(link.target);
|
||||||
},
|
},
|
||||||
|
|
||||||
addFakeNotice(type: FakeNoticeType, node: ReactNode[], fake: boolean) {
|
addFakeNotice(type: FakeNoticeType, node: ReactNode, fake: boolean) {
|
||||||
if (!fake) return node;
|
if (!fake) return node;
|
||||||
|
|
||||||
node = Array.isArray(node) ? node : [node];
|
const nodeArray: ReactNode[] = Array.isArray(node) ? node : [node];
|
||||||
|
|
||||||
switch (type) {
|
switch (type) {
|
||||||
case FakeNoticeType.Sticker: {
|
case FakeNoticeType.Sticker: {
|
||||||
node.push(" This is a FakeNitro sticker and renders like a real sticker only for you. Appears as a link to non-plugin users.");
|
nodeArray.push(" This is a FakeNitro sticker and renders like a real sticker only for you. Appears as a link to non-plugin users.");
|
||||||
|
|
||||||
return node;
|
return node;
|
||||||
}
|
}
|
||||||
case FakeNoticeType.Emoji: {
|
case FakeNoticeType.Emoji: {
|
||||||
node.push(" This is a FakeNitro emoji and renders like a real emoji only for you. Appears as a link to non-plugin users.");
|
nodeArray.push(" This is a FakeNitro emoji and renders like a real emoji only for you. Appears as a link to non-plugin users.");
|
||||||
|
|
||||||
return node;
|
return node;
|
||||||
}
|
}
|
||||||
|
|
|
@ -53,10 +53,10 @@ interface Instance {
|
||||||
resultType?: string;
|
resultType?: string;
|
||||||
};
|
};
|
||||||
props: {
|
props: {
|
||||||
favCopy: Gif[],
|
favCopy: Gif[];
|
||||||
|
|
||||||
favorites: Gif[],
|
favorites: Gif[];
|
||||||
},
|
};
|
||||||
forceUpdate: () => void;
|
forceUpdate: () => void;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -34,7 +34,7 @@ export default definePlugin({
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
isGuildOwner(props: { user?: UserRecord, channel?: ChannelRecord, isOwner: boolean, guildId?: string; }) {
|
isGuildOwner(props: { user?: UserRecord; channel?: ChannelRecord; isOwner: boolean; guildId?: string; }) {
|
||||||
if (!props.user?.id) return props.isOwner;
|
if (!props.user?.id) return props.isOwner;
|
||||||
if (props.channel?.type === ChannelType.GROUP_DM)
|
if (props.channel?.type === ChannelType.GROUP_DM)
|
||||||
return props.isOwner;
|
return props.isOwner;
|
||||||
|
|
|
@ -70,7 +70,7 @@ function greet(channel: ChannelRecord, message: MessageRecord, stickers: string[
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function GreetMenu({ channel, message }: { message: MessageRecord, channel: ChannelRecord; }) {
|
function GreetMenu({ channel, message }: { message: MessageRecord; channel: ChannelRecord; }) {
|
||||||
const s = settings.use(["greetMode", "multiGreetChoices"]);
|
const s = settings.use(["greetMode", "multiGreetChoices"]);
|
||||||
const { greetMode, multiGreetChoices = [] } = s;
|
const { greetMode, multiGreetChoices = [] } = s;
|
||||||
|
|
||||||
|
@ -172,7 +172,7 @@ export default definePlugin({
|
||||||
pickSticker(
|
pickSticker(
|
||||||
event: UIEvent,
|
event: UIEvent,
|
||||||
props: {
|
props: {
|
||||||
channel: ChannelRecord,
|
channel: ChannelRecord;
|
||||||
message: MessageRecord & { deleted?: boolean; };
|
message: MessageRecord & { deleted?: boolean; };
|
||||||
}
|
}
|
||||||
) {
|
) {
|
||||||
|
|
|
@ -303,7 +303,7 @@ export default definePlugin({
|
||||||
return true;
|
return true;
|
||||||
},
|
},
|
||||||
|
|
||||||
renderToggleGameActivityButton: (props: { id?: string; name: string, exePath: string; }, nowPlaying: boolean) => (
|
renderToggleGameActivityButton: (props: { id?: string; name: string; exePath: string; }, nowPlaying: boolean) => (
|
||||||
<ErrorBoundary noop>
|
<ErrorBoundary noop>
|
||||||
<div style={{ marginLeft: 12, zIndex: 0 }}>
|
<div style={{ marginLeft: 12, zIndex: 0 }}>
|
||||||
{ToggleActivityComponent({ id: props.id ?? props.exePath, name: props.name, type: ActivitiesTypes.Game }, nowPlaying)}
|
{ToggleActivityComponent({ id: props.id ?? props.exePath, name: props.name, type: ActivitiesTypes.Game }, nowPlaying)}
|
||||||
|
|
|
@ -25,13 +25,13 @@ import { settings } from "../index";
|
||||||
import { waitFor } from "../utils/waitFor";
|
import { waitFor } from "../utils/waitFor";
|
||||||
|
|
||||||
interface Vec2 {
|
interface Vec2 {
|
||||||
x: number,
|
x: number;
|
||||||
y: number;
|
y: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface MagnifierProps {
|
export interface MagnifierProps {
|
||||||
zoom: number;
|
zoom: number;
|
||||||
size: number,
|
size: number;
|
||||||
instance: any;
|
instance: any;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -261,7 +261,7 @@ export default definePlugin({
|
||||||
stop() {
|
stop() {
|
||||||
disableStyle(styles);
|
disableStyle(styles);
|
||||||
// so componenetWillUnMount gets called if Magnifier component is still alive
|
// so componenetWillUnMount gets called if Magnifier component is still alive
|
||||||
this.root && this.root.unmount();
|
if (this.root) this.root.unmount();
|
||||||
this.element?.remove();
|
this.element?.remove();
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
border-radius: 0;
|
border-radius: 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-imgzoom-nearest-neighbor>img {
|
.vc-imgzoom-nearest-neighbor > img {
|
||||||
image-rendering: pixelated;
|
image-rendering: pixelated;
|
||||||
|
|
||||||
/* https://googlechrome.github.io/samples/image-rendering-pixelated/index.html */
|
/* https://googlechrome.github.io/samples/image-rendering-pixelated/index.html */
|
||||||
|
|
|
@ -40,7 +40,7 @@ export const OnlineMemberCountStore = proxyLazy(() => {
|
||||||
}
|
}
|
||||||
|
|
||||||
return new OnlineMemberCountStore(FluxDispatcher, {
|
return new OnlineMemberCountStore(FluxDispatcher, {
|
||||||
GUILD_MEMBER_LIST_UPDATE({ guildId, groups }: { guildId: string, groups: { count: number; id: string; }[]; }) {
|
GUILD_MEMBER_LIST_UPDATE({ guildId, groups }: { guildId: string; groups: { count: number; id: string; }[]; }) {
|
||||||
onlineMemberMap.set(
|
onlineMemberMap.set(
|
||||||
guildId,
|
guildId,
|
||||||
groups.reduce((total, curr) => total + (curr.id === StatusType.OFFLINE ? 0 : curr.count), 0)
|
groups.reduce((total, curr) => total + (curr.id === StatusType.OFFLINE ? 0 : curr.count), 0)
|
||||||
|
|
|
@ -25,7 +25,7 @@ export default definePlugin({
|
||||||
}
|
}
|
||||||
}],
|
}],
|
||||||
|
|
||||||
renderUsername: ErrorBoundary.wrap((props: { user?: UserRecord, username: string; }) => {
|
renderUsername: ErrorBoundary.wrap((props: { user?: UserRecord; username: string; }) => {
|
||||||
const { user, username } = props;
|
const { user, username } = props;
|
||||||
const [isHovering, setIsHovering] = useState(false);
|
const [isHovering, setIsHovering] = useState(false);
|
||||||
|
|
||||||
|
|
|
@ -18,9 +18,9 @@ type Fill = [FillValue, FillValue, FillValue];
|
||||||
type DiffKey = keyof Diff;
|
type DiffKey = keyof Diff;
|
||||||
|
|
||||||
interface Diff {
|
interface Diff {
|
||||||
days: number,
|
days: number;
|
||||||
hours: number,
|
hours: number;
|
||||||
minutes: number,
|
minutes: number;
|
||||||
seconds: number;
|
seconds: number;
|
||||||
milliseconds: number;
|
milliseconds: number;
|
||||||
}
|
}
|
||||||
|
@ -172,7 +172,7 @@ export default definePlugin({
|
||||||
|
|
||||||
Icon({ delta, fill, props }: {
|
Icon({ delta, fill, props }: {
|
||||||
delta: string | null;
|
delta: string | null;
|
||||||
fill: Fill,
|
fill: Fill;
|
||||||
props: {
|
props: {
|
||||||
onClick: () => void;
|
onClick: () => void;
|
||||||
onMouseEnter: () => void;
|
onMouseEnter: () => void;
|
||||||
|
|
|
@ -255,7 +255,7 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
handleDelete(channelMessages: ChannelMessages | null | undefined, data: { ids: string[], id: string; mlDeleted?: boolean; }, isBulk: boolean) {
|
handleDelete(channelMessages: ChannelMessages | null | undefined, data: { ids: string[]; id: string; mlDeleted?: boolean; }, isBulk: boolean) {
|
||||||
try {
|
try {
|
||||||
if (channelMessages == null || (!isBulk && !channelMessages.has(data.id)))
|
if (channelMessages == null || (!isBulk && !channelMessages.has(data.id)))
|
||||||
return channelMessages;
|
return channelMessages;
|
||||||
|
|
|
@ -2,8 +2,9 @@
|
||||||
display: none;
|
display: none;
|
||||||
}
|
}
|
||||||
|
|
||||||
.messagelogger-deleted
|
/* https://github.com/stylelint-stylistic/stylelint-stylistic/issues/30 */
|
||||||
:is(
|
/* stylelint-disable @stylistic/indentation */
|
||||||
|
.messagelogger-deleted:is(
|
||||||
video,
|
video,
|
||||||
.emoji,
|
.emoji,
|
||||||
[data-type="sticker"],
|
[data-type="sticker"],
|
||||||
|
@ -11,6 +12,7 @@
|
||||||
.messagelogger-deleted-attachment,
|
.messagelogger-deleted-attachment,
|
||||||
[class|="inlineMediaEmbed"]
|
[class|="inlineMediaEmbed"]
|
||||||
) {
|
) {
|
||||||
|
/* stylelint-enable @stylistic/indentation */
|
||||||
filter: grayscale(1) !important;
|
filter: grayscale(1) !important;
|
||||||
transition: 150ms filter ease-in-out;
|
transition: 150ms filter ease-in-out;
|
||||||
|
|
||||||
|
@ -19,8 +21,9 @@
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
.messagelogger-deleted
|
/* https://github.com/stylelint-stylistic/stylelint-stylistic/issues/30 */
|
||||||
:is(
|
/* stylelint-disable @stylistic/indentation */
|
||||||
|
.messagelogger-deleted:is(
|
||||||
video,
|
video,
|
||||||
.emoji,
|
.emoji,
|
||||||
[data-type="sticker"],
|
[data-type="sticker"],
|
||||||
|
@ -28,6 +31,7 @@
|
||||||
.messagelogger-deleted-attachment,
|
.messagelogger-deleted-attachment,
|
||||||
[class|="inlineMediaEmbed"]
|
[class|="inlineMediaEmbed"]
|
||||||
):hover {
|
):hover {
|
||||||
|
/* stylelint-enable @stylistic/indentation */
|
||||||
filter: grayscale(0) !important;
|
filter: grayscale(0) !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -61,7 +61,7 @@ const computePermissions: (options: {
|
||||||
excludeGuildPermissions?: boolean /* = false */;
|
excludeGuildPermissions?: boolean /* = false */;
|
||||||
}) => bigint = findByCodeLazy(".getCurrentUser()", ".computeLurkerPermissionsAllowList()");
|
}) => bigint = findByCodeLazy(".getCurrentUser()", ".computeLurkerPermissionsAllowList()");
|
||||||
|
|
||||||
const Tag: RC<{ type?: number, className?: string, useRemSizes?: boolean; }> & { Types: Record<string, number>; }
|
const Tag: RC<{ type?: number; className?: string; useRemSizes?: boolean; }> & { Types: Record<string, number>; }
|
||||||
= findLazy(m => m.Types?.[0] === "BOT");
|
= findLazy(m => m.Types?.[0] === "BOT");
|
||||||
|
|
||||||
const isWebhook = (message: MessageRecord | undefined, user: UserRecord) => !!message?.webhookId && user.isNonUserBot();
|
const isWebhook = (message: MessageRecord | undefined, user: UserRecord) => !!message?.webhookId && user.isNonUserBot();
|
||||||
|
@ -332,9 +332,9 @@ export default definePlugin({
|
||||||
getTag({
|
getTag({
|
||||||
message, user, channelId, origType, location, channel
|
message, user, channelId, origType, location, channel
|
||||||
}: {
|
}: {
|
||||||
message?: MessageRecord,
|
message?: MessageRecord;
|
||||||
user?: UserRecord,
|
user?: UserRecord;
|
||||||
channel?: ChannelRecord,
|
channel?: ChannelRecord;
|
||||||
channelId?: string;
|
channelId?: string;
|
||||||
origType?: number;
|
origType?: number;
|
||||||
location: "chat" | "not-chat";
|
location: "chat" | "not-chat";
|
||||||
|
|
|
@ -76,7 +76,7 @@ export default definePlugin({
|
||||||
|
|
||||||
isBotOrMe: (user: UserRecord) => user.bot || user.id === UserStore.getCurrentUser()!.id,
|
isBotOrMe: (user: UserRecord) => user.bot || user.id === UserStore.getCurrentUser()!.id,
|
||||||
|
|
||||||
renderMutualGDMs: ErrorBoundary.wrap(({ user, onClose }: { user: UserRecord, onClose: () => void; }) => {
|
renderMutualGDMs: ErrorBoundary.wrap(({ user, onClose }: { user: UserRecord; onClose: () => void; }) => {
|
||||||
const entries = ChannelStore.getSortedPrivateChannels()
|
const entries = ChannelStore.getSortedPrivateChannels()
|
||||||
.filter((channel): channel is GroupDMChannelRecord =>
|
.filter((channel): channel is GroupDMChannelRecord =>
|
||||||
channel.isGroupDM()
|
channel.isGroupDM()
|
||||||
|
|
|
@ -78,7 +78,7 @@ const settings = definePluginSettings({
|
||||||
});
|
});
|
||||||
|
|
||||||
const makeContextMenuPatch = (shouldAddIcon: boolean) =>
|
const makeContextMenuPatch = (shouldAddIcon: boolean) =>
|
||||||
((children, { guild }: { guild?: GuildRecord, onClose: () => void; }) => {
|
((children, { guild }: { guild?: GuildRecord; onClose: () => void; }) => {
|
||||||
if (!guild) return;
|
if (!guild) return;
|
||||||
|
|
||||||
const group = findGroupChildrenByChildId("privacy", children);
|
const group = findGroupChildrenByChildId("privacy", children);
|
||||||
|
|
|
@ -160,10 +160,10 @@
|
||||||
width: -moz-fit-content;
|
width: -moz-fit-content;
|
||||||
width: fit-content;
|
width: fit-content;
|
||||||
height: 24px;
|
height: 24px;
|
||||||
padding: 4px
|
padding: 4px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.custom-profile-theme .vc-permviewer-role-button {
|
.custom-profile-theme .vc-permviewer-role-button {
|
||||||
background: rgb(var(--bg-overlay-color)/var(--bg-overlay-opacity-6));
|
background: rgb(var(--bg-overlay-color) / var(--bg-overlay-opacity-6));
|
||||||
border-color: var(--profile-body-border-color)
|
border-color: var(--profile-body-border-color);
|
||||||
}
|
}
|
||||||
|
|
|
@ -23,8 +23,8 @@ import { DEFAULT_CHUNK_SIZE } from "./constants";
|
||||||
import { canMoveCategory, canMoveCategoryInDirection, categories, type Category, categoryLen, collapseCategory, getAllUncollapsedChannels, getSections, init, isPinned, moveCategory, removeCategory } from "./data";
|
import { canMoveCategory, canMoveCategoryInDirection, categories, type Category, categoryLen, collapseCategory, getAllUncollapsedChannels, getSections, init, isPinned, moveCategory, removeCategory } from "./data";
|
||||||
|
|
||||||
interface ChannelComponentProps {
|
interface ChannelComponentProps {
|
||||||
children: ReactNode,
|
children: ReactNode;
|
||||||
channel: ChannelRecord,
|
channel: ChannelRecord;
|
||||||
selected: boolean;
|
selected: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -6,7 +6,7 @@
|
||||||
text-transform: uppercase;
|
text-transform: uppercase;
|
||||||
font-size: 12px;
|
font-size: 12px;
|
||||||
line-height: 16px;
|
line-height: 16px;
|
||||||
letter-spacing: .02em;
|
letter-spacing: 0.02em;
|
||||||
font-family: var(--font-display);
|
font-family: var(--font-display);
|
||||||
font-weight: 600;
|
font-weight: 600;
|
||||||
flex: 1 1 auto;
|
flex: 1 1 auto;
|
||||||
|
@ -29,7 +29,7 @@
|
||||||
width: 16px;
|
width: 16px;
|
||||||
height: 16px;
|
height: 16px;
|
||||||
color: var(--interactive-normal);
|
color: var(--interactive-normal);
|
||||||
transform: rotate(90deg)
|
transform: rotate(90deg);
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-pindms-collapsed .vc-pindms-collapse-icon {
|
.vc-pindms-collapsed .vc-pindms-collapse-icon {
|
||||||
|
|
|
@ -71,7 +71,7 @@ const Icons = {
|
||||||
|
|
||||||
const StatusUtils = findByPropsLazy("useStatusFillColor", "StatusTypes");
|
const StatusUtils = findByPropsLazy("useStatusFillColor", "StatusTypes");
|
||||||
|
|
||||||
const PlatformIcon = ({ platform, status, small }: { platform: ClientType, status: StatusType; small: boolean; }) => {
|
const PlatformIcon = ({ platform, status, small }: { platform: ClientType; status: StatusType; small: boolean; }) => {
|
||||||
const tooltip = platform === ClientType.EMBEDDED
|
const tooltip = platform === ClientType.EMBEDDED
|
||||||
? "Console"
|
? "Console"
|
||||||
: platform[0]!.toUpperCase() + platform.slice(1);
|
: platform[0]!.toUpperCase() + platform.slice(1);
|
||||||
|
|
|
@ -28,7 +28,7 @@ const UploadAttachmentStore: FluxStore & Record<string, any> = findStoreLazy("Up
|
||||||
|
|
||||||
const getDraft = (channelId: string) => DraftStore.getDraft(channelId, DraftType.CHANNEL_MESSAGE);
|
const getDraft = (channelId: string) => DraftStore.getDraft(channelId, DraftType.CHANNEL_MESSAGE);
|
||||||
|
|
||||||
const getImageBox = (url: string): Promise<{ width: number, height: number; } | null> =>
|
const getImageBox = (url: string): Promise<{ width: number; height: number; } | null> =>
|
||||||
new Promise(res => {
|
new Promise(res => {
|
||||||
const img = new Image();
|
const img = new Image();
|
||||||
img.onload = () => {
|
img.onload = () => {
|
||||||
|
|
|
@ -149,11 +149,11 @@ async function bulkFetchPronouns(ids: string[]): Promise<PronounsResponse> {
|
||||||
|
|
||||||
const SpecialCodes = new Set(["any", "ask", "avoid", "other", "unspecified"]);
|
const SpecialCodes = new Set(["any", "ask", "avoid", "other", "unspecified"]);
|
||||||
|
|
||||||
export function extractPronouns(pronounSet?: { [locale: string]: PronounCode[] }): string {
|
export function extractPronouns(pronounSet?: { [locale: string]: PronounCode[]; }): string {
|
||||||
if (!pronounSet || !pronounSet.en) return PronounMapping.unspecified;
|
if (!pronounSet || !pronounSet.en) return PronounMapping.unspecified;
|
||||||
// PronounDB returns an empty set instead of {sets: {en: ["unspecified"]}}.
|
// PronounDB returns an empty set instead of {sets: {en: ["unspecified"]}}.
|
||||||
const pronouns = pronounSet.en;
|
const pronouns = pronounSet.en;
|
||||||
const { pronounsFormat } = Settings.plugins.PronounDB as { pronounsFormat: PronounsFormat, enabled: boolean; };
|
const { pronounsFormat } = Settings.plugins.PronounDB as { pronounsFormat: PronounsFormat; enabled: boolean; };
|
||||||
|
|
||||||
if (pronouns.length === 1) {
|
if (pronouns.length === 1) {
|
||||||
// For capitalized pronouns or special codes (any, ask, avoid), we always return the normal (capitalized) string
|
// For capitalized pronouns or special codes (any, ask, avoid), we always return the normal (capitalized) string
|
||||||
|
|
|
@ -29,14 +29,14 @@ export interface PronounsResponse {
|
||||||
[id: string]: {
|
[id: string]: {
|
||||||
sets?: {
|
sets?: {
|
||||||
[locale: string]: PronounCode[];
|
[locale: string]: PronounCode[];
|
||||||
}
|
};
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface CachePronouns {
|
export interface CachePronouns {
|
||||||
sets?: {
|
sets?: {
|
||||||
[locale: string]: PronounCode[];
|
[locale: string]: PronounCode[];
|
||||||
}
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
export type PronounCode = keyof typeof PronounMapping;
|
export type PronounCode = keyof typeof PronounMapping;
|
||||||
|
|
|
@ -44,7 +44,7 @@ function ReplyTimestamp({
|
||||||
referencedMessage,
|
referencedMessage,
|
||||||
baseMessage,
|
baseMessage,
|
||||||
}: {
|
}: {
|
||||||
referencedMessage: ReferencedMessage,
|
referencedMessage: ReferencedMessage;
|
||||||
baseMessage: MessageRecord;
|
baseMessage: MessageRecord;
|
||||||
}) {
|
}) {
|
||||||
if (referencedMessage.state !== ReferencedMessageState.LOADED) return null;
|
if (referencedMessage.state !== ReferencedMessageState.LOADED) return null;
|
||||||
|
|
|
@ -83,18 +83,18 @@ export interface ReviewDBCurrentUser extends ReviewDBUser {
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ReviewAuthor {
|
export interface ReviewAuthor {
|
||||||
id: number,
|
id: number;
|
||||||
discordID: string,
|
discordID: string;
|
||||||
username: string,
|
username: string;
|
||||||
profilePhoto: string,
|
profilePhoto: string;
|
||||||
badges: Badge[];
|
badges: Badge[];
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface Review {
|
export interface Review {
|
||||||
comment: string,
|
comment: string;
|
||||||
id: number,
|
id: number;
|
||||||
star: number,
|
star: number;
|
||||||
sender: ReviewAuthor,
|
sender: ReviewAuthor;
|
||||||
timestamp: number;
|
timestamp: number;
|
||||||
type?: ReviewType;
|
type?: ReviewType;
|
||||||
}
|
}
|
||||||
|
|
|
@ -51,7 +51,7 @@ const guildPopoutPatch = ((children, { guild }: { guild?: GuildRecord; onClose:
|
||||||
);
|
);
|
||||||
}) satisfies NavContextMenuPatchCallback;
|
}) satisfies NavContextMenuPatchCallback;
|
||||||
|
|
||||||
const userContextPatch = ((children, { user }: { user?: UserRecord, onClose(): void; }) => {
|
const userContextPatch = ((children, { user }: { user?: UserRecord; onClose(): void; }) => {
|
||||||
if (user)
|
if (user)
|
||||||
children.push(
|
children.push(
|
||||||
<Menu.MenuItem
|
<Menu.MenuItem
|
||||||
|
|
|
@ -78,9 +78,10 @@ export default definePlugin({
|
||||||
// idk if this is good for performance but it doesnt seem to be a problem in my experience
|
// idk if this is good for performance but it doesnt seem to be a problem in my experience
|
||||||
DataStore.update("summaries-data", summaries => {
|
DataStore.update("summaries-data", summaries => {
|
||||||
summaries ??= {};
|
summaries ??= {};
|
||||||
summaries[data.channel_id]
|
if (summaries[data.channel_id])
|
||||||
? summaries[data.channel_id].unshift(...incomingSummaries)
|
summaries[data.channel_id].unshift(...incomingSummaries);
|
||||||
: (summaries[data.channel_id] = incomingSummaries);
|
else
|
||||||
|
summaries[data.channel_id] = incomingSummaries;
|
||||||
if (summaries[data.channel_id].length > 50)
|
if (summaries[data.channel_id].length > 50)
|
||||||
summaries[data.channel_id] = summaries[data.channel_id].slice(0, 50);
|
summaries[data.channel_id] = summaries[data.channel_id].slice(0, 50);
|
||||||
|
|
||||||
|
|
|
@ -54,7 +54,7 @@ type Format = typeof Formats[number];
|
||||||
|
|
||||||
const cl = classNameFactory("vc-st-");
|
const cl = classNameFactory("vc-st-");
|
||||||
|
|
||||||
function PickerModal({ rootProps, close }: { rootProps: ModalProps, close(): void; }) {
|
function PickerModal({ rootProps, close }: { rootProps: ModalProps; close(): void; }) {
|
||||||
const [value, setValue] = useState<string>();
|
const [value, setValue] = useState<string>();
|
||||||
const [format, setFormat] = useState<Format>("");
|
const [format, setFormat] = useState<Format>("");
|
||||||
const time = Math.round((new Date(value!).getTime() || Date.now()) / 1000);
|
const time = Math.round((new Date(value!).getTime() || Date.now()) / 1000);
|
||||||
|
|
|
@ -28,7 +28,7 @@ export interface Language {
|
||||||
name: string;
|
name: string;
|
||||||
id: string;
|
id: string;
|
||||||
devicon?: string;
|
devicon?: string;
|
||||||
grammarUrl: string,
|
grammarUrl: string;
|
||||||
grammar?: ILanguageRegistration["grammar"];
|
grammar?: ILanguageRegistration["grammar"];
|
||||||
scopeName: string;
|
scopeName: string;
|
||||||
aliases?: string[];
|
aliases?: string[];
|
||||||
|
|
|
@ -21,8 +21,8 @@ import type { Dispatch, SetStateAction } from "react";
|
||||||
|
|
||||||
type Shiki = typeof import("../api/shiki").shiki;
|
type Shiki = typeof import("../api/shiki").shiki;
|
||||||
interface ThemeState {
|
interface ThemeState {
|
||||||
id: Shiki["currentThemeUrl"],
|
id: Shiki["currentThemeUrl"];
|
||||||
theme: Shiki["currentTheme"],
|
theme: Shiki["currentTheme"];
|
||||||
}
|
}
|
||||||
|
|
||||||
const currentTheme: ThemeState = {
|
const currentTheme: ThemeState = {
|
||||||
|
|
|
@ -7,8 +7,8 @@ async function handleClick() {
|
||||||
}
|
}
|
||||||
|
|
||||||
export const Example: FC<{
|
export const Example: FC<{
|
||||||
real: boolean,
|
real: boolean;
|
||||||
shigged?: number,
|
shigged?: number;
|
||||||
}> = ({ real, shigged }) => (
|
}> = ({ real, shigged }) => (
|
||||||
<>
|
<>
|
||||||
<p>{`Shigg${real ? `ies${shigged === 0x1B ? "t" : ""}` : "y"}`}</p>
|
<p>{`Shigg${real ? `ies${shigged === 0x1B ? "t" : ""}` : "y"}`}</p>
|
||||||
|
|
|
@ -29,8 +29,8 @@ export const shouldUseHljs = ({
|
||||||
lang,
|
lang,
|
||||||
tryHljs,
|
tryHljs,
|
||||||
}: {
|
}: {
|
||||||
lang: HighlighterProps["lang"],
|
lang: HighlighterProps["lang"];
|
||||||
tryHljs: HljsSetting,
|
tryHljs: HljsSetting;
|
||||||
}) => {
|
}) => {
|
||||||
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
||||||
const hljsLang = lang ? hljs?.getLanguage?.(lang) : null;
|
const hljsLang = lang ? hljs?.getLanguage?.(lang) : null;
|
||||||
|
|
|
@ -95,7 +95,7 @@ const profilePanelComponent = ErrorBoundary.wrap(
|
||||||
{ noop: true }
|
{ noop: true }
|
||||||
);
|
);
|
||||||
|
|
||||||
function ConnectionsComponent({ id, theme, simplified }: { id: string, theme: string, simplified?: boolean; }) {
|
function ConnectionsComponent({ id, theme, simplified }: { id: string; theme: string; simplified?: boolean; }) {
|
||||||
const profile = UserProfileStore.getUserProfile(id);
|
const profile = UserProfileStore.getUserProfile(id);
|
||||||
if (!profile)
|
if (!profile)
|
||||||
return null;
|
return null;
|
||||||
|
@ -131,7 +131,7 @@ function ConnectionsComponent({ id, theme, simplified }: { id: string, theme: st
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
function CompactConnectionComponent({ connection, theme }: { connection: ProfileConnectedAccountData, theme: string; }) {
|
function CompactConnectionComponent({ connection, theme }: { connection: ProfileConnectedAccountData; theme: string; }) {
|
||||||
const platform = Platforms.get(useLegacyPlatformType(connection.type));
|
const platform = Platforms.get(useLegacyPlatformType(connection.type));
|
||||||
const url = platform.getPlatformUserUrl?.(connection);
|
const url = platform.getPlatformUserUrl?.(connection);
|
||||||
|
|
||||||
|
|
|
@ -162,7 +162,7 @@ function SeekBar() {
|
||||||
|
|
||||||
const [position, setPosition] = useState<number>(storePosition);
|
const [position, setPosition] = useState<number>(storePosition);
|
||||||
|
|
||||||
// eslint-disable-next-line consistent-return
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
if (isPlaying && !isSettingPosition) {
|
if (isPlaying && !isSettingPosition) {
|
||||||
setPosition(SpotifyStore.position);
|
setPosition(SpotifyStore.position);
|
||||||
|
@ -359,7 +359,7 @@ export function Player() {
|
||||||
const [shouldHide, setShouldHide] = useState(false);
|
const [shouldHide, setShouldHide] = useState(false);
|
||||||
|
|
||||||
// Hide player after 5 minutes of inactivity
|
// Hide player after 5 minutes of inactivity
|
||||||
// eslint-disable-next-line consistent-return
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
setShouldHide(false);
|
setShouldHide(false);
|
||||||
if (!isPlaying) {
|
if (!isPlaying) {
|
||||||
|
|
|
@ -47,10 +47,10 @@ export interface Track {
|
||||||
interface PlayerState {
|
interface PlayerState {
|
||||||
accountId: string;
|
accountId: string;
|
||||||
track: Track | null;
|
track: Track | null;
|
||||||
volumePercent?: number,
|
volumePercent?: number;
|
||||||
isPlaying?: boolean,
|
isPlaying?: boolean;
|
||||||
repeat: boolean,
|
repeat: boolean;
|
||||||
position?: number,
|
position?: number;
|
||||||
context?: any;
|
context?: any;
|
||||||
device?: Device;
|
device?: Device;
|
||||||
|
|
||||||
|
|
|
@ -38,7 +38,7 @@ const Dismiss = ({ onDismiss }: { onDismiss: () => void; }) => (
|
||||||
</button>
|
</button>
|
||||||
);
|
);
|
||||||
|
|
||||||
export function TranslationAccessory({ message }: { message: MessageRecord & { vencordEmbeddedBy?: string[] }; }) {
|
export function TranslationAccessory({ message }: { message: MessageRecord & { vencordEmbeddedBy?: string[]; }; }) {
|
||||||
const [translation, setTranslation] = useState<TranslationValue>();
|
const [translation, setTranslation] = useState<TranslationValue>();
|
||||||
|
|
||||||
useEffect(() => {
|
useEffect(() => {
|
||||||
|
|
|
@ -42,7 +42,7 @@ const settings = definePluginSettings({
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
export const buildSeveralUsers = ({ a, b, count }: { a: string, b: string, count: number; }) => [
|
export const buildSeveralUsers = ({ a, b, count }: { a: string; b: string; count: number; }) => [
|
||||||
<strong key="0">{a}</strong>,
|
<strong key="0">{a}</strong>,
|
||||||
", ",
|
", ",
|
||||||
<strong key="1">{b}</strong>,
|
<strong key="1">{b}</strong>,
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
.vc-uvs-button>div {
|
.vc-uvs-button > div {
|
||||||
white-space: normal !important;
|
white-space: normal !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -21,7 +21,7 @@
|
||||||
margin-bottom: 0 !important;
|
margin-bottom: 0 !important;
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-uvs-popout-margin-self>[class^="section"] {
|
.vc-uvs-popout-margin-self > [class^="section"] {
|
||||||
padding-top: 0;
|
padding-top: 0;
|
||||||
padding-bottom: 12px;
|
padding-bottom: 12px;
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,7 +18,7 @@ const enum ReferencedMessageState {
|
||||||
}
|
}
|
||||||
|
|
||||||
interface Reply {
|
interface Reply {
|
||||||
baseAuthor: UserRecord,
|
baseAuthor: UserRecord;
|
||||||
baseMessage: MessageRecord;
|
baseMessage: MessageRecord;
|
||||||
channel: ChannelRecord;
|
channel: ChannelRecord;
|
||||||
referencedMessage: { state: ReferencedMessageState; };
|
referencedMessage: { state: ReferencedMessageState; };
|
||||||
|
|
|
@ -146,7 +146,7 @@ function updateStatuses(type: string, { deaf, mute, selfDeaf, selfMute, userId,
|
||||||
*/
|
*/
|
||||||
|
|
||||||
function playSample(tempSettings: any, type: string) {
|
function playSample(tempSettings: any, type: string) {
|
||||||
const settings = Object.assign({}, Settings.plugins.VcNarrator, tempSettings);
|
const settings = { ...Settings.plugins.VcNarrator, ...tempSettings };
|
||||||
const me = UserStore.getCurrentUser()!;
|
const me = UserStore.getCurrentUser()!;
|
||||||
const currGuildId = SelectedGuildStore.getGuildId();
|
const currGuildId = SelectedGuildStore.getGuildId();
|
||||||
|
|
||||||
|
|
|
@ -1,16 +1,16 @@
|
||||||
.vc-toolbox-btn,
|
.vc-toolbox-btn,
|
||||||
.vc-toolbox-btn>svg {
|
.vc-toolbox-btn > svg {
|
||||||
-webkit-app-region: no-drag;
|
-webkit-app-region: no-drag;
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-toolbox-btn>svg {
|
.vc-toolbox-btn > svg {
|
||||||
color: var(--interactive-normal);
|
color: var(--interactive-normal);
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-toolbox-btn[class*="selected"]>svg {
|
.vc-toolbox-btn[class*="selected"] > svg {
|
||||||
color: var(--interactive-active);
|
color: var(--interactive-active);
|
||||||
}
|
}
|
||||||
|
|
||||||
.vc-toolbox-btn:hover>svg {
|
.vc-toolbox-btn:hover > svg {
|
||||||
color: var(--interactive-hover);
|
color: var(--interactive-hover);
|
||||||
}
|
}
|
||||||
|
|
|
@ -135,7 +135,7 @@ function MakeContextCallback(name: "Guild" | "User" | "Channel"): NavContextMenu
|
||||||
if (!Array.isArray(p.children))
|
if (!Array.isArray(p.children))
|
||||||
p.children = [p.children];
|
p.children = [p.children];
|
||||||
|
|
||||||
children = p.children;
|
({ children } = p);
|
||||||
}
|
}
|
||||||
|
|
||||||
children.splice(-1, 0,
|
children.splice(-1, 0,
|
||||||
|
|
|
@ -81,8 +81,8 @@ export default definePlugin({
|
||||||
});
|
});
|
||||||
|
|
||||||
type AudioMetadata = {
|
type AudioMetadata = {
|
||||||
waveform: string,
|
waveform: string;
|
||||||
duration: number,
|
duration: number;
|
||||||
};
|
};
|
||||||
|
|
||||||
const EMPTY_META: AudioMetadata = {
|
const EMPTY_META: AudioMetadata = {
|
||||||
|
|
|
@ -287,7 +287,7 @@ export default definePlugin({
|
||||||
},
|
},
|
||||||
|
|
||||||
async paste() {
|
async paste() {
|
||||||
const clip = (await navigator.clipboard.read())[0];
|
const [clip] = await navigator.clipboard.read();
|
||||||
if (!clip) return;
|
if (!clip) return;
|
||||||
|
|
||||||
const data = new DataTransfer();
|
const data = new DataTransfer();
|
||||||
|
|
|
@ -9,11 +9,11 @@ import type { LiteralUnion } from "type-fest";
|
||||||
// Resolves a possibly nested prop in the form of "some.nested.prop" to type of T.some.nested.prop
|
// Resolves a possibly nested prop in the form of "some.nested.prop" to type of T.some.nested.prop
|
||||||
type ResolvePropDeep<T, P> = P extends `${infer Pre}.${infer Suf}`
|
type ResolvePropDeep<T, P> = P extends `${infer Pre}.${infer Suf}`
|
||||||
? Pre extends keyof T
|
? Pre extends keyof T
|
||||||
? ResolvePropDeep<T[Pre], Suf>
|
? ResolvePropDeep<T[Pre], Suf>
|
||||||
: any
|
: any
|
||||||
: P extends keyof T
|
: P extends keyof T
|
||||||
? T[P]
|
? T[P]
|
||||||
: any;
|
: any;
|
||||||
|
|
||||||
interface SettingsStoreOptions {
|
interface SettingsStoreOptions {
|
||||||
readOnly?: boolean;
|
readOnly?: boolean;
|
||||||
|
@ -26,6 +26,7 @@ interface SettingsStoreOptions {
|
||||||
}
|
}
|
||||||
|
|
||||||
// merges the SettingsStoreOptions type into the class
|
// merges the SettingsStoreOptions type into the class
|
||||||
|
// eslint-disable-next-line @typescript-eslint/no-empty-object-type
|
||||||
export interface SettingsStore<T extends object> extends SettingsStoreOptions { }
|
export interface SettingsStore<T extends object> extends SettingsStoreOptions { }
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -32,5 +32,5 @@ document.addEventListener("DOMContentLoaded", () => {
|
||||||
document.head.append(Object.assign(document.createElement("style"), {
|
document.head.append(Object.assign(document.createElement("style"), {
|
||||||
textContent: styleStr,
|
textContent: styleStr,
|
||||||
id: "vencord-margins"
|
id: "vencord-margins"
|
||||||
})), { once: true };
|
}));
|
||||||
});
|
}, { once: true });
|
||||||
|
|
|
@ -82,11 +82,11 @@ interface AwaiterOpts<T> {
|
||||||
export function useAwaiter<T>(factory: () => Promise<T>): AwaiterRes<T | null>;
|
export function useAwaiter<T>(factory: () => Promise<T>): AwaiterRes<T | null>;
|
||||||
export function useAwaiter<T>(factory: () => Promise<T>, providedOpts: AwaiterOpts<T>): AwaiterRes<T>;
|
export function useAwaiter<T>(factory: () => Promise<T>, providedOpts: AwaiterOpts<T>): AwaiterRes<T>;
|
||||||
export function useAwaiter<T>(factory: () => Promise<T>, providedOpts?: AwaiterOpts<T | null>): AwaiterRes<T | null> {
|
export function useAwaiter<T>(factory: () => Promise<T>, providedOpts?: AwaiterOpts<T | null>): AwaiterRes<T | null> {
|
||||||
const opts: AwaiterOpts<T | null> = Object.assign({
|
const opts: AwaiterOpts<T | null> = {
|
||||||
fallbackValue: null,
|
fallbackValue: null,
|
||||||
deps: [],
|
deps: [],
|
||||||
onError: null,
|
...providedOpts
|
||||||
}, providedOpts);
|
};
|
||||||
const [state, setState] = useState({
|
const [state, setState] = useState({
|
||||||
value: opts.fallbackValue,
|
value: opts.fallbackValue,
|
||||||
error: null,
|
error: null,
|
||||||
|
@ -109,7 +109,7 @@ export function useAwaiter<T>(factory: () => Promise<T>, providedOpts?: AwaiterO
|
||||||
opts.onError?.(error);
|
opts.onError?.(error);
|
||||||
});
|
});
|
||||||
|
|
||||||
return () => { (isAlive = false); };
|
return () => { isAlive = false; };
|
||||||
}, opts.deps);
|
}, opts.deps);
|
||||||
|
|
||||||
return [state.value, state.error, state.pending];
|
return [state.value, state.error, state.pending];
|
||||||
|
|
|
@ -81,7 +81,7 @@ export interface PluginDef {
|
||||||
* These will automatically be enabled and loaded before your plugin
|
* These will automatically be enabled and loaded before your plugin
|
||||||
* Common examples are CommandsAPI, MessageEventsAPI...
|
* Common examples are CommandsAPI, MessageEventsAPI...
|
||||||
*/
|
*/
|
||||||
dependencies?: string[],
|
dependencies?: string[];
|
||||||
/**
|
/**
|
||||||
* Whether this plugin is required and forcefully enabled
|
* Whether this plugin is required and forcefully enabled
|
||||||
*/
|
*/
|
||||||
|
@ -98,7 +98,7 @@ export interface PluginDef {
|
||||||
* When to call the start() method
|
* When to call the start() method
|
||||||
* @default StartAt.WebpackReady
|
* @default StartAt.WebpackReady
|
||||||
*/
|
*/
|
||||||
startAt?: StartAt,
|
startAt?: StartAt;
|
||||||
/**
|
/**
|
||||||
* Which parts of the plugin can be tested by the reporter. Defaults to all parts
|
* Which parts of the plugin can be tested by the reporter. Defaults to all parts
|
||||||
*/
|
*/
|
||||||
|
@ -170,8 +170,9 @@ export const enum OptionType {
|
||||||
|
|
||||||
export type SettingsDefinition = Record<string, PluginSettingDef>;
|
export type SettingsDefinition = Record<string, PluginSettingDef>;
|
||||||
export type SettingsChecks<D extends SettingsDefinition> = {
|
export type SettingsChecks<D extends SettingsDefinition> = {
|
||||||
[K in keyof D]?: D[K] extends PluginSettingComponentDef ? IsDisabled<DefinedSettings<D>> :
|
[K in keyof D]?: D[K] extends PluginSettingComponentDef
|
||||||
(IsDisabled<DefinedSettings<D>> & IsValid<PluginSettingType<D[K]>, DefinedSettings<D>>);
|
? IsDisabled<DefinedSettings<D>>
|
||||||
|
: (IsDisabled<DefinedSettings<D>> & IsValid<PluginSettingType<D[K]>, DefinedSettings<D>>);
|
||||||
};
|
};
|
||||||
|
|
||||||
export type PluginSettingDef = (
|
export type PluginSettingDef = (
|
||||||
|
@ -328,7 +329,7 @@ export interface DefinedSettings<
|
||||||
|
|
||||||
export type PartialExcept<T, R extends keyof T> = Partial<T> & Required<Pick<T, R>>;
|
export type PartialExcept<T, R extends keyof T> = Partial<T> & Required<Pick<T, R>>;
|
||||||
|
|
||||||
export type IpcRes<V = any> = { ok: true; value: V; } | { ok: false, error: any; };
|
export type IpcRes<V = any> = { ok: true; value: V; } | { ok: false; error: any; };
|
||||||
|
|
||||||
/* -------------------------------------------- */
|
/* -------------------------------------------- */
|
||||||
/* Legacy Options Types */
|
/* Legacy Options Types */
|
||||||
|
@ -352,6 +353,8 @@ export type PluginOptionComponent = PluginSettingComponentDef & PluginSettingCom
|
||||||
export type PluginNative<PluginExports extends Record<string, (event: Electron.IpcMainInvokeEvent, ...args: any[]) => any>> = {
|
export type PluginNative<PluginExports extends Record<string, (event: Electron.IpcMainInvokeEvent, ...args: any[]) => any>> = {
|
||||||
[key in keyof PluginExports]:
|
[key in keyof PluginExports]:
|
||||||
PluginExports[key] extends (event: Electron.IpcMainInvokeEvent, ...args: infer Args) => infer Return
|
PluginExports[key] extends (event: Electron.IpcMainInvokeEvent, ...args: infer Args) => infer Return
|
||||||
? (...args: Args) => Return extends Promise<any> ? Return : Promise<Return>
|
? (...args: Args) => Return extends Promise<any>
|
||||||
: never;
|
? Return
|
||||||
|
: Promise<Return>
|
||||||
|
: never;
|
||||||
};
|
};
|
||||||
|
|
|
@ -23,10 +23,10 @@ import type * as t from "./types/components";
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions
|
||||||
export let Forms = {} as {
|
export let Forms = {} as {
|
||||||
FormTitle: t.FormTitle,
|
FormTitle: t.FormTitle;
|
||||||
FormSection: t.FormSection,
|
FormSection: t.FormSection;
|
||||||
FormDivider: t.FormDivider,
|
FormDivider: t.FormDivider;
|
||||||
FormText: t.FormText,
|
FormText: t.FormText;
|
||||||
};
|
};
|
||||||
|
|
||||||
export let Card: t.Card;
|
export let Card: t.Card;
|
||||||
|
|
|
@ -23,7 +23,7 @@ import type * as t from "./types/menu";
|
||||||
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions
|
// eslint-disable-next-line @typescript-eslint/consistent-type-assertions
|
||||||
export let Menu = {} as t.Menu;
|
export let Menu = {} as t.Menu;
|
||||||
|
|
||||||
waitFor(["MenuItem", "MenuSliderControl"], m => Menu = m);
|
waitFor(["MenuItem", "MenuSliderControl"], m => { Menu = m; });
|
||||||
|
|
||||||
export const ContextMenuApi: t.ContextMenuApi = mapMangledModuleLazy('type:"CONTEXT_MENU_OPEN', {
|
export const ContextMenuApi: t.ContextMenuApi = mapMangledModuleLazy('type:"CONTEXT_MENU_OPEN', {
|
||||||
closeContextMenu: filters.byCode("CONTEXT_MENU_CLOSE"),
|
closeContextMenu: filters.byCode("CONTEXT_MENU_CLOSE"),
|
||||||
|
|
|
@ -55,49 +55,49 @@ export const useStateFromStoresObject: Stores.UseStateFromStoresObjectHook = pro
|
||||||
});
|
});
|
||||||
|
|
||||||
export let ChannelStore: Stores.ChannelStore;
|
export let ChannelStore: Stores.ChannelStore;
|
||||||
waitForStore("ChannelStore", m => ChannelStore = m);
|
waitForStore("ChannelStore", m => { ChannelStore = m; });
|
||||||
|
|
||||||
export let DraftStore: Stores.DraftStore;
|
export let DraftStore: Stores.DraftStore;
|
||||||
waitForStore("DraftStore", s => DraftStore = s);
|
waitForStore("DraftStore", s => { DraftStore = s; });
|
||||||
|
|
||||||
export let EmojiStore: Stores.EmojiStore;
|
export let EmojiStore: Stores.EmojiStore;
|
||||||
waitForStore("EmojiStore", m => EmojiStore = m);
|
waitForStore("EmojiStore", m => { EmojiStore = m; });
|
||||||
|
|
||||||
export let GuildChannelStore: Stores.GuildChannelStore;
|
export let GuildChannelStore: Stores.GuildChannelStore;
|
||||||
waitForStore("GuildChannelStore", m => GuildChannelStore = m);
|
waitForStore("GuildChannelStore", m => { GuildChannelStore = m; });
|
||||||
|
|
||||||
export let GuildMemberStore: Stores.GuildMemberStore;
|
export let GuildMemberStore: Stores.GuildMemberStore;
|
||||||
waitForStore("GuildMemberStore", m => GuildMemberStore = m);
|
waitForStore("GuildMemberStore", m => { GuildMemberStore = m; });
|
||||||
|
|
||||||
export let GuildStore: Stores.GuildStore;
|
export let GuildStore: Stores.GuildStore;
|
||||||
waitForStore("GuildStore", m => GuildStore = m);
|
waitForStore("GuildStore", m => { GuildStore = m; });
|
||||||
|
|
||||||
export let MessageStore: Stores.MessageStore;
|
export let MessageStore: Stores.MessageStore;
|
||||||
waitForStore("MessageStore", m => MessageStore = m);
|
waitForStore("MessageStore", m => { MessageStore = m; });
|
||||||
|
|
||||||
export let PermissionStore: Stores.PermissionStore;
|
export let PermissionStore: Stores.PermissionStore;
|
||||||
waitForStore("PermissionStore", m => PermissionStore = m);
|
waitForStore("PermissionStore", m => { PermissionStore = m; });
|
||||||
|
|
||||||
export let PresenceStore: Stores.PresenceStore;
|
export let PresenceStore: Stores.PresenceStore;
|
||||||
waitForStore("PresenceStore", m => PresenceStore = m);
|
waitForStore("PresenceStore", m => { PresenceStore = m; });
|
||||||
|
|
||||||
export let ReadStateStore: Stores.ReadStateStore;
|
export let ReadStateStore: Stores.ReadStateStore;
|
||||||
waitForStore("ReadStateStore", m => ReadStateStore = m);
|
waitForStore("ReadStateStore", m => { ReadStateStore = m; });
|
||||||
|
|
||||||
export let RelationshipStore: Stores.RelationshipStore;
|
export let RelationshipStore: Stores.RelationshipStore;
|
||||||
waitForStore("RelationshipStore", m => RelationshipStore = m);
|
waitForStore("RelationshipStore", m => { RelationshipStore = m; });
|
||||||
|
|
||||||
export let SelectedChannelStore: Stores.SelectedChannelStore;
|
export let SelectedChannelStore: Stores.SelectedChannelStore;
|
||||||
waitForStore("SelectedChannelStore", m => SelectedChannelStore = m);
|
waitForStore("SelectedChannelStore", m => { SelectedChannelStore = m; });
|
||||||
|
|
||||||
export let SelectedGuildStore: Stores.SelectedGuildStore;
|
export let SelectedGuildStore: Stores.SelectedGuildStore;
|
||||||
waitForStore("SelectedGuildStore", m => SelectedGuildStore = m);
|
waitForStore("SelectedGuildStore", m => { SelectedGuildStore = m; });
|
||||||
|
|
||||||
export let UserProfileStore: Stores.UserProfileStore;
|
export let UserProfileStore: Stores.UserProfileStore;
|
||||||
waitForStore("UserProfileStore", m => UserProfileStore = m);
|
waitForStore("UserProfileStore", m => { UserProfileStore = m; });
|
||||||
|
|
||||||
export let UserStore: Stores.UserStore;
|
export let UserStore: Stores.UserStore;
|
||||||
waitForStore("UserStore", s => UserStore = s);
|
waitForStore("UserStore", m => { UserStore = m; });
|
||||||
|
|
||||||
export let WindowStore: Stores.WindowStore;
|
export let WindowStore: Stores.WindowStore;
|
||||||
waitForStore("WindowStore", m => WindowStore = m);
|
waitForStore("WindowStore", m => { WindowStore = m; });
|
||||||
|
|
4
src/webpack/common/types/classes.d.ts
vendored
4
src/webpack/common/types/classes.d.ts
vendored
|
@ -17,8 +17,8 @@
|
||||||
*/
|
*/
|
||||||
|
|
||||||
export interface ImageModalClasses {
|
export interface ImageModalClasses {
|
||||||
image: string,
|
image: string;
|
||||||
modal: string,
|
modal: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ButtonWrapperClasses {
|
export interface ButtonWrapperClasses {
|
||||||
|
|
4
src/webpack/common/types/components.d.ts
vendored
4
src/webpack/common/types/components.d.ts
vendored
|
@ -419,7 +419,7 @@ export type Popout = ComponentType<{
|
||||||
|
|
||||||
export type Dialog = ComponentType<JSX.IntrinsicElements["div"]>;
|
export type Dialog = ComponentType<JSX.IntrinsicElements["div"]>;
|
||||||
|
|
||||||
type Resolve = (data: { theme: "light" | "dark", saturation: number; }) => {
|
type Resolve = (data: { theme: "light" | "dark"; saturation: number; }) => {
|
||||||
hex(): string;
|
hex(): string;
|
||||||
hsl(): string;
|
hsl(): string;
|
||||||
int(): number;
|
int(): number;
|
||||||
|
@ -445,7 +445,7 @@ export type MaskedLink = ComponentType<PropsWithChildren<{
|
||||||
href: string;
|
href: string;
|
||||||
rel?: string;
|
rel?: string;
|
||||||
target?: string;
|
target?: string;
|
||||||
title?: string,
|
title?: string;
|
||||||
className?: string;
|
className?: string;
|
||||||
tabIndex?: number;
|
tabIndex?: number;
|
||||||
onClick?(): void;
|
onClick?(): void;
|
||||||
|
|
10
src/webpack/common/types/menu.d.ts
vendored
10
src/webpack/common/types/menu.d.ts
vendored
|
@ -66,11 +66,11 @@ export interface Menu {
|
||||||
interactive?: boolean;
|
interactive?: boolean;
|
||||||
}>;
|
}>;
|
||||||
MenuSliderControl: RC<{
|
MenuSliderControl: RC<{
|
||||||
minValue: number,
|
minValue: number;
|
||||||
maxValue: number,
|
maxValue: number;
|
||||||
value: number,
|
value: number;
|
||||||
onChange(value: number): void,
|
onChange(value: number): void;
|
||||||
renderValue?(value: number): string,
|
renderValue?(value: number): string;
|
||||||
}>;
|
}>;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
12
src/webpack/common/types/utils.d.ts
vendored
12
src/webpack/common/types/utils.d.ts
vendored
|
@ -92,18 +92,18 @@ export interface RouterUtils {
|
||||||
export interface IconUtils {
|
export interface IconUtils {
|
||||||
getUserAvatarURL(user: UserRecord, canAnimate?: boolean, size?: number, format?: string): string;
|
getUserAvatarURL(user: UserRecord, canAnimate?: boolean, size?: number, format?: string): string;
|
||||||
getDefaultAvatarURL(id: string, discriminator?: string): string;
|
getDefaultAvatarURL(id: string, discriminator?: string): string;
|
||||||
getUserBannerURL(data: { id: string, banner: string, canAnimate?: boolean, size: number; }): string | undefined;
|
getUserBannerURL(data: { id: string; banner: string; canAnimate?: boolean; size: number; }): string | undefined;
|
||||||
getAvatarDecorationURL(data: { avatarDecoration: string, size: number; canCanimate?: boolean; }): string | undefined;
|
getAvatarDecorationURL(data: { avatarDecoration: string; size: number; canCanimate?: boolean; }): string | undefined;
|
||||||
|
|
||||||
getGuildMemberAvatarURL(member: GuildMember, canAnimate?: string): string | null;
|
getGuildMemberAvatarURL(member: GuildMember, canAnimate?: string): string | null;
|
||||||
getGuildMemberAvatarURLSimple(data: { guildId: string, userId: string, avatar: string, canAnimate?: boolean; size?: number; }): string;
|
getGuildMemberAvatarURLSimple(data: { guildId: string; userId: string; avatar: string; canAnimate?: boolean; size?: number; }): string;
|
||||||
getGuildMemberBannerURL(data: { id: string, guildId: string, banner: string, canAnimate?: boolean, size: number; }): string | undefined;
|
getGuildMemberBannerURL(data: { id: string; guildId: string; banner: string; canAnimate?: boolean; size: number; }): string | undefined;
|
||||||
|
|
||||||
getGuildIconURL(data: { id: string, icon?: string, size?: number, canAnimate?: boolean; }): string | undefined;
|
getGuildIconURL(data: { id: string; icon?: string; size?: number; canAnimate?: boolean; }): string | undefined;
|
||||||
getGuildBannerURL(guild: GuildRecord, canAnimate?: boolean): string | null;
|
getGuildBannerURL(guild: GuildRecord, canAnimate?: boolean): string | null;
|
||||||
|
|
||||||
getChannelIconURL(data: { id: string; icon?: string | null | undefined; applicationId?: string; size?: number; }): string | undefined;
|
getChannelIconURL(data: { id: string; icon?: string | null | undefined; applicationId?: string; size?: number; }): string | undefined;
|
||||||
getEmojiURL(data: { id: string, animated: boolean, size: number, forcePNG?: boolean; }): string;
|
getEmojiURL(data: { id: string; animated: boolean; size: number; forcePNG?: boolean; }): string;
|
||||||
|
|
||||||
hasAnimatedGuildIcon(guild: GuildRecord): boolean;
|
hasAnimatedGuildIcon(guild: GuildRecord): boolean;
|
||||||
isAnimatedIconHash(hash: string): boolean;
|
isAnimatedIconHash(hash: string): boolean;
|
||||||
|
|
|
@ -53,12 +53,12 @@ const ToastPosition = {
|
||||||
};
|
};
|
||||||
|
|
||||||
export interface ToastData {
|
export interface ToastData {
|
||||||
message: string,
|
message: string;
|
||||||
id: string,
|
id: string;
|
||||||
/**
|
/**
|
||||||
* Toasts.Type
|
* Toasts.Type
|
||||||
*/
|
*/
|
||||||
type: number,
|
type: number;
|
||||||
options?: ToastOptions;
|
options?: ToastOptions;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -67,7 +67,7 @@ export interface ToastOptions {
|
||||||
* Toasts.Position
|
* Toasts.Position
|
||||||
*/
|
*/
|
||||||
position?: number;
|
position?: number;
|
||||||
component?: ReactNode,
|
component?: ReactNode;
|
||||||
duration?: number;
|
duration?: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -102,7 +102,7 @@ export function showToast(message: string, type = ToastType.MESSAGE, options?: T
|
||||||
}
|
}
|
||||||
|
|
||||||
export let AlertActionCreators: t.AlertActionCreators;
|
export let AlertActionCreators: t.AlertActionCreators;
|
||||||
waitFor(["show", "close"], m => AlertActionCreators = m);
|
waitFor(["show", "close"], m => { AlertActionCreators = m; });
|
||||||
|
|
||||||
export const ApplicationAssetUtils: {
|
export const ApplicationAssetUtils: {
|
||||||
fetchAssetIds: (applicationId: string, e: string[]) => Promise<string[]>;
|
fetchAssetIds: (applicationId: string, e: string[]) => Promise<string[]>;
|
||||||
|
@ -118,7 +118,7 @@ export const ClipboardUtils: t.ClipboardUtils = mapMangledModuleLazy('queryComma
|
||||||
});
|
});
|
||||||
|
|
||||||
export let ComponentDispatch: any;
|
export let ComponentDispatch: any;
|
||||||
waitFor(["ComponentDispatch", "ComponentDispatcher"], m => ComponentDispatch = m.ComponentDispatch);
|
waitFor(["ComponentDispatch", "ComponentDispatcher"], m => { ({ ComponentDispatch } = m); });
|
||||||
|
|
||||||
export const Constants = findByPropsLazy("Endpoints");
|
export const Constants = findByPropsLazy("Endpoints");
|
||||||
|
|
||||||
|
@ -149,7 +149,7 @@ export const InstantInviteActionCreators = findByPropsLazy("resolveInvite");
|
||||||
export const lodash: typeof import("lodash") = findByPropsLazy("debounce", "cloneDeep");
|
export const lodash: typeof import("lodash") = findByPropsLazy("debounce", "cloneDeep");
|
||||||
|
|
||||||
export let MarkupUtils: t.MarkupUtils;
|
export let MarkupUtils: t.MarkupUtils;
|
||||||
waitFor("parseTopic", m => MarkupUtils = m);
|
waitFor("parseTopic", m => { MarkupUtils = m; });
|
||||||
|
|
||||||
export const MessageActionCreators = findByPropsLazy("editMessage", "sendMessage");
|
export const MessageActionCreators = findByPropsLazy("editMessage", "sendMessage");
|
||||||
|
|
||||||
|
@ -176,7 +176,7 @@ export const RouterUtils: t.RouterUtils = mapMangledModuleLazy("Transitioning to
|
||||||
});
|
});
|
||||||
|
|
||||||
export let SnowflakeUtils: t.SnowflakeUtils;
|
export let SnowflakeUtils: t.SnowflakeUtils;
|
||||||
waitFor(["fromTimestamp", "extractTimestamp"], m => SnowflakeUtils = m);
|
waitFor(["fromTimestamp", "extractTimestamp"], m => { SnowflakeUtils = m; });
|
||||||
|
|
||||||
export const UploadAttachmentActionCreators = findByPropsLazy("clearAll", "addFile");
|
export const UploadAttachmentActionCreators = findByPropsLazy("clearAll", "addFile");
|
||||||
|
|
||||||
|
@ -187,7 +187,7 @@ export const UserActionCreators = {
|
||||||
export const UserProfileModalActionCreators = findByPropsLazy("openUserProfileModal", "closeUserProfileModal");
|
export const UserProfileModalActionCreators = findByPropsLazy("openUserProfileModal", "closeUserProfileModal");
|
||||||
|
|
||||||
export let UserSettingsModalActionCreators: any;
|
export let UserSettingsModalActionCreators: any;
|
||||||
waitFor(["open", "saveAccountChanges"], m => UserSettingsModalActionCreators = m);
|
waitFor(["open", "saveAccountChanges"], m => { UserSettingsModalActionCreators = m; });
|
||||||
|
|
||||||
export const UserUtils: t.UserUtils = findByPropsLazy("useName", "getGlobalName");
|
export const UserUtils: t.UserUtils = findByPropsLazy("useName", "getGlobalName");
|
||||||
|
|
||||||
|
|
|
@ -180,7 +180,7 @@ function patchFactories(factories: Record<string, (module: any, exports: any, re
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
exports = module.exports;
|
({ exports } = module);
|
||||||
|
|
||||||
if (!exports) return;
|
if (!exports) return;
|
||||||
|
|
||||||
|
@ -245,7 +245,7 @@ function patchFactories(factories: Record<string, (module: any, exports: any, re
|
||||||
logger.error("Error while firing callback for Webpack subscription:\n", err, filter, callback);
|
logger.error("Error while firing callback for Webpack subscription:\n", err, filter, callback);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
} as any as { toString: () => string, original: any, (...args: any[]): void; };
|
} as any as { toString: () => string; original: any; (...args: any[]): void; };
|
||||||
|
|
||||||
factory.toString = originalMod.toString.bind(originalMod);
|
factory.toString = originalMod.toString.bind(originalMod);
|
||||||
factory.original = originalMod;
|
factory.original = originalMod;
|
||||||
|
|
|
@ -603,7 +603,7 @@ export function waitFor(filter: string | PropsFilter | FilterFn, callback: Callb
|
||||||
else if (typeof filter !== "function")
|
else if (typeof filter !== "function")
|
||||||
throw new Error("filter must be a string, string[] or function, got " + typeof filter);
|
throw new Error("filter must be a string, string[] or function, got " + typeof filter);
|
||||||
|
|
||||||
// eslint-disable-next-line @typescript-eslint/no-unnecessary-condition
|
|
||||||
if (cache != null) {
|
if (cache != null) {
|
||||||
const [existing, id] = find(filter, { isIndirect: true, isWaitFor: true });
|
const [existing, id] = find(filter, { isIndirect: true, isWaitFor: true });
|
||||||
if (existing) {
|
if (existing) {
|
||||||
|
|
Loading…
Reference in a new issue