From b618e5a00f6c456b49a37f679f53c27774467888 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Fri, 13 Feb 2026 22:50:03 +0200 Subject: [PATCH 01/26] client: define the foundation of sectioned cards with multi-level nesting --- apps/client/src/widgets/react/Card.css | 36 +++++++++++++++++++++ apps/client/src/widgets/react/Card.tsx | 43 ++++++++++++++++++++++++++ 2 files changed, 79 insertions(+) create mode 100644 apps/client/src/widgets/react/Card.css create mode 100644 apps/client/src/widgets/react/Card.tsx diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css new file mode 100644 index 0000000000..ea906cc0a8 --- /dev/null +++ b/apps/client/src/widgets/react/Card.css @@ -0,0 +1,36 @@ +.tn-card { + --card-border-radius: 8px; + --card-padding: 8px 16px; + --card-section-gap: 3px; + + display: flex; + flex-direction: column; + gap: var(--card-section-gap); + + .tn-card-section { + padding: var(--card-padding); + border: 1px solid var(--card-border-color); + background: var(--card-background-color); + + &:first-of-type { + border-top-left-radius: var(--card-border-radius); + border-top-right-radius: var(--card-border-radius); + } + + &:last-of-type { + border-bottom-left-radius: var(--card-border-radius); + border-bottom-right-radius: var(--card-border-radius); + } + + &.tn-card-section-nested { + padding-left: calc(30px * var(--tn-card-section-nesting-level)); + opacity: .5; + } + + &.tn-action:hover { + background-color: var(--card-background-hover-color); + transition: background-color .2s ease-out; + } + + } +} \ No newline at end of file diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx new file mode 100644 index 0000000000..fa6a0f489f --- /dev/null +++ b/apps/client/src/widgets/react/Card.tsx @@ -0,0 +1,43 @@ +import "./Card.css"; +import { ComponentChildren, createContext } from "preact"; +import { JSX } from "preact"; +import { useContext } from "preact/hooks"; +import clsx from "clsx"; + +interface CardProps { +} + +export function Card(props: {children: ComponentChildren} & CardProps) { + return
+ {props.children} +
; +} + +interface CardSectionProps { + subSections?: JSX.Element | JSX.Element[]; + childrenVisible?: boolean; +} + +export function CardSection(props: {children: ComponentChildren} & CardSectionProps) { + const parentContext = useContext(CardSectionContext); + const nestingLevel = (parentContext && parentContext.nestingLevel + 1) ?? 0; + + return <> +
0}])} + style={"--tn-card-section-nesting-level: " + nestingLevel}> + {props.children} {nestingLevel} +
+ + {props?.childrenVisible && + + {props.subSections} + + } + ; +} + +interface CardSectionContextType { + nestingLevel: number; +} + +export const CardSectionContext = createContext(undefined); \ No newline at end of file From be12658864448d24d9beacab8ff07280548d3303 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 00:08:00 +0200 Subject: [PATCH 02/26] client/ui/cards: add support for custom class names and action callbacks --- apps/client/src/widgets/react/Card.tsx | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx index fa6a0f489f..1573c2fe0b 100644 --- a/apps/client/src/widgets/react/Card.tsx +++ b/apps/client/src/widgets/react/Card.tsx @@ -5,17 +5,21 @@ import { useContext } from "preact/hooks"; import clsx from "clsx"; interface CardProps { + className?: string; } export function Card(props: {children: ComponentChildren} & CardProps) { - return
+ return
{props.children}
; } interface CardSectionProps { + className?: string; subSections?: JSX.Element | JSX.Element[]; childrenVisible?: boolean; + hasAction: boolean; + onAction?: () => void; } export function CardSection(props: {children: ComponentChildren} & CardSectionProps) { @@ -23,9 +27,13 @@ export function CardSection(props: {children: ComponentChildren} & CardSectionPr const nestingLevel = (parentContext && parentContext.nestingLevel + 1) ?? 0; return <> -
0}])} - style={"--tn-card-section-nesting-level: " + nestingLevel}> - {props.children} {nestingLevel} +
0, + "tn-action": props?.hasAction} + ], props.className)} + style={"--tn-card-section-nesting-level: " + nestingLevel} + onClick={() => {props.onAction?.()}}> + {props.children}
{props?.childrenVisible && From 62ddf3a11bf430b5c680a20f8cfe70c91d898e87 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 00:08:59 +0200 Subject: [PATCH 03/26] client/ui/cards: automatically determine the opacity of the background color of nested card sections --- apps/client/src/widgets/react/Card.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index ea906cc0a8..d717354be1 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -24,7 +24,7 @@ &.tn-card-section-nested { padding-left: calc(30px * var(--tn-card-section-nesting-level)); - opacity: .5; + background-color: color-mix(in srgb, var(--card-background-color) calc(100% / (var(--tn-card-section-nesting-level) + 1)) , transparent); } &.tn-action:hover { From 61953fd7132ebee7e6e06f77357cf43213b23582 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 00:10:54 +0200 Subject: [PATCH 04/26] client/ui/cards: make a property optional --- apps/client/src/widgets/react/Card.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx index 1573c2fe0b..34eea094af 100644 --- a/apps/client/src/widgets/react/Card.tsx +++ b/apps/client/src/widgets/react/Card.tsx @@ -18,7 +18,7 @@ interface CardSectionProps { className?: string; subSections?: JSX.Element | JSX.Element[]; childrenVisible?: boolean; - hasAction: boolean; + hasAction?: boolean; onAction?: () => void; } From 218343ca144882f3a6d4406e60f3206374588ecc Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 01:14:54 +0200 Subject: [PATCH 05/26] client/list view: use a sectioned card to display the list items --- .../collections/legacy/ListOrGridView.css | 35 +++++++++++++++++-- .../collections/legacy/ListOrGridView.tsx | 33 ++++++++++------- apps/client/src/widgets/react/Card.css | 3 +- 3 files changed, 56 insertions(+), 15 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 1bfa389e5c..ef609c1d0d 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -102,9 +102,8 @@ .note-expander { font-size: x-large; - position: relative; - top: 3px; cursor: pointer; + opacity: .65; } .note-list-pager { @@ -117,6 +116,38 @@ opacity: 0.5; } +:root .list-view-card { + --card-nested-section-indent: 40px; +} + +.note-list h5 { + display: flex; + align-items: center; + font-size: 1em; + margin: 0; + + .tn-icon { + color: var(--left-pane-icon-color); + margin-inline-end: 8px; + font-size: 1.2em; + } + + .note-book-title { + color: inherit; + } + + .note-list-attributes { + flex-grow: 1; + text-align: right; + font-size: .75em; + opacity: .75; + } +} + +.note-content-preview:has(.note-book-content:empty) { + display: none; +} + /* #region Grid view */ .note-list.grid-view .note-list-container { display: flex; diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index 61c7193a6e..6bf77c644f 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -1,4 +1,5 @@ import "./ListOrGridView.css"; +import { Card, CardSection } from "../../react/Card"; import { useEffect, useRef, useState } from "preact/hooks"; @@ -33,7 +34,7 @@ export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens } { noteIds.length > 0 &&
{!hasCollectionProperties && } - +
} @@ -93,27 +94,35 @@ function ListNoteCard({ note, parentNote, highlightedTokens, currentLevel, expan // Reset expand state if switching to another note, or if user manually toggled expansion state. useEffect(() => setExpanded(currentLevel <= expandDepth), [ note, currentLevel, expandDepth ]); + const children = <> + {isExpanded && <> + + + + + } + + return ( -
setExpanded(!isExpanded)} data-note-id={note.noteId} > -
+
setExpanded(!isExpanded)} + onClick={(e) => {setExpanded(!isExpanded); e.stopPropagation();}} />
- - {isExpanded && <> - - - } -
+ ); } diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index d717354be1..53fd889b21 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -2,6 +2,7 @@ --card-border-radius: 8px; --card-padding: 8px 16px; --card-section-gap: 3px; + --card-nested-section-indent: 30px; display: flex; flex-direction: column; @@ -23,7 +24,7 @@ } &.tn-card-section-nested { - padding-left: calc(30px * var(--tn-card-section-nesting-level)); + padding-left: calc(8px + (var(--card-nested-section-indent) * var(--tn-card-section-nesting-level))); background-color: color-mix(in srgb, var(--card-background-color) calc(100% / (var(--tn-card-section-nesting-level) + 1)) , transparent); } From fe4a11c5adf01fc37a7a53a87c50d54c67c72fb7 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 16:22:13 +0200 Subject: [PATCH 06/26] client/list view: improve appearance --- .../collections/legacy/ListOrGridView.css | 119 +++++++++++++----- .../collections/legacy/ListOrGridView.tsx | 44 ++++--- apps/client/src/widgets/react/Card.css | 2 +- apps/client/src/widgets/react/Card.tsx | 12 +- 4 files changed, 125 insertions(+), 52 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index ef609c1d0d..d393c2496b 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -100,50 +100,111 @@ overflow: auto; } -.note-expander { - font-size: x-large; - cursor: pointer; - opacity: .65; -} - .note-list-pager { text-align: center; } -.note-list.list-view .note-path { - margin-left: 0.5em; - vertical-align: middle; - opacity: 0.5; +@keyframes note-preview-show { + from { + opacity: 0; + } to { + opacity: 1; + } } -:root .list-view-card { +.nested-note-list { --card-nested-section-indent: 40px; -} -.note-list h5 { - display: flex; - align-items: center; - font-size: 1em; - margin: 0; + h5 { + display: flex; + align-items: center; + font-size: 1em; + font-weight: normal; + margin: 0; - .tn-icon { - color: var(--left-pane-icon-color); - margin-inline-end: 8px; - font-size: 1.2em; + .note-expander { + font-size: x-large; + cursor: pointer; + opacity: .65; + margin-inline-end: 4px; + } + + .tn-icon { + color: var(--left-pane-icon-color); + margin-inline-end: 8px; + font-size: 1.2em; + } + + .note-book-title { + color: inherit; + font-weight: normal; + } + + .note-path { + margin-left: 0.5em; + vertical-align: middle; + opacity: 0.5; + order: -1; + } + + .note-list-attributes { + flex-grow: 1; + text-align: right; + font-size: .75em; + opacity: .75; + } } - .note-book-title { - color: inherit; - } + .note-book-content { + --background: rgba(0, 0, 0, .2); + outline: 1px solid var(--background); + border-radius: 8px; + background-color: var(--background); + overflow: hidden; + user-select: text; + animation: note-preview-show .25s ease-out; + will-change: opacity; - .note-list-attributes { - flex-grow: 1; - text-align: right; - font-size: .75em; - opacity: .75; + > .rendered-content > *:last-child { + margin-bottom: 0; + } + + &.type-text { + padding: 8px 24px; + + .ck-content > *:last-child { + margin-bottom: 0; + } + } + + &.type-protectedSession { + padding: 20px; + } + + &.type-image { + padding: 0; + } + + &.type-pdf { + iframe { + height: 50vh; + } + + .file-footer { + padding: 8px; + } + } + + &.type-webView { + display: flex; + flex-direction: column; + justify-content: center; + min-height: 50vh; + } } } + .note-content-preview:has(.note-book-content:empty) { display: none; } diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index 6bf77c644f..a1bbd6916d 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -15,6 +15,7 @@ import NoteLink from "../../react/NoteLink"; import { ViewModeProps } from "../interface"; import { Pager, usePagination } from "../Pagination"; import { filterChildNotes, useFilteredNoteIds } from "./utils"; +import { JSX } from "preact/jsx-runtime"; export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens }: ViewModeProps<{}>) { const expandDepth = useExpansionDepth(note); @@ -34,7 +35,7 @@ export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens } { noteIds.length > 0 &&
{!hasCollectionProperties && } - + {pageNotes?.map(childNote => ( setExpanded(currentLevel <= expandDepth), [ note, currentLevel, expandDepth ]); - const children = <> - {isExpanded && <> + let subSections: JSX.Element | undefined = undefined; + if (isExpanded) { + subSections = <> - + - - } - + + + } + return ( setExpanded(!isExpanded)} data-note-id={note.noteId} >
- {setExpanded(!isExpanded); e.stopPropagation();}} - /> - + - +
@@ -198,7 +209,8 @@ export function NoteContent({ note, trim, noChildrenList, highlightedTokens, inc }); }, [ note, highlightedTokens ]); - return
; + return
+
; } function NoteChildren({ note, parentNote, highlightedTokens, currentLevel, expandDepth, includeArchived }: { diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index 53fd889b21..4a5b53f82a 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -24,7 +24,7 @@ } &.tn-card-section-nested { - padding-left: calc(8px + (var(--card-nested-section-indent) * var(--tn-card-section-nesting-level))); + padding-left: calc(var(--card-nested-section-indent) * var(--tn-card-section-nesting-level)); background-color: color-mix(in srgb, var(--card-background-color) calc(100% / (var(--tn-card-section-nesting-level) + 1)) , transparent); } diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx index 34eea094af..c717ee5433 100644 --- a/apps/client/src/widgets/react/Card.tsx +++ b/apps/client/src/widgets/react/Card.tsx @@ -27,16 +27,16 @@ export function CardSection(props: {children: ComponentChildren} & CardSectionPr const nestingLevel = (parentContext && parentContext.nestingLevel + 1) ?? 0; return <> -
0, - "tn-action": props?.hasAction} - ], props.className)} - style={"--tn-card-section-nesting-level: " + nestingLevel} - onClick={() => {props.onAction?.()}}> + "tn-action": props.hasAction + })} + style={{"--tn-card-section-nesting-level": nestingLevel}} + onClick={props.onAction}> {props.children}
- {props?.childrenVisible && + {props.childrenVisible && {props.subSections} From 9c13f36ca03058e3d22331f935c4cda2472d192d Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sat, 14 Feb 2026 16:39:20 +0200 Subject: [PATCH 07/26] client/list view: show the contents of a note only after its rendering completes --- .../src/widgets/collections/legacy/ListOrGridView.css | 5 +++++ .../src/widgets/collections/legacy/ListOrGridView.tsx | 10 ++++++++-- 2 files changed, 13 insertions(+), 2 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index d393c2496b..d4596afe88 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -156,6 +156,7 @@ } .note-book-content { + display: none; --background: rgba(0, 0, 0, .2); outline: 1px solid var(--background); border-radius: 8px; @@ -165,6 +166,10 @@ animation: note-preview-show .25s ease-out; will-change: opacity; + &.note-book-content-ready { + display: block; + } + > .rendered-content > *:last-child { margin-bottom: 0; } diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index a1bbd6916d..3a3b2c9974 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -16,6 +16,7 @@ import { ViewModeProps } from "../interface"; import { Pager, usePagination } from "../Pagination"; import { filterChildNotes, useFilteredNoteIds } from "./utils"; import { JSX } from "preact/jsx-runtime"; +import { clsx } from "clsx"; export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens }: ViewModeProps<{}>) { const expandDepth = useExpansionDepth(note); @@ -185,6 +186,9 @@ export function NoteContent({ note, trim, noChildrenList, highlightedTokens, inc const contentRef = useRef(null); const highlightSearch = useImperativeSearchHighlighlighting(highlightedTokens); + const [ready, setReady] = useState(false); + const [noteType, setNoteType] = useState("none"); + useEffect(() => { content_renderer.getRenderedContent(note, { trim, @@ -199,17 +203,19 @@ export function NoteContent({ note, trim, noChildrenList, highlightedTokens, inc } else { contentRef.current.replaceChildren(); } - contentRef.current.classList.add(`type-${type}`); highlightSearch(contentRef.current); + setNoteType(type); + setReady(true); }) .catch(e => { console.warn(`Caught error while rendering note '${note.noteId}' of type '${note.type}'`); console.error(e); contentRef.current?.replaceChildren(t("collections.rendering_error")); + setReady(true); }); }, [ note, highlightedTokens ]); - return
+ return
; } From a6cbde88bbfa4b6430ec99c0f092122797d8bac2 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 01:57:10 +0200 Subject: [PATCH 08/26] client/list view: add an alternate style for search results --- .../collections/legacy/ListOrGridView.css | 42 +++++++++++++++++++ .../collections/legacy/ListOrGridView.tsx | 6 +-- 2 files changed, 45 insertions(+), 3 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index d4596afe88..6685025383 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -209,6 +209,48 @@ } } +.nested-note-list.search-results { + span.tn-icon + span > span { + display: flex; + flex-direction: column-reverse; + align-items: flex-start; + } + + small { + line-height: .85em; + } + + .note-path { + margin-left: 0; + font-size: .85em; + line-height: .85em; + font-weight: 500; + letter-spacing: .5pt; + } + + .tn-icon { + display: flex; + justify-content: center; + align-items: center; + margin-inline-end: 12px; + background: rgb(88, 88, 88); + border-radius: 50%; + width: 1.75em; + height: 1.75em; + font-size: 1.2em; + } + + .note-book-title { + --link-hover-background: transparent; + } + + .ck-find-result { + background: transparent; + color: var(--quick-search-result-highlight-color); + font-weight: 600; + text-decoration: underline; + } +} .note-content-preview:has(.note-book-content:empty) { display: none; diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index 3a3b2c9974..1eba122f9b 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -36,7 +36,7 @@ export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens } { noteIds.length > 0 &&
{!hasCollectionProperties && } - + {pageNotes?.map(childNote => ( setExpanded(!isExpanded)} data-note-id={note.noteId} >
- + setExpanded(!isExpanded)}/> Date: Sun, 15 Feb 2026 02:26:23 +0200 Subject: [PATCH 09/26] client/list view: add a menu button for list items --- .../src/widgets/collections/legacy/ListOrGridView.css | 4 ++++ .../src/widgets/collections/legacy/ListOrGridView.tsx | 6 ++++++ 2 files changed, 10 insertions(+) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 6685025383..018db0a6c7 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -153,6 +153,10 @@ font-size: .75em; opacity: .75; } + + .nested-note-list-item-menu { + margin-inline-start: 8px; + } } .note-book-content { diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index 1eba122f9b..be244cbbe7 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -17,6 +17,8 @@ import { Pager, usePagination } from "../Pagination"; import { filterChildNotes, useFilteredNoteIds } from "./utils"; import { JSX } from "preact/jsx-runtime"; import { clsx } from "clsx"; +import ActionButton from "../../react/ActionButton"; +import linkContextMenuService from "../../../menus/link_context_menu"; export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens }: ViewModeProps<{}>) { const expandDepth = useExpansionDepth(note); @@ -133,6 +135,10 @@ function ListNoteCard({ note, parentNote, highlightedTokens, currentLevel, expan showNotePath={parentNote.type === "search"} highlightedTokens={highlightedTokens} /> + {linkContextMenuService.openContextMenu(notePath, e); e.stopPropagation()}} + />
); From 3774ea37683aed52e9e64229bfb9a9c5c06173cf Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 02:28:52 +0200 Subject: [PATCH 10/26] style/list view: tweak --- apps/client/src/widgets/collections/legacy/ListOrGridView.css | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 018db0a6c7..e1d55a8680 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -234,6 +234,7 @@ .tn-icon { display: flex; + flex-shrink: 0; justify-content: center; align-items: center; margin-inline-end: 12px; From dca201ce42ea27b02b77da18622286fdc3416915 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 13:31:45 +0200 Subject: [PATCH 11/26] style/list view: tweak --- .../src/stylesheets/theme-next-dark.css | 9 + .../src/stylesheets/theme-next-light.css | 9 + .../src/stylesheets/theme-next/shell.css | 6 +- .../collections/legacy/ListOrGridView.css | 208 +++++++++--------- 4 files changed, 131 insertions(+), 101 deletions(-) diff --git a/apps/client/src/stylesheets/theme-next-dark.css b/apps/client/src/stylesheets/theme-next-dark.css index f8fb305726..e74180a230 100644 --- a/apps/client/src/stylesheets/theme-next-dark.css +++ b/apps/client/src/stylesheets/theme-next-dark.css @@ -290,6 +290,15 @@ --ck-editor-toolbar-button-on-shadow: 1px 1px 2px rgba(0, 0, 0, .75); --ck-editor-toolbar-dropdown-button-open-background: #ffffff14; + --note-list-view-icon-color: var(--left-pane-icon-color); + --note-list-view-large-icon-background: var(--note-icon-background-color); + --note-list-view-large-icon-color: var(--note-icon-color); + --note-list-view-search-result-highlight-background: transparent; + --note-list-view-search-result-highlight-color: var(--quick-search-result-highlight-color); + --note-list-view-content-background: rgba(0, 0, 0, .2); + --note-list-view-content-search-result-highlight-background: var(--quick-search-result-highlight-color); + --note-list-view-content-search-result-highlight-color: white; + --calendar-coll-event-background-saturation: 25%; --calendar-coll-event-background-lightness: 20%; --calendar-coll-event-background-color: #3c3c3c; diff --git a/apps/client/src/stylesheets/theme-next-light.css b/apps/client/src/stylesheets/theme-next-light.css index 2d7862ae00..70883f2368 100644 --- a/apps/client/src/stylesheets/theme-next-light.css +++ b/apps/client/src/stylesheets/theme-next-light.css @@ -288,6 +288,15 @@ --ck-editor-toolbar-button-on-shadow: none; --ck-editor-toolbar-dropdown-button-open-background: #0000000f; + --note-list-view-icon-color: var(--left-pane-icon-color); + --note-list-view-large-icon-background: var(--note-icon-background-color); + --note-list-view-large-icon-color: var(--note-icon-color); + --note-list-view-search-result-highlight-background: transparent; + --note-list-view-search-result-highlight-color: var(--quick-search-result-highlight-color); + --note-list-view-content-background: #b1b1b133; + --note-list-view-content-search-result-highlight-background: var(--quick-search-result-highlight-color); + --note-list-view-content-search-result-highlight-color: white; + --calendar-coll-event-background-lightness: 95%; --calendar-coll-event-background-saturation: 80%; --calendar-coll-event-background-color: #eaeaea; diff --git a/apps/client/src/stylesheets/theme-next/shell.css b/apps/client/src/stylesheets/theme-next/shell.css index 0df9d6686a..1ac2f13e77 100644 --- a/apps/client/src/stylesheets/theme-next/shell.css +++ b/apps/client/src/stylesheets/theme-next/shell.css @@ -751,12 +751,14 @@ body[dir=rtl] #left-pane span.fancytree-node.protected > span.fancytree-custom-i } } -#left-pane .fancytree-expander { +#left-pane .fancytree-expander, +.nested-note-list-item .note-expander { opacity: 0.65; transition: opacity 150ms ease-in; } -#left-pane .fancytree-expander:hover { +#left-pane .fancytree-expander:hover, +.nested-note-list-item .note-expander:hover { opacity: 1; transition: opacity 300ms ease-out; } diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index e1d55a8680..7a09e177f8 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -104,6 +104,8 @@ text-align: center; } +/* #region List view */ + @keyframes note-preview-show { from { opacity: 0; @@ -112,108 +114,57 @@ } } -.nested-note-list { +:root .nested-note-list { --card-nested-section-indent: 40px; +} - h5 { - display: flex; - align-items: center; - font-size: 1em; - font-weight: normal; - margin: 0; +/* List item */ +.nested-note-list-item h5 { + display: flex; + align-items: center; + font-size: 1em; + font-weight: normal; + margin: 0; - .note-expander { - font-size: x-large; - cursor: pointer; - opacity: .65; - margin-inline-end: 4px; - } - - .tn-icon { - color: var(--left-pane-icon-color); - margin-inline-end: 8px; - font-size: 1.2em; - } - - .note-book-title { - color: inherit; - font-weight: normal; - } - - .note-path { - margin-left: 0.5em; - vertical-align: middle; - opacity: 0.5; - order: -1; - } - - .note-list-attributes { - flex-grow: 1; - text-align: right; - font-size: .75em; - opacity: .75; - } - - .nested-note-list-item-menu { - margin-inline-start: 8px; - } + .note-expander { + margin-inline-end: 4px; + font-size: x-large; + cursor: pointer; } - .note-book-content { - display: none; - --background: rgba(0, 0, 0, .2); - outline: 1px solid var(--background); - border-radius: 8px; - background-color: var(--background); - overflow: hidden; - user-select: text; - animation: note-preview-show .25s ease-out; - will-change: opacity; + .tn-icon { + margin-inline-end: 8px; + color: var(--note-list-view-icon-color); + font-size: 1.2em; + } - &.note-book-content-ready { - display: block; - } + .note-book-title { + --link-hover-background: transparent; + --link-hover-color: currentColor; + color: inherit; + font-weight: normal; + } - > .rendered-content > *:last-child { - margin-bottom: 0; - } + .note-path { + margin-left: 0.5em; + vertical-align: middle; + opacity: 0.5; + } - &.type-text { - padding: 8px 24px; + .note-list-attributes { + flex-grow: 1; + text-align: right; + font-size: .75em; + opacity: .75; + } - .ck-content > *:last-child { - margin-bottom: 0; - } - } - - &.type-protectedSession { - padding: 20px; - } - - &.type-image { - padding: 0; - } - - &.type-pdf { - iframe { - height: 50vh; - } - - .file-footer { - padding: 8px; - } - } - - &.type-webView { - display: flex; - flex-direction: column; - justify-content: center; - min-height: 50vh; - } + .nested-note-list-item-menu { + margin-inline-start: 8px; } } -.nested-note-list.search-results { +/* List item (search results view) */ +.nested-note-list.search-results .nested-note-list-item { span.tn-icon + span > span { display: flex; flex-direction: column-reverse; @@ -237,23 +188,80 @@ flex-shrink: 0; justify-content: center; align-items: center; - margin-inline-end: 12px; - background: rgb(88, 88, 88); - border-radius: 50%; width: 1.75em; height: 1.75em; + margin-inline-end: 12px; + border-radius: 50%; + background: var(--note-list-view-large-icon-background); font-size: 1.2em; + color: var(--note-list-view-large-icon-color); } - .note-book-title { - --link-hover-background: transparent; + h5 .ck-find-result { + background: var(--note-list-view-search-result-highlight-background); + color: var(--note-list-view-search-result-highlight-color); + font-weight: 600; + text-decoration: underline; + } +} + +/* Note content preview */ +.nested-note-list .note-book-content { + display: none; + outline: 1px solid var(--note-list-view-content-background); + border-radius: 8px; + background-color: var(--note-list-view-content-background); + overflow: hidden; + user-select: text; + animation: note-preview-show .25s ease-out; + will-change: opacity; + + &.note-book-content-ready { + display: block; + } + + > .rendered-content > *:last-child { + margin-bottom: 0; + } + + &.type-text { + padding: 8px 24px; + + .ck-content > *:last-child { + margin-bottom: 0; + } + } + + &.type-protectedSession { + padding: 20px; + } + + &.type-image { + padding: 0; + } + + &.type-pdf { + iframe { + height: 50vh; + } + + .file-footer { + padding: 8px; + } + } + + &.type-webView { + display: flex; + flex-direction: column; + justify-content: center; + min-height: 50vh; } .ck-find-result { - background: transparent; - color: var(--quick-search-result-highlight-color); - font-weight: 600; - text-decoration: underline; + outline: 2px solid var(--note-list-view-content-search-result-highlight-background); + border-radius: 4px; + background: var(--note-list-view-content-search-result-highlight-background); + color: var(--note-list-view-content-search-result-highlight-color); } } @@ -261,6 +269,8 @@ display: none; } +/* #endregion */ + /* #region Grid view */ .note-list.grid-view .note-list-container { display: flex; From 9c2b01e3c94ebcd2b0679962e0d3121ecebdf18a Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 13:34:45 +0200 Subject: [PATCH 12/26] style/list view: tweak --- apps/client/src/stylesheets/theme-next-dark.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/client/src/stylesheets/theme-next-dark.css b/apps/client/src/stylesheets/theme-next-dark.css index e74180a230..eeac40a1fe 100644 --- a/apps/client/src/stylesheets/theme-next-dark.css +++ b/apps/client/src/stylesheets/theme-next-dark.css @@ -297,7 +297,7 @@ --note-list-view-search-result-highlight-color: var(--quick-search-result-highlight-color); --note-list-view-content-background: rgba(0, 0, 0, .2); --note-list-view-content-search-result-highlight-background: var(--quick-search-result-highlight-color); - --note-list-view-content-search-result-highlight-color: white; + --note-list-view-content-search-result-highlight-color: black; --calendar-coll-event-background-saturation: 25%; --calendar-coll-event-background-lightness: 20%; From b2ebaf111fc8764bc2f00554c1c0fc72b4ad56be Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 13:43:06 +0200 Subject: [PATCH 13/26] style/card: add legacy theme fallback --- apps/client/src/widgets/react/Card.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index 4a5b53f82a..49b3145f8d 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -10,7 +10,7 @@ .tn-card-section { padding: var(--card-padding); - border: 1px solid var(--card-border-color); + border: 1px solid var(--card-border-color, var(--main-border-color)); background: var(--card-background-color); &:first-of-type { From 4afbabb977004817fd8ec364df0eb4e757b1a0a1 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 13:51:13 +0200 Subject: [PATCH 14/26] style/list view: tweak --- apps/client/src/widgets/collections/legacy/ListOrGridView.css | 1 + 1 file changed, 1 insertion(+) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 7a09e177f8..88aa719c11 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -213,6 +213,7 @@ background-color: var(--note-list-view-content-background); overflow: hidden; user-select: text; + font-size: .85rem; animation: note-preview-show .25s ease-out; will-change: opacity; From fea8de89c61db28d3b8adec039b61d3cd45ba095 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 14:08:50 +0200 Subject: [PATCH 15/26] style/list view: handle the title and attributes when overflowing the container --- .../src/widgets/collections/legacy/ListOrGridView.css | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 88aa719c11..4cee5d215b 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -153,6 +153,7 @@ .note-list-attributes { flex-grow: 1; + margin-inline-start: 1em; text-align: right; font-size: .75em; opacity: .75; @@ -160,6 +161,16 @@ .nested-note-list-item-menu { margin-inline-start: 8px; + flex-shrink: 0; + } +} + +.nested-note-list:not(.search-results) h5 { + span.tn-icon + span, + .note-list-attributes { + white-space: nowrap; + overflow: hidden; + text-overflow: ellipsis; } } From 6ffbe196674ddcbb1e86aaa06530932b12c1f8a6 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:07:35 +0200 Subject: [PATCH 16/26] client/list view: add support for tinted notes --- apps/client/src/stylesheets/theme-next-dark.css | 6 ++++-- apps/client/src/stylesheets/theme-next-light.css | 6 ++++-- .../widgets/collections/legacy/ListOrGridView.css | 12 ++++++++++-- .../widgets/collections/legacy/ListOrGridView.tsx | 9 ++++++--- 4 files changed, 24 insertions(+), 9 deletions(-) diff --git a/apps/client/src/stylesheets/theme-next-dark.css b/apps/client/src/stylesheets/theme-next-dark.css index eeac40a1fe..43fdeda2d7 100644 --- a/apps/client/src/stylesheets/theme-next-dark.css +++ b/apps/client/src/stylesheets/theme-next-dark.css @@ -312,7 +312,8 @@ * Dark color scheme tweaks */ -#left-pane .fancytree-node.tinted { +#left-pane .fancytree-node.tinted, +.nested-note-list-item.use-note-color { --custom-color: var(--dark-theme-custom-color); /* The background color of the active item in the note tree. @@ -351,7 +352,8 @@ body .todo-list input[type="checkbox"]:not(:checked):before { } .note-split.with-hue, -.quick-edit-dialog-wrapper.with-hue { +.quick-edit-dialog-wrapper.with-hue, +.nested-note-list-item.with-hue { --note-icon-custom-background-color: hsl(var(--custom-color-hue), 15.8%, 30.9%); --note-icon-custom-color: hsl(var(--custom-color-hue), 100%, 76.5%); --note-icon-hover-custom-background-color: hsl(var(--custom-color-hue), 28.3%, 36.7%); diff --git a/apps/client/src/stylesheets/theme-next-light.css b/apps/client/src/stylesheets/theme-next-light.css index 70883f2368..d9f267d6f3 100644 --- a/apps/client/src/stylesheets/theme-next-light.css +++ b/apps/client/src/stylesheets/theme-next-light.css @@ -306,7 +306,8 @@ --calendar-coll-today-background-color: #00000006; } -#left-pane .fancytree-node.tinted { +#left-pane .fancytree-node.tinted, +.nested-note-list-item.use-note-color { --custom-color: var(--light-theme-custom-color); /* The background color of the active item in the note tree. @@ -322,7 +323,8 @@ } .note-split.with-hue, -.quick-edit-dialog-wrapper.with-hue { +.quick-edit-dialog-wrapper.with-hue, +.nested-note-list-item.with-hue { --note-icon-custom-background-color: hsl(var(--custom-color-hue), 44.5%, 43.1%); --note-icon-custom-color: hsl(var(--custom-color-hue), 91.3%, 91%); --note-icon-hover-custom-background-color: hsl(var(--custom-color-hue), 55.1%, 50.2%); diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 4cee5d215b..7e36c445f0 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -165,6 +165,14 @@ } } +.nested-note-list-item.use-note-color { + span.tn-icon + span, + .nested-note-list:not(.search-results) & .tn-icon, + .rendered-note-attributes { + color: var(--custom-color); + } +} + .nested-note-list:not(.search-results) h5 { span.tn-icon + span, .note-list-attributes { @@ -203,9 +211,9 @@ height: 1.75em; margin-inline-end: 12px; border-radius: 50%; - background: var(--note-list-view-large-icon-background); + background: var(--note-icon-custom-background-color, var(--note-list-view-large-icon-background)); font-size: 1.2em; - color: var(--note-list-view-large-icon-color); + color: var(--note-icon-custom-color, var(--note-list-view-large-icon-color)); } h5 .ck-find-result { diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index be244cbbe7..3f92f8ed62 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -116,16 +116,19 @@ function ListNoteCard({ note, parentNote, highlightedTokens, currentLevel, expan includeArchived={includeArchived} /> } - + return ( -
+
setExpanded(!isExpanded)}/> From 3df03a551c8c66a134b4aee984ca9a3e91f9e1c4 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:15:07 +0200 Subject: [PATCH 17/26] client/list view: add support for archived items --- .../collections/legacy/ListOrGridView.css | 22 ++++++++++++++----- 1 file changed, 16 insertions(+), 6 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 7e36c445f0..18f91c1819 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -119,12 +119,15 @@ } /* List item */ -.nested-note-list-item h5 { - display: flex; - align-items: center; - font-size: 1em; - font-weight: normal; - margin: 0; +.nested-note-list-item { + + h5 { + display: flex; + align-items: center; + font-size: 1em; + font-weight: normal; + margin: 0; + } .note-expander { margin-inline-end: 4px; @@ -163,6 +166,13 @@ margin-inline-start: 8px; flex-shrink: 0; } + + &.archived { + .note-book-title, + .tn-icon { + opacity: .5; + } + } } .nested-note-list-item.use-note-color { From 108ca5afb5279ef764934159e645e6e5bf3ab585 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:16:46 +0200 Subject: [PATCH 18/26] client/list view: add support for archived items --- apps/client/src/widgets/collections/legacy/ListOrGridView.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 18f91c1819..eea3222a45 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -170,7 +170,7 @@ &.archived { .note-book-title, .tn-icon { - opacity: .5; + opacity: .75; } } } From 900bfdff9d8fab4250ad28e18b916832084d087e Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:18:50 +0200 Subject: [PATCH 19/26] style/list view: refactor --- .../widgets/collections/legacy/ListOrGridView.css | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index eea3222a45..12199ad3bc 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -173,13 +173,13 @@ opacity: .75; } } -} -.nested-note-list-item.use-note-color { - span.tn-icon + span, - .nested-note-list:not(.search-results) & .tn-icon, - .rendered-note-attributes { - color: var(--custom-color); + &.use-note-color { + span.tn-icon + span, + .nested-note-list:not(.search-results) & .tn-icon, + .rendered-note-attributes { + color: var(--custom-color); + } } } From f645d9d721cb11465069931a413ff816f9923514 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:20:45 +0200 Subject: [PATCH 20/26] style/list view: tweak --- apps/client/src/widgets/collections/legacy/ListOrGridView.css | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 12199ad3bc..618a79030e 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -168,9 +168,9 @@ } &.archived { - .note-book-title, + span.tn-icon + span, .tn-icon { - opacity: .75; + opacity: .6; } } From 10cf1a371eb84e3d1cc57678b4b08beaabd8e9f6 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:34:00 +0200 Subject: [PATCH 21/26] style/card: improve --- apps/client/src/widgets/react/Card.css | 9 +++++---- apps/client/src/widgets/react/Card.tsx | 7 ++++--- 2 files changed, 9 insertions(+), 7 deletions(-) diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index 49b3145f8d..4afa49b898 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -1,6 +1,7 @@ .tn-card { --card-border-radius: 8px; - --card-padding: 8px 16px; + --card-padding-block: 8px; + --card-padding-inline: 16px; --card-section-gap: 3px; --card-nested-section-indent: 30px; @@ -9,7 +10,7 @@ gap: var(--card-section-gap); .tn-card-section { - padding: var(--card-padding); + padding: var(--card-padding-block) var(--card-padding-inline); border: 1px solid var(--card-border-color, var(--main-border-color)); background: var(--card-background-color); @@ -24,11 +25,11 @@ } &.tn-card-section-nested { - padding-left: calc(var(--card-nested-section-indent) * var(--tn-card-section-nesting-level)); + padding-left: calc(var(--card-padding-inline) + var(--card-nested-section-indent) * var(--tn-card-section-nesting-level)); background-color: color-mix(in srgb, var(--card-background-color) calc(100% / (var(--tn-card-section-nesting-level) + 1)) , transparent); } - &.tn-action:hover { + &.tn-card-section-highlight-on-hover:hover { background-color: var(--card-background-hover-color); transition: background-color .2s ease-out; } diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx index c717ee5433..141cd0119f 100644 --- a/apps/client/src/widgets/react/Card.tsx +++ b/apps/client/src/widgets/react/Card.tsx @@ -17,7 +17,8 @@ export function Card(props: {children: ComponentChildren} & CardProps) { interface CardSectionProps { className?: string; subSections?: JSX.Element | JSX.Element[]; - childrenVisible?: boolean; + subSectionsVisible?: boolean; + highlightOnHover?: boolean; hasAction?: boolean; onAction?: () => void; } @@ -29,14 +30,14 @@ export function CardSection(props: {children: ComponentChildren} & CardSectionPr return <>
0, - "tn-action": props.hasAction + "tn-card-section-highlight-on-hover": props.highlightOnHover || props.hasAction })} style={{"--tn-card-section-nesting-level": nestingLevel}} onClick={props.onAction}> {props.children}
- {props.childrenVisible && + {props.subSectionsVisible && {props.subSections} From 80b488deec28fbea51acff35036cd97964ccb90f Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:34:54 +0200 Subject: [PATCH 22/26] style/list view: tweak indentation size --- .../src/widgets/collections/legacy/ListOrGridView.css | 6 +++++- .../src/widgets/collections/legacy/ListOrGridView.tsx | 4 ++-- 2 files changed, 7 insertions(+), 3 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index 618a79030e..a1586135dc 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -115,7 +115,11 @@ } :root .nested-note-list { - --card-nested-section-indent: 40px; + --card-nested-section-indent: 25px; +} + +:root .nested-note-list.search-results { + --card-nested-section-indent: 32px; } /* List item */ diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index 3f92f8ed62..d024e8616b 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -124,8 +124,8 @@ function ListNoteCard({ note, parentNote, highlightedTokens, currentLevel, expan "archived": note.isArchived })} subSections={subSections} - childrenVisible={isExpanded} - hasAction + subSectionsVisible={isExpanded} + highlightOnHover data-note-id={note.noteId} >
From b6582536878d506bf9ef0ce40e949eb025f0d02b Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:55:04 +0200 Subject: [PATCH 23/26] style/card: refactor --- apps/client/src/widgets/react/Card.css | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/apps/client/src/widgets/react/Card.css b/apps/client/src/widgets/react/Card.css index 4afa49b898..ce6bf6dc61 100644 --- a/apps/client/src/widgets/react/Card.css +++ b/apps/client/src/widgets/react/Card.css @@ -1,10 +1,12 @@ -.tn-card { +:where(.tn-card) { --card-border-radius: 8px; --card-padding-block: 8px; --card-padding-inline: 16px; --card-section-gap: 3px; --card-nested-section-indent: 30px; +} +.tn-card { display: flex; flex-direction: column; gap: var(--card-section-gap); From 7e6daf5b3613db8b15cb90e72609a982959fd8f0 Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 18:55:23 +0200 Subject: [PATCH 24/26] style/list view: refactor --- .../src/widgets/collections/legacy/ListOrGridView.css | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index a1586135dc..b2251185ed 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -114,12 +114,12 @@ } } -:root .nested-note-list { +.nested-note-list { --card-nested-section-indent: 25px; -} -:root .nested-note-list.search-results { - --card-nested-section-indent: 32px; + &.search-results { + --card-nested-section-indent: 32px; + } } /* List item */ From 483c57029aebeb6b6c933564ca61734f531fd18a Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 19:10:31 +0200 Subject: [PATCH 25/26] client/list view: extract event handler --- .../src/widgets/collections/legacy/ListOrGridView.tsx | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index d024e8616b..f4750c6ef5 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -19,6 +19,7 @@ import { JSX } from "preact/jsx-runtime"; import { clsx } from "clsx"; import ActionButton from "../../react/ActionButton"; import linkContextMenuService from "../../../menus/link_context_menu"; +import { TargetedMouseEvent } from "preact"; export function ListView({ note, noteIds: unfilteredNoteIds, highlightedTokens }: ViewModeProps<{}>) { const expandDepth = useExpansionDepth(note); @@ -140,7 +141,7 @@ function ListNoteCard({ note, parentNote, highlightedTokens, currentLevel, expan {linkContextMenuService.openContextMenu(notePath, e); e.stopPropagation()}} + onClick={(e) => openNoteMenu(notePath, e)} />
@@ -274,3 +275,8 @@ function useExpansionDepth(note: FNote) { return parseInt(expandDepth, 10); } + +function openNoteMenu(notePath, e: TargetedMouseEvent) { + linkContextMenuService.openContextMenu(notePath, e); + e.stopPropagation() +} From d1a3bceaa69a3a2e21dfc02904affee2f0201dfd Mon Sep 17 00:00:00 2001 From: Adorian Doran Date: Sun, 15 Feb 2026 19:15:58 +0200 Subject: [PATCH 26/26] client/list view: refactor --- apps/client/src/widgets/collections/legacy/ListOrGridView.css | 1 - apps/client/src/widgets/collections/legacy/ListOrGridView.tsx | 3 +-- apps/client/src/widgets/react/Card.tsx | 3 +-- 3 files changed, 2 insertions(+), 5 deletions(-) diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.css b/apps/client/src/widgets/collections/legacy/ListOrGridView.css index b2251185ed..ea9a4e2e4b 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.css +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.css @@ -124,7 +124,6 @@ /* List item */ .nested-note-list-item { - h5 { display: flex; align-items: center; diff --git a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx index f4750c6ef5..cdde8a6087 100644 --- a/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx +++ b/apps/client/src/widgets/collections/legacy/ListOrGridView.tsx @@ -225,8 +225,7 @@ export function NoteContent({ note, trim, noChildrenList, highlightedTokens, inc }); }, [ note, highlightedTokens ]); - return
-
; + return
; } function NoteChildren({ note, parentNote, highlightedTokens, currentLevel, expandDepth, includeArchived }: { diff --git a/apps/client/src/widgets/react/Card.tsx b/apps/client/src/widgets/react/Card.tsx index 141cd0119f..26b52040be 100644 --- a/apps/client/src/widgets/react/Card.tsx +++ b/apps/client/src/widgets/react/Card.tsx @@ -19,7 +19,6 @@ interface CardSectionProps { subSections?: JSX.Element | JSX.Element[]; subSectionsVisible?: boolean; highlightOnHover?: boolean; - hasAction?: boolean; onAction?: () => void; } @@ -30,7 +29,7 @@ export function CardSection(props: {children: ComponentChildren} & CardSectionPr return <>
0, - "tn-card-section-highlight-on-hover": props.highlightOnHover || props.hasAction + "tn-card-section-highlight-on-hover": props.highlightOnHover || props.onAction })} style={{"--tn-card-section-nesting-level": nestingLevel}} onClick={props.onAction}>