mirror of
				https://github.com/zadam/trilium.git
				synced 2025-10-31 11:39:01 +01:00 
			
		
		
		
	chore(react/collections): calculate note Ids
This commit is contained in:
		
							parent
							
								
									5fb843268f
								
							
						
					
					
						commit
						ecf44deecf
					
				
							
								
								
									
										18
									
								
								apps/client/src/widgets/collections/NoteList.css
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										18
									
								
								apps/client/src/widgets/collections/NoteList.css
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,18 @@ | ||||
| .note-list-widget { | ||||
|     min-height: 0; | ||||
|     overflow: auto; | ||||
|     contain: none !important; | ||||
| } | ||||
| 
 | ||||
| .note-list-widget .note-list { | ||||
|     padding: 10px; | ||||
| } | ||||
| 
 | ||||
| .note-list-widget.full-height, | ||||
| .note-list-widget.full-height .note-list-widget-content { | ||||
|     height: 100%; | ||||
| } | ||||
| 
 | ||||
| .note-list-widget video { | ||||
|     height: 100%; | ||||
| } | ||||
| @ -1,7 +1,80 @@ | ||||
| import { allViewTypes, ViewTypeOptions } from "./interface"; | ||||
| import { useNoteContext, useNoteLabel, useTriliumEvent } from "../react/hooks"; | ||||
| import FNote from "../../entities/fnote"; | ||||
| import "./NoteList.css"; | ||||
| import ListView from "./legacy/ListView"; | ||||
| import { useEffect, useState } from "preact/hooks"; | ||||
| 
 | ||||
| interface NoteListProps { | ||||
|     displayOnlyCollections?: boolean; | ||||
| } | ||||
| 
 | ||||
| export default function NoteList({ }: NoteListProps) { | ||||
|     return <p>Hi</p> | ||||
|     const { note } = useNoteContext(); | ||||
|     const viewType = useNoteViewType(note); | ||||
|     const noteIds = useNoteIds(note, viewType); | ||||
|     const isEnabled = (!!viewType); | ||||
| 
 | ||||
|     // Refresh note Ids
 | ||||
|     console.log("Got note ids", noteIds); | ||||
| 
 | ||||
|     return ( | ||||
|         <div className="note-list-widget"> | ||||
|             {isEnabled && ( | ||||
|                 <div className="note-list-widget-content"> | ||||
|                     {getComponentByViewType(viewType)} | ||||
|                 </div> | ||||
|             )} | ||||
|         </div> | ||||
|     ); | ||||
| } | ||||
| 
 | ||||
