From 1c794c18ea66af2e8c9caa7c032e58d91d91cd12 Mon Sep 17 00:00:00 2001 From: Lost Paul <70213368+LostPaul@users.noreply.github.com> Date: Sat, 21 Sep 2024 21:49:34 +0200 Subject: [PATCH] Fix issues with 1.7.2 Obsidian release and some code rewrite --- src/Commands.ts | 6 +-- src/events/MutationObserver.ts | 3 ++ src/folderOverview/FileExplorer.ts | 3 +- src/functions/styleFunctions.ts | 61 ++++++++++++----------------- src/main.ts | 45 +++++++++++++-------- src/suggesters/FileSuggester.ts | 4 +- src/suggesters/FolderSuggester.ts | 4 +- src/suggesters/Suggest.ts | 14 ++++--- src/suggesters/TemplateSuggester.ts | 4 +- styles.css | 6 ++- 10 files changed, 81 insertions(+), 69 deletions(-) diff --git a/src/Commands.ts b/src/Commands.ts index 799dc7a..71bc48f 100644 --- a/src/Commands.ts +++ b/src/Commands.ts @@ -8,7 +8,7 @@ import { addExcludedFolder, deleteExcludedFolder, getDetachedFolder, getExcluded import ExcludedFolderSettings from './ExcludeFolders/modals/ExcludeFolderSettings' import { ExcludePattern } from './ExcludeFolders/ExcludePattern'; import PatternSettings from './ExcludeFolders/modals/PatternSettings'; -import { loadFolderClasses } from './functions/styleFunctions'; +import { applyCSSClassesToFolder } from './functions/styleFunctions'; export class Commands { plugin: FolderNotesPlugin; @@ -373,7 +373,7 @@ export class Commands { this.plugin.settings.excludeFolders = this.plugin.settings.excludeFolders.filter( (folder) => (folder.path !== file.path) && folder.hideNote); this.plugin.saveSettings(false); - loadFolderClasses(true, file, this.plugin); + applyCSSClassesToFolder(file.path, this.plugin); }); }); } else { @@ -391,7 +391,7 @@ export class Commands { excludedFolder.excludeFromFolderOverview = false; excludedFolder.hideInSettings = true; addExcludedFolder(this.plugin, excludedFolder, false); - loadFolderClasses(true, file, this.plugin); + applyCSSClassesToFolder(file.path, this.plugin); }); }); } diff --git a/src/events/MutationObserver.ts b/src/events/MutationObserver.ts index f5afc94..fd57a9b 100644 --- a/src/events/MutationObserver.ts +++ b/src/events/MutationObserver.ts @@ -3,6 +3,7 @@ import { Platform, Keymap } from 'obsidian'; import { getFolderNote } from 'src/functions/folderNoteFunctions'; import { handleFolderClick, handleViewHeaderClick } from './handleClick'; import { getExcludedFolder } from 'src/ExcludeFolders/functions/folderFunctions'; +import { applyCSSClassesToFolder } from 'src/functions/styleFunctions'; export async function addObserver(plugin: FolderNotesPlugin) { plugin.observer = new MutationObserver((mutations: MutationRecord[]) => { @@ -12,6 +13,8 @@ export async function addObserver(plugin: FolderNotesPlugin) { .forEach((element: HTMLElement) => { if (element.onclick) return; if (Platform.isMobile && plugin.settings.disableOpenFolderNoteOnClick) return; + const folderPath = element.parentElement?.getAttribute('data-path') || ''; + const apply = applyCSSClassesToFolder(folderPath, plugin); // handle middle click element.addEventListener('auxclick', (event: MouseEvent) => { if (event.button == 1) { diff --git a/src/folderOverview/FileExplorer.ts b/src/folderOverview/FileExplorer.ts index cdbf52c..60ef763 100644 --- a/src/folderOverview/FileExplorer.ts +++ b/src/folderOverview/FileExplorer.ts @@ -63,10 +63,9 @@ export class FileExplorerOverview { folderElement = document.querySelectorAll('.nav-files-container')[0] as HTMLElement; - console.log('folderElement', folderElement); if (!folderElement) return; + const newFolderElement = folderElement.cloneNode(true) as HTMLElement; - console.log('newFolderElement', newFolderElement); newFolderElement.querySelectorAll('div.nav-folder-title').forEach((el) => { const folder = plugin.app.vault.getAbstractFileByPath(el.getAttribute('data-path') || ''); diff --git a/src/functions/styleFunctions.ts b/src/functions/styleFunctions.ts index 123cbc8..07bcd4b 100644 --- a/src/functions/styleFunctions.ts +++ b/src/functions/styleFunctions.ts @@ -26,55 +26,49 @@ export function loadFileClasses(forceReload = false, plugin: FolderNotesPlugin) removeCSSClassFromEL(file?.path, 'only-has-folder-note'); } else { if (!excludedFolder?.hideNote) { - addCSSClassToTitleEL(plugin, folderNote.path, 'is-folder-note'); - } - addCSSClassToTitleEL(plugin, file.path, 'has-folder-note'); - if (plugin.isEmptyFolderNoteFolder(file)) { - addCSSClassToTitleEL(plugin, file.path, 'only-has-folder-note'); - } else { - removeCSSClassFromEL(file.path, 'only-has-folder-note'); + addCSSClassToTitleEL(folderNote.path, 'is-folder-note'); } + addCSSClassesToFolder(file, plugin); } }); } -// load classes of specific folder -export async function loadFolderClasses(forceReload = false, folder: TFolder, plugin: FolderNotesPlugin) { - if (plugin.activeFileExplorer === getFileExplorer() && !forceReload) { return; } - plugin.activeFileExplorer = getFileExplorer(); + +export async function applyCSSClassesToFolder(folderPath: string, plugin: FolderNotesPlugin) { + const folder = plugin.app.vault.getAbstractFileByPath(folderPath); + if (!folder || !(folder instanceof TFolder)) { return; } const folderNote = getFolderNote(plugin, folder.path); if (!folderNote) { removeCSSClassFromEL(folder?.path, 'has-folder-note'); removeCSSClassFromEL(folder?.path, 'only-has-folder-note'); - plugin.isEmptyFolderNoteFolder(folder) return; } const excludedFolder = await getExcludedFolder(plugin, folder.path, true); - // cleanup after ourselves - // Incase settings have changed + if (excludedFolder?.disableFolderNote) { removeCSSClassFromEL(folderNote.path, 'is-folder-note'); removeCSSClassFromEL(folder.path, 'has-folder-note'); removeCSSClassFromEL(folder?.path, 'only-has-folder-note'); } else { if (!excludedFolder?.hideNote) { - addCSSClassToTitleEL(plugin, folderNote.path, 'is-folder-note'); + addCSSClassToFolderNote(folderNote); } - addCSSClassToTitleEL(plugin, folder.path, 'has-folder-note'); + addCSSClassesToFolder(folder, plugin); if (plugin.isEmptyFolderNoteFolder(folder)) { - addCSSClassToTitleEL(plugin, folder.path, 'only-has-folder-note'); + addCSSClassToTitleEL(folder.path, 'only-has-folder-note'); } else { removeCSSClassFromEL(folder.path, 'only-has-folder-note'); } } + addCSSClassesToBothFolderAndNote(folderNote, folder, plugin); } -export function addCSSClassesToBothFolderAndNote(file: TFile, folder: TFolder) { +export function addCSSClassesToBothFolderAndNote(file: TFile, folder: TFolder, plugin: FolderNotesPlugin) { addCSSClassToFolderNote(file); - addCSSClassesToFolder(folder); + addCSSClassesToFolder(folder, plugin); } export function removeCSSClassesFromBothFolderAndNote(folder: TFolder, file: TFile) { @@ -82,30 +76,30 @@ export function removeCSSClassesFromBothFolderAndNote(folder: TFolder, file: TFi removeCSSClassesFromFolder(folder); } -export function addCSSClassesToFolder(folder: TFolder) { - addCSSClassToTitleEL(undefined, folder.path, 'has-folder-note'); - if (this.isEmptyFolderNoteFolder(folder)) { - addCSSClassToTitleEL(undefined, folder.path, 'only-has-folder-note'); +export function addCSSClassesToFolder(folder: TFolder, plugin: FolderNotesPlugin) { + addCSSClassToTitleEL(folder.path, 'has-folder-note'); + if (plugin.isEmptyFolderNoteFolder(folder)) { + addCSSClassToTitleEL(folder.path, 'only-has-folder-note'); } else { removeCSSClassFromEL(folder.path, 'only-has-folder-note'); } } export function addCSSClassToFolderNote(file: TFile) { - addCSSClassToTitleEL(undefined, file.path, 'is-folder-note'); + addCSSClassToTitleEL(file.path, 'is-folder-note'); } export function removeCSSClassFromFolderNote(file: TFile) { - this.removeCSSClassFromEL(file.path, 'is-folder-note'); + removeCSSClassFromEL(file.path, 'is-folder-note'); } export function removeCSSClassesFromFolder(folder: TFolder) { - this.removeCSSClassFromEL(folder.path, 'has-folder-note'); - this.removeCSSClassFromEL(folder.path, 'only-has-folder-note'); + removeCSSClassFromEL(folder.path, 'has-folder-note'); + removeCSSClassFromEL(folder.path, 'only-has-folder-note'); } -export async function addCSSClassToTitleEL(plugin: FolderNotesPlugin | undefined, path: string, cssClass: string, waitForCreate = false, count = 0) { - const fileExplorerItem = getEl(path) +export async function addCSSClassToTitleEL(path: string, cssClass: string, waitForCreate = false, count = 0) { + const fileExplorerItem = getEl(path); if (!fileExplorerItem) { if (waitForCreate && count < 5) { // sleep for a second for the file-explorer event to catch up @@ -113,21 +107,19 @@ export async function addCSSClassToTitleEL(plugin: FolderNotesPlugin | undefined // If we could guarrantee load order it wouldn't be an issue but we can't // realise this is racey and needs to be fixed. await new Promise((r) => setTimeout(r, 500)); - addCSSClassToTitleEL(plugin, path, cssClass, waitForCreate, count + 1); + addCSSClassToTitleEL(path, cssClass, waitForCreate, count + 1); return; } return; } - fileExplorerItem.addClass(cssClass); - const viewHeaderItems = document.querySelectorAll(`[data-path="${path}"]`); viewHeaderItems.forEach((item) => { item.addClass(cssClass); }); } -export async function removeCSSClassFromEL(path: string | undefined, cssClass: string) { +export function removeCSSClassFromEL(path: string | undefined, cssClass: string) { if (!path) return; const fileExplorerItem = getEl(path); const viewHeaderItems = document.querySelectorAll(`[data-path="${path}"]`); @@ -145,5 +137,4 @@ export function getEl(path: string): HTMLElement | null { if (!fileExplorerItem) { return null; } if (fileExplorerItem.selfEl) return fileExplorerItem.selfEl; return fileExplorerItem.titleEl; -} - +} \ No newline at end of file diff --git a/src/main.ts b/src/main.ts index 6575265..90e4049 100644 --- a/src/main.ts +++ b/src/main.ts @@ -13,7 +13,7 @@ import { FolderOverview } from './folderOverview/FolderOverview'; import { TabManager } from './events/TabManager'; import './functions/ListComponent'; import { handleDelete } from './events/handleDelete'; -import { addCSSClassToTitleEL, getEl, loadFileClasses, removeCSSClassFromEL } from './functions/styleFunctions'; +import { addCSSClassToTitleEL, getEl, loadFileClasses } from './functions/styleFunctions'; import { getExcludedFolder } from './ExcludeFolders/functions/folderFunctions'; import { ClipBoardManager, FileExplorerView, InternalPlugin, InternalPlugins } from 'obsidian-typings' export default class FolderNotesPlugin extends Plugin { @@ -87,11 +87,6 @@ export default class FolderNotesPlugin extends Plugin { this.hoverLinkTriggered = true; }); - this.registerEvent(this.app.workspace.on('layout-change', () => { - loadFileClasses(undefined, this); - this.tabManager?.updateTabs(); - })); - this.registerEvent(this.app.vault.on('create', (file: TAbstractFile) => { handleCreate(file, this); })); @@ -129,8 +124,18 @@ export default class FolderNotesPlugin extends Plugin { if (this.app.workspace.layoutReady) { loadFileClasses(undefined, this); + this.registerEvent(this.app.workspace.on('layout-change', () => { + loadFileClasses(undefined, this); + this.tabManager?.updateTabs(); + })); } else { - this.app.workspace.onLayoutReady(async () => loadFileClasses(undefined, this)); + this.app.workspace.onLayoutReady(async () => { + loadFileClasses(undefined, this) + this.registerEvent(this.app.workspace.on('layout-change', () => { + loadFileClasses(undefined, this); + this.tabManager?.updateTabs(); + })); + }); } } @@ -141,13 +146,20 @@ export default class FolderNotesPlugin extends Plugin { this.tabManager = new TabManager(this); this.tabManager.updateTabs(); - const view = this.app.workspace.getLeavesOfType('markdown')[0]?.view; + const leaf = this.app.workspace.getLeavesOfType('markdown').first(); + const view = leaf?.view; + if (!view) { return; } + + // @ts-ignore + const editMode = view.editMode ?? view.sourceMode ?? this.app.workspace.activeEditor?.editMode; const plugin = this; + // @ts-ignore - const originalHandleDragOver = view.editMode.clipboardManager.constructor.prototype.handleDragOver; + const originalHandleDragOver = editMode.clipboardManager.constructor.prototype.handleDragOver; + // @ts-ignore - view.editMode.clipboardManager.constructor.prototype.handleDragOver = function (evt, ...args) { + editMode.clipboardManager.constructor.prototype.handleDragOver = function (evt, ...args) { const { draggable } = plugin.app.dragManager; if (draggable && draggable.file instanceof TFolder && getFolderNote(plugin, draggable.file.path)) { plugin.app.dragManager.setAction(window.i18next.t("interface.drag-and-drop.insert-link-here")); @@ -157,9 +169,9 @@ export default class FolderNotesPlugin extends Plugin { }; // @ts-ignore - const originalHandleDrop = view.editMode.clipboardManager.constructor.prototype.handleDrop; + const originalHandleDrop = editMode.clipboardManager.constructor.prototype.handleDrop; // @ts-ignore - view.editMode.clipboardManager.constructor.prototype.handleDrop = function (evt, ...args) { + editMode.clipboardManager.constructor.prototype.handleDrop = function (evt, ...args) { const { draggable } = plugin.app.dragManager; if (draggable && draggable.file instanceof TFolder && getFolderNote(plugin, draggable.file.path)) { const folderNote = getFolderNote(plugin, draggable.file.path); @@ -171,9 +183,7 @@ export default class FolderNotesPlugin extends Plugin { return originalHandleDrop.call(this, evt, ...args); } - // const fileExplorerPluginInstance = this.app.internalPlugins.getEnabledPluginById(InternalPluginName.FileExplorer); - - + // const fileExplorerPluginInstance = this.app.internalPlugins.getEnabledPluginById(InternalPluginName.FileExplorer); } @@ -189,17 +199,18 @@ export default class FolderNotesPlugin extends Plugin { }, { capture: true }); } }); + observer.observe(el, { childList: true, subtree: true, }); + try { if (this.app.workspace.layoutReady) { const folderOverview = new FolderOverview(this, ctx, source, el); folderOverview.create(this, parseYaml(source), el, ctx); } else { this.app.workspace.onLayoutReady(() => { - console.log('layout ready'); const folderOverview = new FolderOverview(this, ctx, source, el); folderOverview.create(this, parseYaml(source), el, ctx); }); @@ -216,7 +227,7 @@ export default class FolderNotesPlugin extends Plugin { const attachmentsAreInRootFolder = attachmentFolderPath === './' || attachmentFolderPath === ''; const threshold = this.settings.storageLocation === 'insideFolder' ? 1 : 0; if (folder.children.length == 0) { - addCSSClassToTitleEL(this, folder.path, 'fn-empty-folder'); + addCSSClassToTitleEL(folder.path, 'fn-empty-folder'); } if (folder.children.length == threshold) { diff --git a/src/suggesters/FileSuggester.ts b/src/suggesters/FileSuggester.ts index 6b0c685..09777da 100644 --- a/src/suggesters/FileSuggester.ts +++ b/src/suggesters/FileSuggester.ts @@ -11,9 +11,9 @@ export enum FileSuggestMode { export class FileSuggest extends TextInputSuggest { constructor( public inputEl: HTMLInputElement, - private plugin: FolderNotesPlugin + plugin: FolderNotesPlugin ) { - super(inputEl); + super(inputEl, plugin); } diff --git a/src/suggesters/FolderSuggester.ts b/src/suggesters/FolderSuggester.ts index 1da9087..7d3fb00 100644 --- a/src/suggesters/FolderSuggester.ts +++ b/src/suggesters/FolderSuggester.ts @@ -11,11 +11,11 @@ export enum FileSuggestMode { export class FolderSuggest extends TextInputSuggest { constructor( public inputEl: HTMLInputElement, - private plugin: FolderNotesPlugin, + plugin: FolderNotesPlugin, private whitelistSuggester: boolean, public folder?: TFolder, ) { - super(inputEl); + super(inputEl, plugin); } diff --git a/src/suggesters/Suggest.ts b/src/suggesters/Suggest.ts index d3f7f4f..fa92e75 100644 --- a/src/suggesters/Suggest.ts +++ b/src/suggesters/Suggest.ts @@ -3,6 +3,7 @@ import { ISuggestOwner, Scope } from 'obsidian'; import { createPopper, Instance as PopperInstance } from '@popperjs/core'; +import FolderNotesPlugin from 'src/main'; const wrapAround = (value: number, size: number): number => { return ((value % size) + size) % size; @@ -14,6 +15,7 @@ class Suggest { private suggestions: HTMLDivElement[]; private selectedItem: number; private containerEl: HTMLElement; + plugin: FolderNotesPlugin; constructor( owner: ISuggestOwner, @@ -117,12 +119,14 @@ export abstract class TextInputSuggest implements ISuggestOwner { private scope: Scope; private suggestEl: HTMLElement; private suggest: Suggest; + plugin: FolderNotesPlugin; - constructor(inputEl: HTMLInputElement | HTMLTextAreaElement) { + constructor(inputEl: HTMLInputElement | HTMLTextAreaElement, plugin: FolderNotesPlugin) { this.inputEl = inputEl; + this.plugin = plugin; this.scope = new Scope(); - this.suggestEl = createDiv('fn-suggestion-container'); + this.suggestEl = createDiv('suggestion-container'); const suggestion = this.suggestEl.createDiv('suggestion'); this.suggest = new Suggest(this, suggestion, this.scope); @@ -133,7 +137,7 @@ export abstract class TextInputSuggest implements ISuggestOwner { this.inputEl.addEventListener('blur', this.close.bind(this)); this.suggestEl.on( 'mousedown', - '.fn-suggestion-container', + '.suggestion-container', (event: MouseEvent) => { event.preventDefault(); } @@ -160,7 +164,7 @@ export abstract class TextInputSuggest implements ISuggestOwner { open(container: HTMLElement, inputEl: HTMLElement): void { // eslint-disable-next-line @typescript-eslint/no-explicit-any - app.keymap.pushScope(this.scope); + this.plugin.app.keymap.pushScope(this.scope); container.appendChild(this.suggestEl); this.popper = createPopper(inputEl, this.suggestEl, { @@ -189,7 +193,7 @@ export abstract class TextInputSuggest implements ISuggestOwner { } close(): void { - app.keymap.popScope(this.scope); + this.plugin.app.keymap.popScope(this.scope); this.suggest.setSuggestions([]); if (this.popper) this.popper.destroy(); diff --git a/src/suggesters/TemplateSuggester.ts b/src/suggesters/TemplateSuggester.ts index a32abc3..f73edf1 100644 --- a/src/suggesters/TemplateSuggester.ts +++ b/src/suggesters/TemplateSuggester.ts @@ -12,9 +12,9 @@ export enum FileSuggestMode { export class TemplateSuggest extends TextInputSuggest { constructor( public inputEl: HTMLInputElement, - private plugin: FolderNotesPlugin + plugin: FolderNotesPlugin ) { - super(inputEl); + super(inputEl, plugin); } diff --git a/styles.css b/styles.css index 0007f64..fe2301c 100644 --- a/styles.css +++ b/styles.css @@ -5,6 +5,10 @@ padding-top: 4px !important; } +.fn-whitespace-stop-collapsing .collapse-icon { + padding-top: 4px !important; +} + .mod-rtl .fn-whitespace-stop-collapsing .nav-folder-title-content { padding-left: 8px !important; } @@ -266,4 +270,4 @@ body:not(.disable-folder-highlight) .tree-item-self.fn-is-active { border: 1px solid var(--background-modifier-border); box-shadow: var(--shadow-s); z-index: var(--layer-notice); -} \ No newline at end of file +}