diff --git a/src/plugins/relationshipIndicators/README.md b/src/plugins/relationshipIndicators/README.md new file mode 100644 index 0000000000..a7ebe9d4a2 --- /dev/null +++ b/src/plugins/relationshipIndicators/README.md @@ -0,0 +1,16 @@ +# Relationship Indicators + +## Description +Adds a display to the badges, messages, and member list to indicate your relationship with the user. + + +### Friend Indicator +![friend indicator in chat](https://github.com/Vendicated/Vencord/assets/97131358/10a33c55-cbe5-4369-bb49-6f3aee59059c) +![friend indicator in member list](https://github.com/Vendicated/Vencord/assets/97131358/614653e6-b51b-4082-998d-d123fbac595f) +![friend indicator in profile (badge)](https://github.com/Vendicated/Vencord/assets/97131358/270c6667-e810-40a6-861a-40984f575aa6) + +### Blocked Indicator + +![blocked indicator in chat](https://github.com/Vendicated/Vencord/assets/97131358/bfdebf30-6b5c-480f-94fd-acc5cd736d9b) +![blocked indicator in member list](https://github.com/Vendicated/Vencord/assets/97131358/5054729a-e30c-4104-945b-8652df6cf71c) +![blocked indicator in profile (badge)](https://github.com/Vendicated/Vencord/assets/97131358/f0ee1279-ffa0-464d-b62a-3ff7d8d3a646) diff --git a/src/plugins/relationshipIndicators/icons.tsx b/src/plugins/relationshipIndicators/icons.tsx new file mode 100644 index 0000000000..6bc95ce51d --- /dev/null +++ b/src/plugins/relationshipIndicators/icons.tsx @@ -0,0 +1,49 @@ +/* + * Vencord, a Discord client mod + * Copyright (c) 2024 Vendicated and contributors + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +// uhh... can i put this in Icons.tsx? +import { Tooltip } from "@webpack/common"; + +type IconProps = { + tooltip?: string, + paths: { fill: string, path: string }[] + viewBox?: string +} + +function Icon(iconProps: IconProps) { + return ( + + {props => ( + + )} + + + ); +} + +export function FriendIcon() { + return ( + + ); +} + +export function BlockedIcon() { + return ( + + ); +} diff --git a/src/plugins/relationshipIndicators/index.tsx b/src/plugins/relationshipIndicators/index.tsx new file mode 100644 index 0000000000..b15972aa3e --- /dev/null +++ b/src/plugins/relationshipIndicators/index.tsx @@ -0,0 +1,85 @@ +/* + * Vencord, a Discord client mod + * Copyright (c) 2024 Vendicated and contributors + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +import { + addBadge, + BadgePosition, + ProfileBadge, + removeBadge +} from "@api/Badges"; +import { addDecorator, removeDecorator } from "@api/MemberListDecorators"; +import { addDecoration, removeDecoration } from "@api/MessageDecorations"; +import { definePluginSettings } from "@api/Settings"; +import ErrorBoundary from "@components/ErrorBoundary"; +import { Devs } from "@utils/constants"; +import definePlugin, { OptionType } from "@utils/types"; + +import { getBadges, RelationshipIndicator } from "./utils"; + +const indicatorLocations = { + list: { + description: "In the member list", + onEnable: () => addDecorator("friend-indicator", props => + + + + ), + onDisable: () => removeDecorator("friend-indicator") + }, + badges: { + description: "In user profiles, as badges", + onEnable: () => addBadge(badge), + onDisable: () => removeBadge(badge) + }, + messages: { + description: "Inside messages", + onEnable: () => addDecoration("friend-indicator", props => + + + + ), + onDisable: () => removeDecoration("friend-indicator") + } +}; + +const badge: ProfileBadge = { + getBadges, + position: BadgePosition.START +}; + +const settings = definePluginSettings({ + ...Object.fromEntries( + Object.entries(indicatorLocations).map(([key, value]) => { + return [key, { + type: OptionType.BOOLEAN, + description: `Show indicators ${value.description.toLowerCase()}`, + // onChange doesn't give any way to know which setting was changed, so restart required + restartNeeded: true, + default: true + }]; + }) + ), +}); + +export default definePlugin({ + name: "RelationshipIndicators", + authors: [Devs.Scyye], + settings, + description: "Adds icons to indicate relationships with users.", + start() { + Object.entries(indicatorLocations).forEach(([key, value]) => { + if (settings.store[key]) value.onEnable(); + }); + }, + stop() { + Object.entries(indicatorLocations).forEach(([key, value]) => { + if (settings.store[key]) value.onDisable(); + }); + }, +}); + + + diff --git a/src/plugins/relationshipIndicators/utils.tsx b/src/plugins/relationshipIndicators/utils.tsx new file mode 100644 index 0000000000..2a16ba7967 --- /dev/null +++ b/src/plugins/relationshipIndicators/utils.tsx @@ -0,0 +1,52 @@ +/* + * Vencord, a Discord client mod + * Copyright (c) 2024 Vendicated and contributors + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +import { BadgeUserArgs, ProfileBadge } from "@api/Badges"; +import { RelationshipStore, UserStore } from "@webpack/common"; +import { User } from "discord-types/general"; + +import { BlockedIcon, FriendIcon } from "./icons"; + +const shouldShowIndicator = (user?: User|null) => { + return user && !user.bot && (RelationshipStore.isFriend(user.id) || RelationshipStore.isBlocked(user.id)); +}; + +export const RelationshipIndicator = ({ user, wantMargin = true, wantTopMargin = false }: { user: User; wantMargin?: boolean; wantTopMargin?: boolean; }) => { + if (!shouldShowIndicator(user)) return null; + + return ( + + {RelationshipStore.isFriend(user.id)? : } + + ); +}; + +export function getBadges({ userId }: BadgeUserArgs): ProfileBadge[] { + const user = UserStore.getUser(userId); + if (!shouldShowIndicator(user)) return []; + + return [{ + component: () => ( + + + + ), + key: `vc-${RelationshipStore.isFriend(userId)?"friend":"blocked"}-indicator`, + }]; +} diff --git a/src/utils/constants.ts b/src/utils/constants.ts index c399baafea..572247e024 100644 --- a/src/utils/constants.ts +++ b/src/utils/constants.ts @@ -533,6 +533,10 @@ export const Devs = /* #__PURE__*/ Object.freeze({ Antti: { name: "Antti", id: 312974985876471810n + }, + Scyye: { + name: "Scyye", + id: 553652308295155723n } } satisfies Record);