mirror of
https://github.com/Sqaaakoi/vc-newPluginsManager.git
synced 2024-11-16 14:54:37 -05:00
New Settings menu update
This commit is contained in:
parent
4518705185
commit
317c386933
3 changed files with 91 additions and 49 deletions
|
@ -8,12 +8,14 @@ import { useSettings } from "@api/Settings";
|
||||||
import { classNameFactory } from "@api/Styles";
|
import { classNameFactory } from "@api/Styles";
|
||||||
import { PluginCard } from "@components/PluginSettings";
|
import { PluginCard } from "@components/PluginSettings";
|
||||||
import { ChangeList } from "@utils/ChangeList";
|
import { ChangeList } from "@utils/ChangeList";
|
||||||
import { ModalContent, ModalFooter, ModalHeader, ModalProps, ModalRoot, ModalSize, openModal } from "@utils/modal";
|
import { ModalCloseButton, ModalContent, ModalFooter, ModalHeader, ModalProps, ModalRoot, ModalSize, openModal } from "@utils/modal";
|
||||||
import { Alerts, Button, Flex, Forms, Parser, React, Text, Tooltip, useMemo } from "@webpack/common";
|
import { useForceUpdater } from "@utils/react";
|
||||||
|
import { Button, Flex, Forms, Parser, React, Text, Tooltip, useMemo } from "@webpack/common";
|
||||||
|
import { JSX } from "react";
|
||||||
|
|
||||||
import Plugins from "~plugins";
|
import Plugins from "~plugins";
|
||||||
|
|
||||||
import { getNewPlugins, writeKnownPlugins } from "./knownPlugins";
|
import { getNewPlugins, getNewSettings, KnownPluginSettingsMap, writeKnownSettings } from "./knownSettings";
|
||||||
|
|
||||||
const cl = classNameFactory("vc-plugins-");
|
const cl = classNameFactory("vc-plugins-");
|
||||||
|
|
||||||
|
@ -21,29 +23,10 @@ let hasSeen = false;
|
||||||
|
|
||||||
// Most of this was stolen from PluginSettings directly.
|
// Most of this was stolen from PluginSettings directly.
|
||||||
|
|
||||||
export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalProps; newPlugins: Set<string>; }) {
|
export function NewPluginsModal({ modalProps, newPlugins, newSettings }: { modalProps: ModalProps; newPlugins: Set<string>; newSettings: KnownPluginSettingsMap; }) {
|
||||||
const settings = useSettings();
|
const settings = useSettings();
|
||||||
const changes = React.useMemo(() => new ChangeList<string>(), []);
|
const changes = React.useMemo(() => new ChangeList<string>(), []);
|
||||||
|
let updateContinueButton = () => { };
|
||||||
React.useEffect(() => {
|
|
||||||
return () => void (changes.hasChanges && Alerts.show({
|
|
||||||
title: "Restart required",
|
|
||||||
body: (
|
|
||||||
<>
|
|
||||||
<p>The following plugins require a restart:</p>
|
|
||||||
<div>{changes.map((s, i) => (
|
|
||||||
<>
|
|
||||||
{i > 0 && ", "}
|
|
||||||
{Parser.parse("`" + s + "`")}
|
|
||||||
</>
|
|
||||||
))}</div>
|
|
||||||
</>
|
|
||||||
),
|
|
||||||
confirmText: "Restart now",
|
|
||||||
cancelText: "Later!",
|
|
||||||
onConfirm: () => location.reload()
|
|
||||||
}));
|
|
||||||
}, []);
|
|
||||||
|
|
||||||
const depMap = React.useMemo(() => {
|
const depMap = React.useMemo(() => {
|
||||||
const o = {} as Record<string, string[]>;
|
const o = {} as Record<string, string[]>;
|
||||||
|
@ -59,8 +42,13 @@ export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalP
|
||||||
return o;
|
return o;
|
||||||
}, []);
|
}, []);
|
||||||
|
|
||||||
const sortedPlugins = useMemo(() => [...newPlugins].map(pn => Plugins[pn])
|
const mapPlugins = (array: string[]) => array.map(pn => Plugins[pn])
|
||||||
.sort((a, b) => a.name.localeCompare(b.name)), []);
|
.sort((a, b) => a.name.localeCompare(b.name));
|
||||||
|
|
||||||
|
const sortedPlugins = useMemo(() => [
|
||||||
|
...mapPlugins([...newPlugins]),
|
||||||
|
...mapPlugins([...newSettings.keys()].filter(p => !newPlugins.has(p)))
|
||||||
|
], []);
|
||||||
|
|
||||||
const plugins = [] as JSX.Element[];
|
const plugins = [] as JSX.Element[];
|
||||||
const requiredPlugins = [] as JSX.Element[];
|
const requiredPlugins = [] as JSX.Element[];
|
||||||
|
@ -82,10 +70,14 @@ export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalP
|
||||||
<PluginCard
|
<PluginCard
|
||||||
onMouseLeave={onMouseLeave}
|
onMouseLeave={onMouseLeave}
|
||||||
onMouseEnter={onMouseEnter}
|
onMouseEnter={onMouseEnter}
|
||||||
onRestartNeeded={name => changes.handleChange(name)}
|
onRestartNeeded={name => {
|
||||||
|
changes.handleChange(name);
|
||||||
|
updateContinueButton();
|
||||||
|
}}
|
||||||
disabled={true}
|
disabled={true}
|
||||||
plugin={p}
|
plugin={p}
|
||||||
key={p.name}
|
key={p.name}
|
||||||
|
isNew={newPlugins.has(p.name)}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</Tooltip>
|
</Tooltip>
|
||||||
|
@ -93,10 +85,14 @@ export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalP
|
||||||
} else {
|
} else {
|
||||||
plugins.push(
|
plugins.push(
|
||||||
<PluginCard
|
<PluginCard
|
||||||
onRestartNeeded={name => changes.handleChange(name)}
|
onRestartNeeded={name => {
|
||||||
|
changes.handleChange(name);
|
||||||
|
updateContinueButton();
|
||||||
|
}}
|
||||||
disabled={false}
|
disabled={false}
|
||||||
plugin={p}
|
plugin={p}
|
||||||
key={p.name}
|
key={p.name}
|
||||||
|
isNew={newPlugins.has(p.name)}
|
||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
@ -105,7 +101,16 @@ export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalP
|
||||||
|
|
||||||
return <ModalRoot {...modalProps} size={ModalSize.MEDIUM} >
|
return <ModalRoot {...modalProps} size={ModalSize.MEDIUM} >
|
||||||
<ModalHeader>
|
<ModalHeader>
|
||||||
<Text variant="heading-lg/semibold">New Plugins ({[...plugins, ...requiredPlugins].length})</Text>
|
<Text variant="heading-lg/semibold">New Plugins and Settings ({[...plugins, ...requiredPlugins].length})</Text>
|
||||||
|
<Tooltip text="Dismiss for this session">
|
||||||
|
{tooltipProps =>
|
||||||
|
<ModalCloseButton
|
||||||
|
{...tooltipProps}
|
||||||
|
onClick={modalProps.onClose}
|
||||||
|
className={cl("close")}
|
||||||
|
/>
|
||||||
|
}
|
||||||
|
</Tooltip>
|
||||||
</ModalHeader>
|
</ModalHeader>
|
||||||
<ModalContent>
|
<ModalContent>
|
||||||
<div className={cl("grid")}>
|
<div className={cl("grid")}>
|
||||||
|
@ -114,20 +119,46 @@ export function NewPluginsModal({ modalProps, newPlugins }: { modalProps: ModalP
|
||||||
</ModalContent>
|
</ModalContent>
|
||||||
<ModalFooter>
|
<ModalFooter>
|
||||||
<Flex direction={Flex.Direction.HORIZONTAL_REVERSE}>
|
<Flex direction={Flex.Direction.HORIZONTAL_REVERSE}>
|
||||||
<Button
|
<ContinueButton
|
||||||
color={Button.Colors.GREEN}
|
close={modalProps.onClose}
|
||||||
onClick={async () => {
|
changes={changes}
|
||||||
await writeKnownPlugins();
|
callback={(v: () => void) => updateContinueButton = v}
|
||||||
modalProps.onClose();
|
/>
|
||||||
}}
|
|
||||||
>
|
|
||||||
Continue
|
|
||||||
</Button>
|
|
||||||
</Flex>
|
</Flex>
|
||||||
</ModalFooter>
|
</ModalFooter>
|
||||||
</ModalRoot>;
|
</ModalRoot>;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
function ContinueButton(props: { callback: (update: () => void) => void; changes: ChangeList<string>; close: () => any; }) {
|
||||||
|
const update = useForceUpdater();
|
||||||
|
props.callback(update);
|
||||||
|
return <Tooltip
|
||||||
|
text={<>
|
||||||
|
The following plugins require a restart:
|
||||||
|
<div>{props.changes.map((s, i) => (
|
||||||
|
<>
|
||||||
|
{i > 0 && ", "}
|
||||||
|
{Parser.parse("`" + s + "`")}
|
||||||
|
</>
|
||||||
|
))}</div>
|
||||||
|
</>}
|
||||||
|
shouldShow={props.changes.hasChanges}
|
||||||
|
>
|
||||||
|
{tooltipProps =>
|
||||||
|
<Button
|
||||||
|
{...tooltipProps}
|
||||||
|
color={Button.Colors.GREEN}
|
||||||
|
onClick={async () => {
|
||||||
|
await writeKnownSettings();
|
||||||
|
props.changes.hasChanges ? location.reload() : props.close();
|
||||||
|
}}
|
||||||
|
>
|
||||||
|
{props.changes.hasChanges ? "Restart" : "Continue"}
|
||||||
|
</Button>
|
||||||
|
}
|
||||||
|
</Tooltip>;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
function makeDependencyList(deps: string[]) {
|
function makeDependencyList(deps: string[]) {
|
||||||
return (
|
return (
|
||||||
|
@ -140,12 +171,14 @@ function makeDependencyList(deps: string[]) {
|
||||||
|
|
||||||
export async function openNewPluginsModal() {
|
export async function openNewPluginsModal() {
|
||||||
const newPlugins = await getNewPlugins();
|
const newPlugins = await getNewPlugins();
|
||||||
if (newPlugins.size && !hasSeen) {
|
const newSettings = await getNewSettings();
|
||||||
|
if (newSettings.size && !hasSeen) {
|
||||||
hasSeen = true;
|
hasSeen = true;
|
||||||
openModal(modalProps => (
|
openModal(modalProps => (
|
||||||
<NewPluginsModal
|
<NewPluginsModal
|
||||||
modalProps={modalProps}
|
modalProps={modalProps}
|
||||||
newPlugins={newPlugins}
|
newPlugins={newPlugins}
|
||||||
|
newSettings={newSettings}
|
||||||
/>
|
/>
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,19 +7,22 @@
|
||||||
import { Devs } from "@utils/constants";
|
import { Devs } from "@utils/constants";
|
||||||
import definePlugin from "@utils/types";
|
import definePlugin from "@utils/types";
|
||||||
|
|
||||||
import { KNOWN_PLUGINS_DATA_KEY } from "./knownPlugins";
|
import * as KnownSettings from "./knownSettings";
|
||||||
|
import { KNOWN_PLUGINS_LEGACY_DATA_KEY, KNOWN_SETTINGS_DATA_KEY } from "./knownSettings";
|
||||||
import { openNewPluginsModal } from "./NewPluginsModal";
|
import { openNewPluginsModal } from "./NewPluginsModal";
|
||||||
|
|
||||||
export default definePlugin({
|
export default definePlugin({
|
||||||
name: "NewPluginsManager",
|
name: "NewPluginsManager",
|
||||||
description: "Utility that notifies you when new plugins are added to Vencord",
|
description: "Utility that notifies you when new plugins are added to Vencord",
|
||||||
authors: [Devs.Sqaaakoi],
|
authors: [Devs.Sqaaakoi],
|
||||||
enabledByDefault: true,
|
enabledByDefault: true, // This is intentional.
|
||||||
flux: {
|
flux: {
|
||||||
async POST_CONNECTION_OPEN() {
|
async POST_CONNECTION_OPEN() {
|
||||||
openNewPluginsModal();
|
openNewPluginsModal();
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
openNewPluginsModal,
|
openNewPluginsModal,
|
||||||
KNOWN_PLUGINS_DATA_KEY
|
KNOWN_PLUGINS_LEGACY_DATA_KEY,
|
||||||
|
KNOWN_SETTINGS_DATA_KEY,
|
||||||
|
KnownSettings
|
||||||
});
|
});
|
||||||
|
|
|
@ -11,11 +11,6 @@ import plugins from "~plugins";
|
||||||
|
|
||||||
export type KnownPluginSettingsMap = Map<string, Set<string>>;
|
export type KnownPluginSettingsMap = Map<string, Set<string>>;
|
||||||
|
|
||||||
type PluginSettings = {
|
|
||||||
[setting: string]: any;
|
|
||||||
enabled?: boolean;
|
|
||||||
};
|
|
||||||
|
|
||||||
export const KNOWN_PLUGINS_LEGACY_DATA_KEY = "NewPluginsManager_KnownPlugins";
|
export const KNOWN_PLUGINS_LEGACY_DATA_KEY = "NewPluginsManager_KnownPlugins";
|
||||||
export const KNOWN_SETTINGS_DATA_KEY = "NewPluginsManager_KnownSettings";
|
export const KNOWN_SETTINGS_DATA_KEY = "NewPluginsManager_KnownSettings";
|
||||||
|
|
||||||
|
@ -35,7 +30,7 @@ export async function getKnownSettings(): Promise<KnownPluginSettingsMap> {
|
||||||
let map = await DataStore.get(KNOWN_SETTINGS_DATA_KEY) as KnownPluginSettingsMap;
|
let map = await DataStore.get(KNOWN_SETTINGS_DATA_KEY) as KnownPluginSettingsMap;
|
||||||
if (map === undefined) {
|
if (map === undefined) {
|
||||||
const knownPlugins = await DataStore.get(KNOWN_PLUGINS_LEGACY_DATA_KEY) ?? [] as string[];
|
const knownPlugins = await DataStore.get(KNOWN_PLUGINS_LEGACY_DATA_KEY) ?? [] as string[];
|
||||||
DataStore.del(KNOWN_PLUGINS_LEGACY_DATA_KEY);
|
// DataStore.del(KNOWN_PLUGINS_LEGACY_DATA_KEY);
|
||||||
const Plugins = [...Object.keys(plugins), ...knownPlugins];
|
const Plugins = [...Object.keys(plugins), ...knownPlugins];
|
||||||
map = getCurrentSettings(Plugins);
|
map = getCurrentSettings(Plugins);
|
||||||
DataStore.set(KNOWN_SETTINGS_DATA_KEY, map);
|
DataStore.set(KNOWN_SETTINGS_DATA_KEY, map);
|
||||||
|
@ -48,7 +43,7 @@ export async function getNewSettings(): Promise<KnownPluginSettingsMap> {
|
||||||
const knownSettings = await getKnownSettings();
|
const knownSettings = await getKnownSettings();
|
||||||
map.forEach((settings, plugin) => {
|
map.forEach((settings, plugin) => {
|
||||||
const filteredSettings = [...settings].filter(setting => !knownSettings.get(plugin)?.has(setting));
|
const filteredSettings = [...settings].filter(setting => !knownSettings.get(plugin)?.has(setting));
|
||||||
if (filteredSettings.length === 0 && knownSettings.has(plugin)) return map.delete(plugin);
|
if (!filteredSettings.length) return map.delete(plugin);
|
||||||
map.set(plugin, new Set(filteredSettings));
|
map.set(plugin, new Set(filteredSettings));
|
||||||
});
|
});
|
||||||
return map;
|
return map;
|
||||||
|
@ -77,3 +72,14 @@ export async function writeKnownSettings() {
|
||||||
});
|
});
|
||||||
await DataStore.set(KNOWN_SETTINGS_DATA_KEY, allSettings);
|
await DataStore.set(KNOWN_SETTINGS_DATA_KEY, allSettings);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export async function debugWipeSomeData() {
|
||||||
|
const settings = await getKnownSettings();
|
||||||
|
settings.forEach((value, key) => {
|
||||||
|
if (Math.random() > 0.8) {
|
||||||
|
if (Math.random() > 0.5) return settings.set(key, new Set([...value].filter(() => Math.random() > 0.5)));
|
||||||
|
return settings.delete(key);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
await DataStore.set(KNOWN_SETTINGS_DATA_KEY, settings);
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in a new issue