pi-weave 0.3.9 → 0.3.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,7 +1,5 @@
1
1
  /** The vault and repository tree column. */
2
2
 
3
- import type { TrailMark } from "../trail/trail.model";
4
- import { trailRowClass } from "../trail/trail.model";
5
3
  import { NOTE_DRAG_TYPE } from "../shell/shell.model";
6
4
  import { useLayoutEffect, useRef, useState } from "preact/hooks";
7
5
  import { createFolder, deleteFolder, deleteNote, moveNote, renameFolder, renameNote } from "../api";
@@ -48,8 +46,6 @@ export interface TreeProps {
48
46
  graph: GraphPayload | null;
49
47
  selectedId: string | null;
50
48
  recentIds: ReadonlySet<string>;
51
- /** Recall-trail glows by row id (`trail/trail.model.ts`). */
52
- trail?: ReadonlyMap<string, TrailMark>;
53
49
  onSelect: (id: string, newTab?: boolean, keepSidebar?: boolean) => void;
54
50
  /**
55
51
  * Ask before a mutation that would invalidate an open draft. `false` means
@@ -80,13 +76,13 @@ export function Icon({ name, class: className }: { name: IconName; class?: strin
80
76
  );
81
77
  }
82
78
 
83
- function Row({ view, recentIds, trail, edit, onEdit, onRename, onSelect, onToggle, onMenu, onDrop }: { view: ReturnType<typeof rowViews>[number]; recentIds: ReadonlySet<string>; trail: TrailMark | undefined; edit: string | null; onEdit: (value: string) => void; onRename: (value: string | null) => void; onSelect: (newTab: boolean) => void; onToggle: () => void; onMenu: (x: number, y: number) => void; onDrop: (id: string) => void }) {
79
+ function Row({ view, recentIds, edit, onEdit, onRename, onSelect, onToggle, onMenu, onDrop }: { view: ReturnType<typeof rowViews>[number]; recentIds: ReadonlySet<string>; edit: string | null; onEdit: (value: string) => void; onRename: (value: string | null) => void; onSelect: (newTab: boolean) => void; onToggle: () => void; onMenu: (x: number, y: number) => void; onDrop: (id: string) => void }) {
84
80
  const folder = dropFolder(view.id);
85
81
  return (
86
82
  <li
87
83
  id={view.domId}
88
84
  data-row-id={view.id}
89
- class={`weave-row weave-row-${view.kind}${view.selected ? " weave-row-on" : ""}${recentIds.has(view.id) ? " weave-row-new" : ""}${trailRowClass(trail)}`}
85
+ class={`weave-row weave-row-${view.kind}${view.selected ? " weave-row-on" : ""}${recentIds.has(view.id) ? " weave-row-new" : ""}`}
90
86
  role="treeitem"
91
87
  aria-level={view.level}
92
88
  aria-posinset={view.posinset}
@@ -301,7 +297,7 @@ export function Tree(props: TreeProps) {
301
297
  setMenu({ id: "vault", label: "Vault", x: event.clientX, y: event.clientY });
302
298
  }}
303
299
  >
304
- {rowViews(rows, props.selectedId, props.now).map((view) => <Row key={view.id} view={view} recentIds={props.recentIds} trail={props.trail?.get(view.id)} edit={editing?.id === view.id ? editing.value : null} onEdit={(value) => setEditing((current) => current === null ? null : { ...current, value })} onRename={commitEdit} onSelect={(newTab) => { props.onSelect(view.id, newTab); if (view.hasKids) setState((current) => toggleExpanded(current, view.id)); }} onToggle={() => setState(toggleExpanded(state, view.id))} onMenu={(x, y) => setMenu({ id: view.id, label: view.label, x, y })} onDrop={(dragged) => { const folder = dropFolder(view.id); if (dragged.startsWith("note:") && folder !== undefined) { const target = mutableTreeRow(dragged); if (target !== null && !props.onMutate(affectedNoteSlugs(props.graph, target))) return; void run(moveNote(fetchJson, dragged.slice("note:".length), folder)); } }} />)}
300
+ {rowViews(rows, props.selectedId, props.now).map((view) => <Row key={view.id} view={view} recentIds={props.recentIds} edit={editing?.id === view.id ? editing.value : null} onEdit={(value) => setEditing((current) => current === null ? null : { ...current, value })} onRename={commitEdit} onSelect={(newTab) => { props.onSelect(view.id, newTab); if (view.hasKids) setState((current) => toggleExpanded(current, view.id)); }} onToggle={() => setState(toggleExpanded(state, view.id))} onMenu={(x, y) => setMenu({ id: view.id, label: view.label, x, y })} onDrop={(dragged) => { const folder = dropFolder(view.id); if (dragged.startsWith("note:") && folder !== undefined) { const target = mutableTreeRow(dragged); if (target !== null && !props.onMutate(affectedNoteSlugs(props.graph, target))) return; void run(moveNote(fetchJson, dragged.slice("note:".length), folder)); } }} />)}
305
301
  </ul>
306
302
  ) : <p class="weave-tree-empty">{empty}</p>}
307
303
  <p class="weave-tree-count">{rowCountLabel(rows)}</p>
@@ -3,7 +3,7 @@
3
3
  * `light` and `dark` keep existing saved choices compatible.
4
4
  */
5
5
  const latte = {
6
- bg: "#eff1f5", panel: "#e6e9ef", page: "#dce0e8", raise: "#ccd0da",
6
+ bg: "#eff1f5", panel: "#e6e9ef", page: "#ffffff", raise: "#ccd0da",
7
7
  fg: "#4c4f69", dim: "#56586a", faint: "#606274", line: "#ccd0da", "line-strong": "#bcc0cc",
8
8
  accent: "#7113ec", ok: "#28641b", warn: "#7c4f10", bad: "#b20d30",
9
9
  };
@@ -27,6 +27,11 @@ export interface WorkspaceLayout {
27
27
  readonly ratio: number;
28
28
  readonly treeVisible: boolean;
29
29
  readonly contextVisible: boolean;
30
+ /**
31
+ * Context as a docked column (true) or a card floating over the page's
32
+ * right margin (false, the default since the refresh).
33
+ */
34
+ readonly contextPinned: boolean;
30
35
  readonly treeWidth: number;
31
36
  readonly contextWidth: number;
32
37
  readonly contextGraphHeight: number;
@@ -50,6 +55,7 @@ export function initialLayout(): WorkspaceLayout {
50
55
  ratio: 0.5,
51
56
  treeVisible: true,
52
57
  contextVisible: true,
58
+ contextPinned: false,
53
59
  treeWidth: 240,
54
60
  contextWidth: 240,
55
61
  contextGraphHeight: 260,
@@ -246,11 +252,13 @@ function boundedId(value: unknown, prefix?: "pane" | "tab"): value is string {
246
252
  }
247
253
 
248
254
  export function parseWorkspaceLayout(value: unknown): WorkspaceLayout | null {
249
- if (!record(value) || !exactKeys(value, ["version", "panes", "activePane", "split", "ratio", "treeVisible", "contextVisible", "treeWidth", "contextWidth", "theme", ...["preferences", "contextGraphHeight", "contextTagsHeight"].filter(key => Object.hasOwn(value, key))])) return null;
255
+ if (!record(value) || !exactKeys(value, ["version", "panes", "activePane", "split", "ratio", "treeVisible", "contextVisible", "treeWidth", "contextWidth", "theme", ...["preferences", "contextGraphHeight", "contextTagsHeight", "contextPinned"].filter(key => Object.hasOwn(value, key))])) return null;
250
256
  if (value["version"] !== 1 || !Array.isArray(value["panes"]) || value["panes"].length < 1 || value["panes"].length > 2 || !boundedId(value["activePane"], "pane")) return null;
251
257
  if (value["split"] !== "right" && value["split"] !== "down") return null;
252
258
  if (typeof value["ratio"] !== "number" || !Number.isFinite(value["ratio"]) || value["ratio"] < 0.1 || value["ratio"] > 0.9) return null;
253
259
  if (typeof value["treeVisible"] !== "boolean" || typeof value["contextVisible"] !== "boolean") return null;
260
+ const contextPinned = Object.hasOwn(value, "contextPinned") ? value["contextPinned"] : false;
261
+ if (typeof contextPinned !== "boolean") return null;
254
262
  if (typeof value["treeWidth"] !== "number" || !Number.isFinite(value["treeWidth"]) || value["treeWidth"] < 120 || value["treeWidth"] > 800) return null;
255
263
  if (typeof value["contextWidth"] !== "number" || !Number.isFinite(value["contextWidth"]) || value["contextWidth"] < 120 || value["contextWidth"] > 800) return null;
256
264
  const contextGraphHeight = Object.hasOwn(value, "contextGraphHeight") ? value["contextGraphHeight"] : 260;
@@ -292,7 +300,7 @@ export function parseWorkspaceLayout(value: unknown): WorkspaceLayout | null {
292
300
  panes.push({ id: rawPane["id"], tabs, activeTab: rawPane["activeTab"], ...(typeof lastDocumentTab === "string" ? { lastDocumentTab } : {}) });
293
301
  }
294
302
  if (count > MAX_TABS || graphs > 1 || !panes.some((pane) => pane.id === value["activePane"])) return null;
295
- return { version: 1, panes, activePane: value["activePane"], split: value["split"], ratio: value["ratio"], treeVisible: value["treeVisible"], contextVisible: value["contextVisible"], treeWidth: value["treeWidth"], contextWidth: value["contextWidth"], contextGraphHeight, contextTagsHeight, theme: value["theme"], preferences };
303
+ return { version: 1, panes, activePane: value["activePane"], split: value["split"], ratio: value["ratio"], treeVisible: value["treeVisible"], contextVisible: value["contextVisible"], contextPinned, treeWidth: value["treeWidth"], contextWidth: value["contextWidth"], contextGraphHeight, contextTagsHeight, theme: value["theme"], preferences };
296
304
  }
297
305
 
298
306
  /** Startup choice resets navigation only; appearance and sidebar preferences survive. */