feat: add a setting to manually clear the highlights, make automatically clearing highlights the default when there is a change in editor

This commit is contained in:
rivea0 2025-07-03 11:30:42 +03:00
parent 126f1c9d0a
commit 348d451723
4 changed files with 95 additions and 57 deletions

View file

@ -197,7 +197,7 @@ You can choose "Enter match syntax" to write your syntax and click "Find matches
You can bind hotkeys for the commands by going to **Community plugins**, find MatchSyntax in Installed Plugins, and choosing "Hotkeys" button.
At the moment, highlights will stay until you explicitly clear them.
Highlights are cleared automatically when there is a change in editor. You can override this behavior by setting "Manually clear the highlights" on inside plugin settings.
### TODO and Ideas
- Custom tags

View file

@ -1,13 +1,20 @@
import { App, Notice, Plugin, PluginSettingTab, Setting } from 'obsidian';
import { Notice, Plugin } from 'obsidian';
import { EditorView, ViewPlugin, Decoration } from '@codemirror/view';
import { MatchTextModal } from './modal';
import { getMatchRanges } from './utils';
import MatchSyntaxString from './syntaxObj';
import type { PluginValue, DecorationSet, PluginSpec, ViewUpdate } from '@codemirror/view';
import type {
PluginValue,
DecorationSet,
PluginSpec,
ViewUpdate,
} from '@codemirror/view';
import type { MatchSyntaxPluginSettings, IRange } from './types';
import { keepHighlights, MatchSyntaxSettingTab } from './settings';
const DEFAULT_SETTINGS: MatchSyntaxPluginSettings = {
showNumberOfMatchesNotification: true,
manuallyClearHighlights: false,
};
const SYNTAX = new MatchSyntaxString();
@ -40,8 +47,12 @@ export default class MatchSyntaxPlugin extends Plugin {
plugin.makeDeco(ranges);
}
if (this.settings.showNumberOfMatchesNotification) {
const numberOfMatches = ranges.length
new Notice(`${numberOfMatches} match${numberOfMatches === 1 ? '' : 'es'} found.`);
const numberOfMatches = ranges.length;
new Notice(
`${numberOfMatches} match${
numberOfMatches === 1 ? '' : 'es'
} found.`
);
}
}).open();
},
@ -56,13 +67,13 @@ export default class MatchSyntaxPlugin extends Plugin {
const plugin = cm6Editor.plugin(highlightViewPlugin);
if (plugin) {
if (plugin.decorations === Decoration.none) {
new Notice('No decorations found!');
new Notice('No highlights found!');
} else {
SYNTAX.clearValue();
plugin.clearDeco();
}
}
}
},
});
}
@ -82,35 +93,6 @@ export default class MatchSyntaxPlugin extends Plugin {
}
}
class MatchSyntaxSettingTab extends PluginSettingTab {
plugin: MatchSyntaxPlugin;
constructor(app: App, plugin: MatchSyntaxPlugin) {
super(app, plugin);
this.plugin = plugin;
}
display(): void {
const { containerEl } = this;
containerEl.empty();
new Setting(containerEl)
.setName('Notify the number of matches found')
.setDesc(
'The number of match results will be shown in a notification when you search for a match syntax'
)
.addToggle((toggle) => {
toggle
.setValue(this.plugin.settings.showNumberOfMatchesNotification)
.onChange(async (value) => {
this.plugin.settings.showNumberOfMatchesNotification = value;
await this.plugin.saveSettings();
});
});
}
}
class HighlighterPlugin implements PluginValue {
decorations: DecorationSet;
constructor(view: EditorView) {
@ -120,9 +102,14 @@ class HighlighterPlugin implements PluginValue {
update(viewUpdate: ViewUpdate) {
if (viewUpdate.docChanged) {
if (this.decorations !== Decoration.none) {
const docEl = viewUpdate.view.state.doc;
const ranges = getMatchRanges(docEl, SYNTAX.getValue());
this.makeDeco(ranges);
if (!keepHighlights) {
SYNTAX.clearValue();
this.clearDeco();
} else {
const docEl = viewUpdate.view.state.doc;
const ranges = getMatchRanges(docEl, SYNTAX.getValue());
this.makeDeco(ranges);
}
}
}
}

50
src/settings.ts Normal file
View file

@ -0,0 +1,50 @@
import { App, PluginSettingTab, Setting } from 'obsidian';
import MatchSyntaxPlugin from './main';
let keepHighlights = false;
export class MatchSyntaxSettingTab extends PluginSettingTab {
plugin: MatchSyntaxPlugin;
constructor(app: App, plugin: MatchSyntaxPlugin) {
super(app, plugin);
this.plugin = plugin;
}
display(): void {
const { containerEl } = this;
containerEl.empty();
new Setting(containerEl)
.setName('Notify the number of matches found')
.setDesc(
'The number of match results will be shown in a notification when you search for a match syntax'
)
.addToggle((toggle) => {
toggle
.setValue(this.plugin.settings.showNumberOfMatchesNotification)
.onChange(async (value) => {
this.plugin.settings.showNumberOfMatchesNotification = value;
await this.plugin.saveSettings();
});
});
new Setting(containerEl)
.setName('Manually clear the highlights')
.setDesc(
'Do not automatically clear highlights when there is a change in the editor'
)
.addToggle((toggle) => {
toggle
.setValue(this.plugin.settings.manuallyClearHighlights)
.onChange(async (value) => {
this.plugin.settings.manuallyClearHighlights = value;
await this.plugin.saveSettings();
keepHighlights = !keepHighlights;
});
});
}
}
export { keepHighlights };

View file

@ -1,31 +1,32 @@
export interface MatchSyntaxPluginSettings {
showNumberOfMatchesNotification: boolean;
manuallyClearHighlights: boolean;
}
export interface IOffsetOutput {
text: string,
text: string;
terms: {
text: string,
pre: string,
post: string,
tags: string[],
normal: string,
index: number[],
id: string,
chunk: string,
dirty: boolean,
offset: IOffset
}[],
offset: IOffset
text: string;
pre: string;
post: string;
tags: string[];
normal: string;
index: number[];
id: string;
chunk: string;
dirty: boolean;
offset: IOffset;
}[];
offset: IOffset;
}
export interface IRange {
from: number,
to: number
from: number;
to: number;
}
interface IOffset {
index: number,
start: number,
length: number
index: number;
start: number;
length: number;
}