mindnet_obsidian/src/unresolvedLink/unresolvedLinkHandler.ts

122 lines
3.5 KiB
TypeScript
Raw Normal View History

/**
* Unresolved link click handler for Reading View and Live Preview.
*/
import { App, MarkdownPostProcessorContext, Notice } from "obsidian";
import type { InterviewConfig } from "../interview/types";
import { ProfileSelectionModal } from "../ui/ProfileSelectionModal";
import {
extractLinkTargetFromAnchor,
isUnresolvedLink,
waitForFileModify,
} from "./linkHelpers";
import type { MindnetSettings } from "../settings";
import { TFile } from "obsidian";
export interface UnresolvedLinkClickContext {
mode: "reading" | "live";
linkText: string;
sourcePath: string;
resolved: boolean;
}
/**
* Check if bypass modifier is pressed.
*/
export function isBypassModifierPressed(
evt: MouseEvent,
bypassModifier: "Alt" | "Ctrl" | "Shift" | "None"
): boolean {
if (bypassModifier === "None") return false;
if (bypassModifier === "Alt") return evt.altKey;
if (bypassModifier === "Ctrl") return evt.ctrlKey || evt.metaKey;
if (bypassModifier === "Shift") return evt.shiftKey;
return false;
}
/**
* Start wizard after note creation, with optional Templater wait.
*/
export async function startWizardAfterCreate(
app: App,
settings: MindnetSettings,
file: TFile,
profile: any,
content: string,
isUnresolvedClick: boolean,
onWizardComplete: (result: any) => void,
onWizardSave: (result: any) => void,
pluginInstance?: { ensureGraphSchemaLoaded?: () => Promise<import("../mapping/graphSchema").GraphSchema | null> },
initialPendingEdgeAssignments?: import("../interview/wizardState").PendingEdgeAssignment[]
): Promise<void> {
// Determine if wizard should start
const shouldStartInterview = isUnresolvedClick
? (settings.autoStartOnUnresolvedClick || settings.autoStartInterviewOnCreate)
: settings.autoStartInterviewOnCreate;
if (!shouldStartInterview) {
if (settings.debugLogging) {
console.log("[Mindnet] Wizard start skipped (settings)");
}
return;
}
// Wait for Templater if enabled
if (settings.waitForFirstModifyAfterCreate) {
if (settings.debugLogging) {
console.log(
`[Mindnet] Waiting for file modify (timeout: ${settings.waitForModifyTimeoutMs}ms)`
);
}
const result = await waitForFileModify(
app,
file,
settings.waitForModifyTimeoutMs
);
if (settings.debugLogging) {
console.log(`[Mindnet] File modify wait result: ${result}`);
}
// Reload file content in case Templater modified it
if (result === "modified") {
content = await app.vault.read(file);
}
}
// Start wizard
try {
if (settings.debugLogging) {
console.log("[Mindnet] Starting wizard", {
profileKey: profile.key,
file: file.path,
wizardStartReason: isUnresolvedClick
? settings.autoStartOnUnresolvedClick
? "autoStartOnUnresolvedClick"
: "autoStartInterviewOnCreate"
: "autoStartInterviewOnCreate",
});
}
const { InterviewWizardModal } = await import("../ui/InterviewWizardModal");
new InterviewWizardModal(
app,
profile,
file,
content,
onWizardComplete,
onWizardSave,
settings, // Pass settings for post-run edging
pluginInstance, // Pass plugin instance for graph schema loading
initialPendingEdgeAssignments // Pass initial edge assignments
).open();
} catch (e) {
const msg = e instanceof Error ? e.message : String(e);
new Notice(`Failed to start interview wizard: ${msg}`);
console.error("[Mindnet] Failed to start wizard:", e);
}
}