summaryrefslogtreecommitdiff
path: root/packages/frontend/src/scripts/get-note-menu.ts
diff options
context:
space:
mode:
Diffstat (limited to 'packages/frontend/src/scripts/get-note-menu.ts')
-rw-r--r--packages/frontend/src/scripts/get-note-menu.ts91
1 files changed, 66 insertions, 25 deletions
diff --git a/packages/frontend/src/scripts/get-note-menu.ts b/packages/frontend/src/scripts/get-note-menu.ts
index a409f1b775..40359a88bb 100644
--- a/packages/frontend/src/scripts/get-note-menu.ts
+++ b/packages/frontend/src/scripts/get-note-menu.ts
@@ -1,15 +1,16 @@
/*
- * SPDX-FileCopyrightText: syuilo and other misskey contributors
+ * SPDX-FileCopyrightText: syuilo and misskey-project
* SPDX-License-Identifier: AGPL-3.0-only
*/
-import { defineAsyncComponent, Ref } from 'vue';
+import { defineAsyncComponent, Ref, ShallowRef } from 'vue';
import * as Misskey from 'misskey-js';
import { claimAchievement } from './achievements.js';
import { $i } from '@/account.js';
import { i18n } from '@/i18n.js';
import { instance } from '@/instance.js';
import * as os from '@/os.js';
+import { misskeyApi } from '@/scripts/misskey-api.js';
import copyToClipboard from '@/scripts/copy-to-clipboard.js';
import { url } from '@/config.js';
import { defaultStore, noteActions } from '@/store.js';
@@ -35,18 +36,18 @@ export async function getNoteClipMenu(props: {
const appearNote = isRenote ? props.note.renote as Misskey.entities.Note : props.note;
const clips = await clipsCache.fetch();
- return [...clips.map(clip => ({
+ const menu: MenuItem[] = [...clips.map(clip => ({
text: clip.name,
action: () => {
claimAchievement('noteClipped1');
os.promiseDialog(
- os.api('clips/add-note', { clipId: clip.id, noteId: appearNote.id }),
+ misskeyApi('clips/add-note', { clipId: clip.id, noteId: appearNote.id }),
null,
async (err) => {
if (err.id === '734806c4-542c-463a-9311-15c512803965') {
const confirm = await os.confirm({
type: 'warning',
- text: i18n.t('confirmToUnclipAlreadyClippedNote', { name: clip.name }),
+ text: i18n.tsx.confirmToUnclipAlreadyClippedNote({ name: clip.name }),
});
if (!confirm.canceled) {
os.apiWithDialog('clips/remove-note', { clipId: clip.id, noteId: appearNote.id });
@@ -92,6 +93,8 @@ export async function getNoteClipMenu(props: {
os.apiWithDialog('clips/add-note', { clipId: clip.id, noteId: appearNote.id });
},
}];
+
+ return menu;
}
export function getAbuseNoteMenu(note: Misskey.entities.Note, text: string): MenuItem {
@@ -99,10 +102,13 @@ export function getAbuseNoteMenu(note: Misskey.entities.Note, text: string): Men
icon: 'ph-warning-circle ph-bold ph-lg',
text,
action: (): void => {
- const u = note.url ?? note.uri ?? `${url}/notes/${note.id}`;
+ const localUrl = `${url}/notes/${note.id}`;
+ let noteInfo = '';
+ if (note.url ?? note.uri != null) noteInfo = `Note: ${note.url ?? note.uri}\n`;
+ noteInfo += `Local Note: ${localUrl}\n`;
os.popup(defineAsyncComponent(() => import('@/components/MkAbuseReportWindow.vue')), {
user: note.user,
- initialComment: `Note: ${u}\n-----\n`,
+ initialComment: `${noteInfo}-----\n`,
}, {}, 'closed');
},
};
@@ -132,7 +138,6 @@ export function getCopyNoteOriginLinkMenu(note: misskey.entities.Note, text: str
export function getNoteMenu(props: {
note: Misskey.entities.Note;
- menuButton: Ref<HTMLElement>;
translation: Ref<Misskey.entities.NotesTranslateResponse | null>;
translating: Ref<boolean>;
isDeleted: Ref<boolean>;
@@ -156,7 +161,7 @@ export function getNoteMenu(props: {
}).then(({ canceled }) => {
if (canceled) return;
- os.api('notes/delete', {
+ misskeyApi('notes/delete', {
noteId: appearNote.id,
});
@@ -173,7 +178,7 @@ export function getNoteMenu(props: {
}).then(({ canceled }) => {
if (canceled) return;
- os.api('notes/delete', {
+ misskeyApi('notes/delete', {
noteId: appearNote.id,
});
@@ -252,7 +257,7 @@ export function getNoteMenu(props: {
function share(): void {
navigator.share({
- title: i18n.t('noteOf', { user: appearNote.user.name }),
+ title: i18n.tsx.noteOf({ user: appearNote.user.name }),
text: appearNote.text,
url: `${url}/notes/${appearNote.id}`,
});
@@ -265,7 +270,7 @@ export function getNoteMenu(props: {
async function translate(): Promise<void> {
if (props.translation.value != null) return;
props.translating.value = true;
- const res = await os.api('notes/translate', {
+ const res = await misskeyApi('notes/translate', {
noteId: appearNote.id,
targetLang: miLocalStorage.getItem('lang') ?? navigator.language,
});
@@ -275,7 +280,7 @@ export function getNoteMenu(props: {
let menu: MenuItem[];
if ($i) {
- const statePromise = os.api('notes/state', {
+ const statePromise = misskeyApi('notes/state', {
noteId: appearNote.id,
});
@@ -296,7 +301,7 @@ export function getNoteMenu(props: {
text: i18n.ts.copyContent,
action: copyContent,
}, getCopyNoteLinkMenu(appearNote, i18n.ts.copyLink)
- , (appearNote.url || appearNote.uri) ?
+ , (appearNote.url || appearNote.uri) ?
getCopyNoteOriginLinkMenu(appearNote, 'Copy link (Origin)')
: undefined,
(appearNote.url || appearNote.uri) ? {
@@ -355,7 +360,7 @@ export function getNoteMenu(props: {
icon: 'ph-user ph-bold ph-lg',
text: i18n.ts.user,
children: async () => {
- const user = appearNote.userId === $i?.id ? $i : await os.api('users/show', { userId: appearNote.userId });
+ const user = appearNote.userId === $i?.id ? $i : await misskeyApi('users/show', { userId: appearNote.userId });
const { menu, cleanup } = getUserMenu(user);
cleanups.push(cleanup);
return menu;
@@ -377,19 +382,55 @@ export function getNoteMenu(props: {
]
: []
),
+ ...(appearNote.channel && (appearNote.channel.userId === $i.id || $i.isModerator || $i.isAdmin) ? [
+ { type: 'divider' },
+ {
+ type: 'parent' as const,
+ icon: 'ti ti-device-tv',
+ text: i18n.ts.channel,
+ children: async () => {
+ const channelChildMenu = [] as MenuItem[];
+
+ const channel = await misskeyApi('channels/show', { channelId: appearNote.channel!.id });
+
+ if (channel.pinnedNoteIds.includes(appearNote.id)) {
+ channelChildMenu.push({
+ icon: 'ti ti-pinned-off',
+ text: i18n.ts.unpin,
+ action: () => os.apiWithDialog('channels/update', {
+ channelId: appearNote.channel!.id,
+ pinnedNoteIds: channel.pinnedNoteIds.filter(id => id !== appearNote.id),
+ }),
+ });
+ } else {
+ channelChildMenu.push({
+ icon: 'ti ti-pin',
+ text: i18n.ts.pin,
+ action: () => os.apiWithDialog('channels/update', {
+ channelId: appearNote.channel!.id,
+ pinnedNoteIds: [...channel.pinnedNoteIds, appearNote.id],
+ }),
+ });
+ }
+ return channelChildMenu;
+ },
+ },
+ ]
+ : []
+ ),
...(appearNote.userId === $i.id || $i.isModerator || $i.isAdmin ? [
{ type: 'divider' },
appearNote.userId === $i.id ? {
- icon: 'ph-pencil ph-bold ph-lg',
+ icon: 'ph-pencil-simple ph-bold ph-lg',
text: i18n.ts.edit,
action: edit,
} : undefined,
{
- icon: 'ph-pencil-line ph-bold ph-lg',
+ icon: 'ph-pencil-simple-line ph-bold ph-lg',
text: i18n.ts.deleteAndEdit,
danger: true,
action: delEdit,
- },
+ },
{
icon: 'ph-trash ph-bold ph-lg',
text: i18n.ts.delete,
@@ -409,7 +450,7 @@ export function getNoteMenu(props: {
text: i18n.ts.copyContent,
action: copyContent,
}, getCopyNoteLinkMenu(appearNote, i18n.ts.copyLink)
- , (appearNote.url || appearNote.uri) ?
+ , (appearNote.url || appearNote.uri) ?
getCopyNoteOriginLinkMenu(appearNote, 'Copy link (Origin)')
: undefined,
(appearNote.url || appearNote.uri) ? {
@@ -468,7 +509,7 @@ function smallerVisibility(a: Visibility | string, b: Visibility | string): Visi
export function getRenoteMenu(props: {
note: Misskey.entities.Note;
- renoteButton: Ref<HTMLElement>;
+ renoteButton: ShallowRef<HTMLElement | undefined>;
mock?: boolean;
}) {
const isRenote = (
@@ -488,7 +529,7 @@ export function getRenoteMenu(props: {
text: i18n.ts.inChannelRenote,
icon: 'ti ti-repeat',
action: () => {
- const el = props.renoteButton.value as HTMLElement | null | undefined;
+ const el = props.renoteButton.value;
if (el) {
const rect = el.getBoundingClientRect();
const x = rect.left + (el.offsetWidth / 2);
@@ -497,7 +538,7 @@ export function getRenoteMenu(props: {
}
if (!props.mock) {
- os.api('notes/create', {
+ misskeyApi('notes/create', {
renoteId: appearNote.id,
channelId: appearNote.channelId,
}).then(() => {
@@ -524,7 +565,7 @@ export function getRenoteMenu(props: {
text: i18n.ts.renote,
icon: 'ti ti-repeat',
action: () => {
- const el = props.renoteButton.value as HTMLElement | null | undefined;
+ const el = props.renoteButton.value;
if (el) {
const rect = el.getBoundingClientRect();
const x = rect.left + (el.offsetWidth / 2);
@@ -542,7 +583,7 @@ export function getRenoteMenu(props: {
}
if (!props.mock) {
- os.api('notes/create', {
+ misskeyApi('notes/create', {
localOnly,
visibility,
renoteId: appearNote.id,
@@ -564,7 +605,7 @@ export function getRenoteMenu(props: {
const renoteItems = [
...normalRenoteItems,
- ...(channelRenoteItems.length > 0 && normalRenoteItems.length > 0) ? [{ type: 'divider' }] : [],
+ ...(channelRenoteItems.length > 0 && normalRenoteItems.length > 0) ? [{ type: 'divider' }] as MenuItem[] : [],
...channelRenoteItems,
];