diff --git a/README.md b/README.md index d548dc3..d08c1b6 100644 --- a/README.md +++ b/README.md @@ -12,8 +12,9 @@ The factors include, letter count, forward & backward weight, and forward tree w | ------------------------------- | ------------------------------------------------------------------------------------------------------- | ------------- | | Forward link weight multiplier | Weight of single link coming forward out of a node | 1 | | Travel forward tree | Determines if forward weight is decided by just the immediate nodes coming out or everything after it | off | -| Backward link weight multiplier | Weight of single link coming backward out of a node | 1 | +| Backward link weight multiplier | Weight of single link coming backward out of a node | 1 | | Character per weight | Given number of letters give 1 weight | 0 | +| Manually Set Weight | Manually set weight of any file, weight set here overrides everything else | empty set | ## Author CalfMoon: [Email](kritagyabhattarai@proton.me), [Github](https://github.com/CalfMoon) ## Bug Reports diff --git a/src/file-suggest.ts b/src/file-suggest.ts new file mode 100644 index 0000000..6721f9c --- /dev/null +++ b/src/file-suggest.ts @@ -0,0 +1,32 @@ +import { App, AbstractInputSuggest } from "obsidian"; + +export default class FileSuggest extends AbstractInputSuggest { + private files: Array; + private inputEl: HTMLInputElement; + + constructor(app: App, inputEl: HTMLInputElement) { + super(app, inputEl); + + this.inputEl = inputEl; + this.files = this.app.vault.getFiles().map((file) => file.path); + } + + getSuggestions(inputStr: string): string[] { + const inputLower = inputStr.toLowerCase(); + + return this.files.filter((file) => + file.toLowerCase().includes(inputLower), + ); + } + + renderSuggestion(folder: string, el: HTMLElement): void { + el.setText(folder); + } + + selectSuggestion(folder: string): void { + this.inputEl.value = folder; + const event = new Event("input"); + this.inputEl.dispatchEvent(event); + this.close(); + } +} diff --git a/src/main.ts b/src/main.ts index 2f400ea..ee08ba1 100644 --- a/src/main.ts +++ b/src/main.ts @@ -11,10 +11,12 @@ export default class NodeFactor extends Plugin { this.addSettingTab(new NodeFactorSettingTab(this.app, this)); this.registerEvent( - this.app.workspace.on("active-leaf-change", () => { - // we can still use cache when only active leaf changes - this.updateGraph(); - }), + this.app.workspace.on("active-leaf-change", () => + this.updateGraph(), + ), + ); + this.registerEvent( + this.app.workspace.on("layout-change", () => this.updateGraph()), ); // clear cache when there is change in the vault @@ -71,6 +73,13 @@ export default class NodeFactor extends Plugin { const settings = this.settings; let weight = 0; + const manualFileData = settings.manual.find( + (manualFileData) => manualFileData.id == node.id, + ); + if (manualFileData != null) { + return manualFileData.weight; + } + weight += Object.keys(node.reverse).length * settings.bwdMultiplier; if (settings.fwdTree) { weight += diff --git a/src/settings.ts b/src/settings.ts index 7210b88..052b383 100644 --- a/src/settings.ts +++ b/src/settings.ts @@ -1,6 +1,16 @@ -import { App, PluginSettingTab, Setting } from "obsidian"; +import { + App, + ButtonComponent, + Notice, + PluginSettingTab, + SearchComponent, + Setting, + SliderComponent, +} from "obsidian"; import NodeFactor from "./main"; +import FileSuggest from "./file-suggest"; +import { FileData } from "./types"; export default class NodeFactorSettingTab extends PluginSettingTab { plugin: NodeFactor; @@ -14,57 +24,61 @@ export default class NodeFactorSettingTab extends PluginSettingTab { const { containerEl } = this; containerEl.empty(); + new Setting(containerEl) + .setName("Programatically Set Size") + .setHeading(); + new Setting(containerEl) .setName("Forward link weight multiplier") .setDesc("Multiplier for forward links weight (0 to disable).") - .addSlider((slider) => + .addSlider((slider) => { slider .setLimits(0, 20, 1) .setDynamicTooltip() .setValue(this.plugin.settings.fwdMultiplier) .onChange(async (value) => { - this.plugin.recalculateSize(); this.plugin.settings.fwdMultiplier = value; await this.plugin.saveSettings(); - }), - ); + this.plugin.recalculateSize(); + }); + }); new Setting(containerEl) .setName("Travel forward tree") .setDesc( "Travel forward and add all other nodes to determine final node size.", ) - .addToggle((toggle) => + .addToggle((toggle) => { toggle .setValue(this.plugin.settings.fwdTree) .onChange(async (value) => { - this.plugin.recalculateSize(); this.plugin.settings.fwdTree = value; await this.plugin.saveSettings(); - }), - ); + this.plugin.recalculateSize(); + }); + }); new Setting(containerEl) .setName("Backward link weight multiplier") .setDesc("Multiplier for backward links weight (0 to disable).") - .addSlider((slider) => + .addSlider((slider) => { slider .setLimits(0, 20, 1) .setDynamicTooltip() .setValue(this.plugin.settings.bwdMultiplier) .onChange(async (value) => { - this.plugin.recalculateSize(); this.plugin.settings.bwdMultiplier = value; await this.plugin.saveSettings(); - }), - ); + this.plugin.recalculateSize(); + }); + }); new Setting(containerEl) .setName("Character per weight") .setDesc( "Add 1 weight to node size per no of given character (0 to disable).", ) - .addSlider((slider) => + .addSlider((slider) => { slider .setLimits(0, 5000, 100) .setDynamicTooltip() @@ -72,7 +86,82 @@ export default class NodeFactorSettingTab extends PluginSettingTab { .onChange(async (value) => { this.plugin.settings.lettersPerWt = value; await this.plugin.saveSettings(); - }), - ); + this.plugin.recalculateSize(); + }); + }); + + new Setting(containerEl).setName("Manually Set Weight").setHeading(); + + let selectedWeight: SliderComponent; + let selectedFile: SearchComponent; + let submitButton: ButtonComponent; + new Setting(containerEl) + .setName("Add new weight") + .setDesc("Weight added here overrides everything else.") + .addSearch((search) => { + new FileSuggest(this.app, search.inputEl); + selectedFile = search; + search + .setPlaceholder("Enter File Name") + .onChange(async (value) => { + if (value != "") submitButton.setDisabled(false); + }); + }) + .addSlider((slider) => { + selectedWeight = slider; + slider.setLimits(0, 100, 5).setDynamicTooltip().setValue(0); + }) + .addButton((button) => { + submitButton = button; + button + .setDisabled(true) + .setButtonText("Add") + .setTooltip("Click to add") + .onClick(async () => { + const enteredFileData: FileData = { + id: selectedFile.getValue(), + weight: selectedWeight.getValue(), + }; + selectedWeight.setValue(0); + selectedFile.setValue(""); + + const fileExists = this.plugin.settings.manual.find( + (foundFile) => { + foundFile.id == enteredFileData.id; + }, + ); + + if (!fileExists) { + new Notice(`That file's size has already been entered, + remove it first to change weight.`); + return; + } + + this.plugin.settings.manual.push(enteredFileData); + await this.plugin.saveSettings(); + new Notice("Manual Size added"); + + // Rerender display + this.display(); + this.plugin.recalculateSize(); + }); + }); + + // Display all manually added weights + this.plugin.settings.manual.forEach((value: FileData) => { + new Setting(containerEl) + .setName(value.id) + .setDesc(`Weight: ${String(value.weight)}`) + .addButton((button) => { + button + .setIcon("trash") + .setTooltip("Remove Manually added size") + .onClick(async () => { + this.plugin.settings.manual.remove(value); + await this.plugin.saveSettings(); + this.display(); + }); + }); + }); } } diff --git a/src/types.ts b/src/types.ts index 68f17f6..5a808fb 100644 --- a/src/types.ts +++ b/src/types.ts @@ -12,6 +12,13 @@ export interface NodeFactorSettings { bwdMultiplier: number; lettersPerWt: number; + + manual: Array; +} + +export interface FileData { + id: string; + weight: number; } export const DEFAULT_SETTINGS: NodeFactorSettings = { @@ -21,4 +28,6 @@ export const DEFAULT_SETTINGS: NodeFactorSettings = { bwdMultiplier: 1, lettersPerWt: 0, + + manual: new Array(), };