chore(react/ribbon): react to add new label/relation even when not shown

This commit is contained in:
Elian Doran 2025-08-27 13:05:51 +03:00
parent 9d760a21d5
commit 066f3ea078
No known key found for this signature in database
5 changed files with 25 additions and 53 deletions

View File

@ -28,50 +28,6 @@ export default class RibbonContainer extends NoteContextAwareWidget {
this.buttonWidgets = []; this.buttonWidgets = [];
} }
isRibbonTabActive(name: string) {
const $ribbonComponent = this.$widget.find(`.ribbon-tab-title[data-ribbon-component-name='${name}']`);
return $ribbonComponent.hasClass("active");
}
ensureOwnedAttributesAreOpen(ntxId: string | null | undefined) {
if (ntxId && this.isNoteContext(ntxId) && !this.isRibbonTabActive("ownedAttributes")) {
this.toggleRibbonTabWithName("ownedAttributes", ntxId);
}
}
addNewLabelEvent({ ntxId }: EventData<"addNewLabel">) {
this.ensureOwnedAttributesAreOpen(ntxId);
}
addNewRelationEvent({ ntxId }: EventData<"addNewRelation">) {
this.ensureOwnedAttributesAreOpen(ntxId);
}
toggleRibbonTabWithName(name: string, ntxId?: string) {
if (!this.isNoteContext(ntxId)) {
return false;
}
const $ribbonComponent = this.$widget.find(`.ribbon-tab-title[data-ribbon-component-name='${name}']`);
if ($ribbonComponent) {
this.toggleRibbonTab($ribbonComponent);
}
}
handleEvent<T extends EventNames>(name: T, data: EventData<T>) {
const PREFIX = "toggleRibbonTab";
if (name.startsWith(PREFIX)) {
let componentName = name.substr(PREFIX.length);
componentName = componentName[0].toLowerCase() + componentName.substr(1);
this.toggleRibbonTabWithName(componentName, (data as any).ntxId);
} else {
return super.handleEvent(name, data);
}
}
async handleEventInChildren<T extends EventNames>(name: T, data: EventData<T>) { async handleEventInChildren<T extends EventNames>(name: T, data: EventData<T>) {
if (["activeContextChanged", "setNoteContext"].includes(name)) { if (["activeContextChanged", "setNoteContext"].includes(name)) {

View File

@ -1,11 +1,14 @@
import { useTriliumEvents } from "../react/hooks";
import AttributeEditor from "./components/AttributeEditor"; import AttributeEditor from "./components/AttributeEditor";
import { TabContext } from "./ribbon-interface"; import { TabContext } from "./ribbon-interface";
export default function OwnedAttributesTab({ note, ...restProps }: TabContext) { export default function OwnedAttributesTab({ note, hidden, activate, ...restProps }: TabContext) {
useTriliumEvents([ "addNewLabel", "addNewRelation" ], activate);
return ( return (
<div className="attribute-list"> <div className="attribute-list">
{ note && ( { note && (
<AttributeEditor note={note} {...restProps} /> <AttributeEditor note={note} {...restProps} hidden={hidden} />
)} )}
</div> </div>
) )

View File

@ -1,6 +1,6 @@
import { useCallback, useEffect, useMemo, useRef, useState } from "preact/hooks"; import { useCallback, useEffect, useMemo, useRef, useState } from "preact/hooks";
import { t } from "../../services/i18n"; import { t } from "../../services/i18n";
import { useNoteContext, useStaticTooltip, useTooltip, useTriliumEvents } from "../react/hooks"; import { useNoteContext, useStaticTooltip, useTooltip, useTriliumEvent, useTriliumEvents } from "../react/hooks";
import "./style.css"; import "./style.css";
import { VNode } from "preact"; import { VNode } from "preact";
import BasicPropertiesTab from "./BasicPropertiesTab"; import BasicPropertiesTab from "./BasicPropertiesTab";
@ -39,7 +39,7 @@ interface TabConfiguration {
toggleCommand?: KeyboardActionNames; toggleCommand?: KeyboardActionNames;
activate?: boolean | ((context: TitleContext) => boolean); activate?: boolean | ((context: TitleContext) => boolean);
/** /**
* By default the tab content will not be rendered unless the tab is active (i.e. selected by the user). Setting to `true` will ensure that the tab is rendered even when inactive, for cases where the tab needs to be accessible at all times (e.g. for the detached editor toolbar). * By default the tab content will not be rendered unless the tab is active (i.e. selected by the user). Setting to `true` will ensure that the tab is rendered even when inactive, for cases where the tab needs to be accessible at all times (e.g. for the detached editor toolbar) or if event handling is needed.
*/ */
stayInDom?: boolean; stayInDom?: boolean;
} }
@ -119,7 +119,8 @@ const TAB_CONFIGURATION = numberObjectsInPlace<TabConfiguration>([
icon: "bx bx-list-check", icon: "bx bx-list-check",
content: OwnedAttributesTab, content: OwnedAttributesTab,
show: ({note}) => !note?.isLaunchBarConfig(), show: ({note}) => !note?.isLaunchBarConfig(),
toggleCommand: "toggleRibbonTabOwnedAttributes" toggleCommand: "toggleRibbonTabOwnedAttributes",
stayInDom: true
}, },
{ {
title: t("inherited_attribute_list.title"), title: t("inherited_attribute_list.title"),
@ -228,7 +229,10 @@ export default function Ribbon() {
hoistedNoteId, hoistedNoteId,
notePath, notePath,
noteContext, noteContext,
componentId componentId,
activate: useCallback(() => {
setActiveTabIndex(tab.index)
}, [setActiveTabIndex])
}); });
})} })}
</div> </div>

View File

@ -74,7 +74,15 @@ const mentionSetup: MentionFeed[] = [
]; ];
export default function AttributeEditor({ note, componentId, notePath, ntxId }: { note: FNote, componentId: string, notePath?: string | null, ntxId?: string | null }) { interface AttributeEditorProps {
note: FNote;
componentId: string;
notePath?: string | null;
ntxId?: string | null;
hidden?: boolean;
}
export default function AttributeEditor({ note, componentId, notePath, ntxId, hidden }: AttributeEditorProps) {
const [ state, setState ] = useState<"normal" | "showHelpTooltip" | "showAttributeDetail">(); const [ state, setState ] = useState<"normal" | "showHelpTooltip" | "showAttributeDetail">();
const [ error, setError ] = useState<unknown>(); const [ error, setError ] = useState<unknown>();
const [ needsSaving, setNeedsSaving ] = useState(false); const [ needsSaving, setNeedsSaving ] = useState(false);
@ -267,7 +275,7 @@ export default function AttributeEditor({ note, componentId, notePath, ntxId }:
return ( return (
<> <>
<div {!hidden && <div
ref={wrapperRef} ref={wrapperRef}
style="position: relative; padding-top: 10px; padding-bottom: 10px" style="position: relative; padding-top: 10px; padding-bottom: 10px"
onKeyDown={(e) => { onKeyDown={(e) => {
@ -379,7 +387,7 @@ export default function AttributeEditor({ note, componentId, notePath, ntxId }:
{getErrorMessage(error)} {getErrorMessage(error)}
</div> </div>
)} )}
</div> </div>}
{attributeDetailWidgetEl} {attributeDetailWidgetEl}
</> </>

View File

@ -9,4 +9,5 @@ export interface TabContext {
notePath?: string | null; notePath?: string | null;
noteContext?: NoteContext; noteContext?: NoteContext;
componentId: string; componentId: string;
activate(): void;
} }