| function getComponentByViewType(viewType: ViewTypeOptions) { | ||||
|     console.log("Got ", viewType); | ||||
|     switch (viewType) { | ||||
|         case "list": | ||||
|             return <ListView />; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| function useNoteViewType(note?: FNote | null): ViewTypeOptions | undefined { | ||||
|     const [ viewType ] = useNoteLabel(note, "viewType"); | ||||
|      | ||||
|     if (!note) { | ||||
|         return undefined; | ||||
|     } else if (!(allViewTypes as readonly string[]).includes(viewType || "")) { | ||||
|         // when not explicitly set, decide based on the note type
 | ||||
|         return note.type === "search" ? "list" : "grid"; | ||||
|     } else { | ||||
|         return viewType as ViewTypeOptions; | ||||
|     } | ||||
| } | ||||
| 
 | ||||
| function useNoteIds(note: FNote | null | undefined, viewType: ViewTypeOptions | undefined) { | ||||
|     const [ noteIds, setNoteIds ] = useState<string[]>([]); | ||||
|      | ||||
|     async function refreshNoteIds() { | ||||
|         console.log("Refreshed note IDs"); | ||||
|         if (!note) { | ||||
|             setNoteIds([]); | ||||
|         } else if (viewType === "list" || viewType === "grid") { | ||||
|             setNoteIds(note.getChildNoteIds()); | ||||
|         } else { | ||||
|             setNoteIds(await note.getSubtreeNoteIds()); | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     // Refresh on note switch.
 | ||||
|     useEffect(() => { refreshNoteIds() }, [ note ]); | ||||
| 
 | ||||
|     // Refresh on alterations to the note subtree.
 | ||||
|     useTriliumEvent("entitiesReloaded", ({ loadResults }) => { | ||||
|         if (note && loadResults.getBranchRows().some(branch => | ||||
|                 branch.parentNoteId === note.noteId | ||||
|                 || noteIds.includes(branch.parentNoteId ?? ""))) { | ||||
|             refreshNoteIds();     | ||||
|         } | ||||
|     }) | ||||
| 
 | ||||
|     return noteIds; | ||||
| } | ||||
| @ -1,5 +1,5 @@ | ||||
| import type { ViewModeArgs } from "../view_widgets/view_mode"; | ||||
| 
 | ||||
| const allViewTypes = ["list", "grid", "calendar", "table", "geoMap", "board"] as const; | ||||
| export const allViewTypes = ["list", "grid", "calendar", "table", "geoMap", "board"] as const; | ||||
| export type ArgsWithoutNoteId = Omit<ViewModeArgs, "noteIds">; | ||||
| export type ViewTypeOptions = typeof allViewTypes[number]; | ||||
|  | ||||
							
								
								
									
										138
									
								
								apps/client/src/widgets/collections/legacy/ListOrGridView.css
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										138
									
								
								apps/client/src/widgets/collections/legacy/ListOrGridView.css
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,138 @@ | ||||
| .note-list { | ||||
|     overflow: hidden; | ||||
|     position: relative; | ||||
|     height: 100%; | ||||
| } | ||||
| 
 | ||||
| .note-book-card { | ||||
|     border-radius: 10px; | ||||
|     background-color: var(--accented-background-color); | ||||
|     padding: 10px 15px 15px 8px; | ||||
|     margin: 5px 5px 5px 5px; | ||||
|     overflow: hidden; | ||||
|     display: flex; | ||||
|     flex-direction: column; | ||||
|     flex-shrink: 0; | ||||
|     flex-grow: 1; | ||||
| } | ||||
| 
 | ||||
| .note-book-card:not(.expanded) .note-book-content { | ||||
|     display: none !important; | ||||
|     padding: 10px | ||||
| } | ||||
| 
 | ||||
| .note-book-card.expanded .note-book-content { | ||||
|     display: block; | ||||
|     min-height: 0; | ||||
|     height: 100%; | ||||
|     padding-top: 10px; | ||||
| } | ||||
| 
 | ||||
| .note-book-content .rendered-content { | ||||
|     height: 100%; | ||||
| } | ||||
| 
 | ||||
| .note-book-header { | ||||
|     border-bottom: 1px solid var(--main-border-color); | ||||
|     margin-bottom: 0; | ||||
|     padding-bottom: .5rem; | ||||
|     word-break: break-all; | ||||
| } | ||||
| 
 | ||||
| /* not-expanded title is limited to one line only */ | ||||
| .note-book-card:not(.expanded) .note-book-header { | ||||
|     overflow: hidden; | ||||
|     white-space: nowrap; | ||||
|     text-overflow: ellipsis; | ||||
| } | ||||
| 
 | ||||
| .note-book-header .rendered-note-attributes { | ||||
|     font-size: medium; | ||||
| } | ||||
| 
 | ||||
| .note-book-header .rendered-note-attributes:before { | ||||
|     content: "\\00a0\\00a0"; | ||||
| } | ||||
| 
 | ||||
| .note-book-header .note-icon { | ||||
|     font-size: 100%; | ||||
|     display: inline-block; | ||||
|     padding-right: 7px; | ||||
|     position: relative; | ||||
| } | ||||
| 
 | ||||
| .note-book-card .note-book-card { | ||||
|     border: 1px solid var(--main-border-color); | ||||
| } | ||||
| 
 | ||||
| .note-book-content.type-image, .note-book-content.type-file, .note-book-content.type-protectedSession { | ||||
|     display: flex; | ||||
|     align-items: center; | ||||
|     justify-content: center; | ||||
|     text-align: center; | ||||
|     padding: 10px; | ||||
| } | ||||
| 
 | ||||
| .note-book-content.type-image img, .note-book-content.type-canvas svg { | ||||
|     max-width: 100%; | ||||
|     max-height: 100%; | ||||
|     object-fit: contain; | ||||
| } | ||||
| 
 | ||||
| .note-book-card.type-image .note-book-content img, | ||||
| .note-book-card.type-text .note-book-content img, | ||||
| .note-book-card.type-canvas .note-book-content img { | ||||
|     max-width: 100%; | ||||
|     max-height: 100%; | ||||
| } | ||||
| 
 | ||||
| .note-book-header { | ||||
|     flex-grow: 0; | ||||
| } | ||||
| 
 | ||||
| .note-list-wrapper { | ||||
|     height: 100%; | ||||
|     overflow: auto; | ||||
| } | ||||
| 
 | ||||
| .note-expander { | ||||
|     font-size: x-large; | ||||
|     position: relative; | ||||
|     top: 3px; | ||||
|     cursor: pointer; | ||||
| } | ||||
| 
 | ||||
| .note-list-pager { | ||||
|     text-align: center; | ||||
| } | ||||
| 
 | ||||
| /* #region Grid view */ | ||||
| .note-list.grid-view .note-list-container { | ||||
|     display: flex; | ||||
|     flex-wrap: wrap; | ||||
| } | ||||
| 
 | ||||
| .note-list.grid-view .note-book-card { | ||||
|     flex-basis: 300px; | ||||
|     border: 1px solid transparent; | ||||
| } | ||||
| 
 | ||||
| .note-list.grid-view .note-expander { | ||||
|     display: none; | ||||
| } | ||||
| 
 | ||||
| .note-list.grid-view .note-book-card { | ||||
|     max-height: 300px; | ||||
| } | ||||
| 
 | ||||
| .note-list.grid-view .note-book-card img { | ||||
|     max-height: 220px; | ||||
|     object-fit: contain; | ||||
| } | ||||
| 
 | ||||
| .note-list.grid-view .note-book-card:hover { | ||||
|     cursor: pointer; | ||||
|     border: 1px solid var(--main-border-color); | ||||
|     background: var(--more-accented-background-color); | ||||
| } | ||||
| /* #endregion */ | ||||
							
								
								
									
										14
									
								
								apps/client/src/widgets/collections/legacy/ListView.tsx
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										14
									
								
								apps/client/src/widgets/collections/legacy/ListView.tsx
									
									
									
									
									
										Normal file
									
								
							| @ -0,0 +1,14 @@ | ||||
| export default function ListView() { | ||||
|     return ( | ||||
|         <div class="note-list"> | ||||
|             <div class="note-list-wrapper"> | ||||
|                 List view goes here. | ||||
|                 <div class="note-list-pager"></div> | ||||
|          | ||||
|                 <div class="note-list-container use-tn-links"></div> | ||||
|          | ||||
|                 <div class="note-list-pager"></div> | ||||
|             </div> | ||||
|         </div> | ||||
|     ); | ||||
| } | ||||
| @ -4,32 +4,6 @@ import type FNote from "../../entities/fnote.js"; | ||||
| import type { CommandListener, CommandListenerData, CommandMappings, CommandNames, EventData, EventNames } from "../../components/app_context.js"; | ||||
| import type ViewMode from "../view_widgets/view_mode.js"; | ||||
| 
 | ||||
| const TPL = /*html*/` | ||||
| <div class="note-list-widget"> | ||||
|     <style> | ||||
|     .note-list-widget { | ||||
|         min-height: 0; | ||||
|         overflow: auto; | ||||
|     } | ||||
| 
 | ||||
|     .note-list-widget .note-list { | ||||
|         padding: 10px; | ||||
|     } | ||||
| 
 | ||||
|     .note-list-widget.full-height, | ||||
|     .note-list-widget.full-height .note-list-widget-content { | ||||
|         height: 100%; | ||||
|     } | ||||
| 
 | ||||
|     .note-list-widget video { | ||||
|         height: 100%; | ||||
|     } | ||||
|     </style> | ||||
| 
 | ||||
|     <div class="note-list-widget-content"> | ||||
|     </div> | ||||
| </div>`; | ||||
| 
 | ||||
| export default class NoteListWidget extends NoteContextAwareWidget { | ||||
| 
 | ||||
|     private $content!: JQuery<HTMLElement>; | ||||
| @ -49,10 +23,6 @@ export default class NoteListWidget extends NoteContextAwareWidget { | ||||
|     } | ||||
| 
 | ||||
|     isEnabled() { | ||||
|         if (!super.isEnabled()) { | ||||
|             return false; | ||||
|         } | ||||
| 
 | ||||
|         if (this.displayOnlyCollections && this.note?.type !== "book") { | ||||
|             const viewType = this.note?.getLabelValue("viewType"); | ||||
|             if (!viewType || ["grid", "list"].includes(viewType)) { | ||||
|  | ||||
| @ -17,17 +17,6 @@ export default class NoteListRenderer { | ||||
|         this.viewType = this.#getViewType(args.parentNote); | ||||
|     } | ||||
| 
 | ||||
|     #getViewType(parentNote: FNote): ViewTypeOptions { | ||||
|         const viewType = parentNote.getLabelValue("viewType"); | ||||
| 
 | ||||
|         if (!(allViewTypes as readonly string[]).includes(viewType || "")) { | ||||
|             // when not explicitly set, decide based on the note type
 | ||||
|             return parentNote.type === "search" ? "list" : "grid"; | ||||
|         } else { | ||||
|             return viewType as ViewTypeOptions; | ||||
|         } | ||||
|     } | ||||
| 
 | ||||
|     get isFullHeight() { | ||||
|         switch (this.viewType) { | ||||
|             case "list": | ||||
|  | ||||
| @ -8,156 +8,6 @@ import type FNote from "../../entities/fnote.js"; | ||||
| import ViewMode, { type ViewModeArgs } from "./view_mode.js"; | ||||
| import { ViewTypeOptions } from "../collections/interface.js"; | ||||
| 
 | ||||
| const TPL = /*html*/` | ||||
| <div class="note-list"> | ||||
|     <style> | ||||
|     .note-list { | ||||
|         overflow: hidden; | ||||
|         position: relative; | ||||
|         height: 100%; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-list-container { | ||||
|         display: flex; | ||||
|         flex-wrap: wrap; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-book-card { | ||||
|         flex-basis: 300px; | ||||
|         border: 1px solid transparent; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-expander { | ||||
|         display: none; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-book-card { | ||||
|         max-height: 300px; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-book-card img { | ||||
|         max-height: 220px; | ||||
|         object-fit: contain; | ||||
|     } | ||||
| 
 | ||||
|     .note-list.grid-view .note-book-card:hover { | ||||
|         cursor: pointer; | ||||
|         border: 1px solid var(--main-border-color); | ||||
|         background: var(--more-accented-background-color); | ||||
|     } | ||||
| 
 | ||||
|     .note-book-card { | ||||
|         border-radius: 10px; | ||||
|         background-color: var(--accented-background-color); | ||||
|         padding: 10px 15px 15px 8px; | ||||
|         margin: 5px 5px 5px 5px; | ||||
|         overflow: hidden; | ||||
|         display: flex; | ||||
|         flex-direction: column; | ||||
|         flex-shrink: 0; | ||||
|         flex-grow: 1; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-card:not(.expanded) .note-book-content { | ||||
|         display: none !important; | ||||
|         padding: 10px | ||||
|     } | ||||
| 
 | ||||
|     .note-book-card.expanded .note-book-content { | ||||
|         display: block; | ||||
|         min-height: 0; | ||||
|         height: 100%; | ||||
|         padding-top: 10px; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-content .rendered-content { | ||||
|         height: 100%; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-header { | ||||
|         border-bottom: 1px solid var(--main-border-color); | ||||
|         margin-bottom: 0; | ||||
|         padding-bottom: .5rem; | ||||
|         word-break: break-all; | ||||
|     } | ||||
| 
 | ||||
|     /* not-expanded title is limited to one line only */ | ||||
|     .note-book-card:not(.expanded) .note-book-header { | ||||
|         overflow: hidden; | ||||
|         white-space: nowrap; | ||||
|         text-overflow: ellipsis; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-header .rendered-note-attributes { | ||||
|         font-size: medium; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-header .rendered-note-attributes:before { | ||||
|         content: "\\00a0\\00a0"; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-header .note-icon { | ||||
|         font-size: 100%; | ||||
|         display: inline-block; | ||||
|         padding-right: 7px; | ||||
|         position: relative; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-card .note-book-card { | ||||
|         border: 1px solid var(--main-border-color); | ||||
|     } | ||||
| 
 | ||||
|     .note-book-content.type-image, .note-book-content.type-file, .note-book-content.type-protectedSession { | ||||
|         display: flex; | ||||
|         align-items: center; | ||||
|         justify-content: center; | ||||
|         text-align: center; | ||||
|         padding: 10px; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-content.type-image img, .note-book-content.type-canvas svg { | ||||
|         max-width: 100%; | ||||
|         max-height: 100%; | ||||
|         object-fit: contain; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-card.type-image .note-book-content img, | ||||
|     .note-book-card.type-text .note-book-content img, | ||||
|     .note-book-card.type-canvas .note-book-content img { | ||||
|         max-width: 100%; | ||||
|         max-height: 100%; | ||||
|     } | ||||
| 
 | ||||
|     .note-book-header { | ||||
|         flex-grow: 0; | ||||
|     } | ||||
| 
 | ||||
|     .note-list-wrapper { | ||||
|         height: 100%; | ||||
|         overflow: auto; | ||||
|     } | ||||
| 
 | ||||
|     .note-expander { | ||||
|         font-size: x-large; | ||||
|         position: relative; | ||||
|         top: 3px; | ||||
|         cursor: pointer; | ||||
|     } | ||||
| 
 | ||||
|     .note-list-pager { | ||||
|         text-align: center; | ||||
|     } | ||||
|     </style> | ||||
| 
 | ||||
|     <div class="note-list-wrapper"> | ||||
|         <div class="note-list-pager"></div> | ||||
| 
 | ||||
|         <div class="note-list-container use-tn-links"></div> | ||||
| 
 | ||||
|         <div class="note-list-pager"></div> | ||||
|     </div> | ||||
| </div>`;
 | ||||
| 
 | ||||
| class ListOrGridView extends ViewMode<{}> { | ||||
|     private $noteList: JQuery<HTMLElement>; | ||||
| 
 | ||||
|  | ||||
| @ -48,10 +48,6 @@ export default abstract class ViewMode<T extends object> extends Component { | ||||
|     } | ||||
| 
 | ||||
|     async entitiesReloadedEvent(e: EventData<"entitiesReloaded">) { | ||||
|         if (e.loadResults.getBranchRows().some(branch => branch.parentNoteId === this.parentNote.noteId || this.noteIds.includes(branch.parentNoteId ?? ""))) { | ||||
|             this.#refreshNoteIds(); | ||||
|         } | ||||
| 
 | ||||
|         if (await this.onEntitiesReloaded(e)) { | ||||
|             appContext.triggerEvent("refreshNoteList", { noteId: this.parentNote.noteId }); | ||||
|         } | ||||
| @ -70,14 +66,4 @@ export default abstract class ViewMode<T extends object> extends Component { | ||||
|         return this._viewStorage; | ||||
|     } | ||||
| 
 | ||||
|     async #refreshNoteIds() { | ||||
|         let noteIds: string[]; | ||||
|         if (this.viewType === "list" || this.viewType === "grid") { | ||||
|             noteIds = this.args.parentNote.getChildNoteIds(); | ||||
|         } else { | ||||
|             noteIds = await this.args.parentNote.getSubtreeNoteIds(); | ||||
|         } | ||||
|         this.noteIds = noteIds; | ||||
|     } | ||||
| 
 | ||||
| } | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 Elian Doran
						Elian Doran