mirror of
https://github.com/zadam/trilium.git
synced 2026-09-12 19:50:20 +05:00
105 lines
4.5 KiB
TypeScript
105 lines
4.5 KiB
TypeScript
import type { GeoMouseEvent } from "../widgets/collections/geomap/map.js";
|
|
|
|
import appContext, { type CommandNames } from "../components/app_context.js";
|
|
import { t } from "../services/i18n.js";
|
|
import type { ViewScope } from "../services/link.js";
|
|
import utils, { isMobile } from "../services/utils.js";
|
|
import { getClosestNtxId } from "../widgets/widget_utils.js";
|
|
import contextMenu, { type ContextMenuEvent, type MenuItem } from "./context_menu.js";
|
|
|
|
function openContextMenu(notePath: string, e: ContextMenuEvent, viewScope: ViewScope = {}, hoistedNoteId: string | null = null) {
|
|
contextMenu.show({
|
|
x: e.pageX,
|
|
y: e.pageY,
|
|
items: getItems(e),
|
|
selectMenuItemHandler: ({ command }) => handleLinkContextMenuItem(command, e, notePath, viewScope, hoistedNoteId)
|
|
});
|
|
}
|
|
|
|
function getItems(e: ContextMenuEvent | GeoMouseEvent): MenuItem<CommandNames>[] {
|
|
return [ ...getOpenItems(e), getQuickEditItem() ];
|
|
}
|
|
|
|
/** The places the note can be opened in, without the quick edit popup. */
|
|
function getOpenItems(e: ContextMenuEvent | GeoMouseEvent): MenuItem<CommandNames>[] {
|
|
const ntxId = getNtxId(e);
|
|
const isMobileSplitOpen = isMobile() && appContext.tabManager.getNoteContextById(ntxId).getMainContext().getSubContexts().length > 1;
|
|
|
|
return [
|
|
{ title: t("link_context_menu.open_note_in_new_tab"), command: "openNoteInNewTab", uiIcon: "bx bx-link-external" },
|
|
{ title: !isMobileSplitOpen ? t("link_context_menu.open_note_in_new_split") : t("link_context_menu.open_note_in_other_split"), command: "openNoteInNewSplit", uiIcon: "bx bx-dock-right" },
|
|
{ title: t("link_context_menu.open_note_in_new_window"), command: "openNoteInNewWindow", uiIcon: "bx bx-window-open" }
|
|
];
|
|
}
|
|
|
|
/** Opens the note in a popup over the current one. */
|
|
function getQuickEditItem(): MenuItem<CommandNames> {
|
|
return { title: t("link_context_menu.open_note_in_popup"), command: "openNoteInPopup", uiIcon: "bx bx-edit" };
|
|
}
|
|
|
|
/**
|
|
* The same places, folded into one submenu, for a menu that lists entries of its own beside them.
|
|
*
|
|
* The items keep their commands, so `handleLinkContextMenuItem` handles them from a submenu as it
|
|
* does from the top level. The entry carries the first of those commands itself, so that picking it
|
|
* opens a new tab without going into the submenu for the place it is opened in most often.
|
|
*/
|
|
function getOpenNoteItem(e: ContextMenuEvent | GeoMouseEvent): MenuItem<CommandNames> {
|
|
return {
|
|
title: t("link_context_menu.open_note"),
|
|
uiIcon: "bx bx-link-external",
|
|
command: "openNoteInNewTab",
|
|
items: getOpenItems(e)
|
|
};
|
|
}
|
|
|
|
function handleLinkContextMenuItem(command: string | undefined, e: ContextMenuEvent | GeoMouseEvent, notePath: string, viewScope = {}, hoistedNoteId: string | null = null) {
|
|
if (!hoistedNoteId) {
|
|
hoistedNoteId = appContext.tabManager.getActiveContext()?.hoistedNoteId ?? null;
|
|
}
|
|
|
|
if (command === "openNoteInNewTab") {
|
|
appContext.tabManager.openContextWithNote(notePath, { hoistedNoteId, viewScope });
|
|
return true;
|
|
} else if (command === "openNoteInNewSplit") {
|
|
const ntxId = getNtxId(e);
|
|
if (!ntxId) return false;
|
|
appContext.triggerCommand("openNewNoteSplit", { ntxId, notePath, hoistedNoteId, viewScope });
|
|
return true;
|
|
} else if (command === "openNoteInNewWindow") {
|
|
appContext.triggerCommand("openInWindow", { notePath, hoistedNoteId, viewScope });
|
|
return true;
|
|
} else if (command === "openNoteInPopup") {
|
|
appContext.triggerCommand("openInPopup", { noteIdOrPath: notePath, viewScope });
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
|
|
function getNtxId(e: ContextMenuEvent | GeoMouseEvent) {
|
|
if (utils.isDesktop()) {
|
|
const subContexts = appContext.tabManager.getActiveContext()?.getSubContexts();
|
|
if (!subContexts) return null;
|
|
return subContexts[subContexts.length - 1].ntxId;
|
|
} else {
|
|
const target = "originalEvent" in e ? e.originalEvent?.target : e.target;
|
|
if (target instanceof HTMLElement) {
|
|
const closest = getClosestNtxId(target);
|
|
if (closest) return closest;
|
|
}
|
|
}
|
|
// Fallback: when the event originates outside any note-context DOM
|
|
// (e.g. mobile sidebar), target the currently active context so downstream
|
|
// lookups don't fail with a null ntxId.
|
|
return appContext.tabManager.activeNtxId ?? null;
|
|
}
|
|
|
|
export default {
|
|
getItems,
|
|
getQuickEditItem,
|
|
getOpenNoteItem,
|
|
handleLinkContextMenuItem,
|
|
openContextMenu
|
|
};
|