Add YAML file support: views, settings, and syntax highlighting (#26)

Fixes #25
This commit is contained in:
Stuart Gilbert 2026-01-28 21:06:35 -08:00 committed by GitHub
parent 5264f26ae6
commit 09ab9a3fe2
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
9 changed files with 127 additions and 16 deletions

View file

@ -1,11 +1,11 @@
{
"id": "data-files-editor",
"name": "Data Files Editor",
"version": "1.2.1",
"version": "1.2.2",
"minAppVersion": "0.15.0",
"description": "Plugin to edit data files like txt, xml, json",
"description": "Plugin to edit data files like txt, xml, json, and yaml",
"author": "ZukTol",
"authorUrl": "https://github.com/ZukTol",
"fundingUrl": "",
"isDesktopOnly": false
}
}

54
package-lock.json generated
View file

@ -1,16 +1,17 @@
{
"name": "data-files-loader",
"version": "1.2.0",
"version": "1.2.2",
"lockfileVersion": 3,
"requires": true,
"packages": {
"": {
"name": "data-files-loader",
"version": "1.2.0",
"version": "1.2.1",
"license": "MIT",
"dependencies": {
"@codemirror/commands": "^6.10.0",
"@codemirror/lang-json": "^6.0.2",
"@codemirror/lang-yaml": "^6.1.1",
"@codemirror/state": "^6.5.2",
"@codemirror/theme-one-dark": "^6.1.3",
"@codemirror/view": "^6.38.6",
@ -77,6 +78,21 @@
"@lezer/json": "^1.0.0"
}
},
"node_modules/@codemirror/lang-yaml": {
"version": "6.1.2",
"resolved": "https://registry.npmjs.org/@codemirror/lang-yaml/-/lang-yaml-6.1.2.tgz",
"integrity": "sha512-dxrfG8w5Ce/QbT7YID7mWZFKhdhsaTNOYjOkSIMt1qmC4VQnXSDSYVHHHn8k6kJUfIhtLo8t1JJgltlxWdsITw==",
"license": "MIT",
"dependencies": {
"@codemirror/autocomplete": "^6.0.0",
"@codemirror/language": "^6.0.0",
"@codemirror/state": "^6.0.0",
"@lezer/common": "^1.2.0",
"@lezer/highlight": "^1.2.0",
"@lezer/lr": "^1.0.0",
"@lezer/yaml": "^1.0.0"
}
},
"node_modules/@codemirror/language": {
"version": "6.9.2",
"resolved": "https://registry.npmjs.org/@codemirror/language/-/language-6.9.2.tgz",
@ -592,16 +608,18 @@
"peer": true
},
"node_modules/@lezer/common": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/@lezer/common/-/common-1.1.0.tgz",
"integrity": "sha512-XPIN3cYDXsoJI/oDWoR2tD++juVrhgIago9xyKhZ7IhGlzdDM9QgC8D8saKNCz5pindGcznFr2HBSsEQSWnSjw=="
"version": "1.5.0",
"resolved": "https://registry.npmjs.org/@lezer/common/-/common-1.5.0.tgz",
"integrity": "sha512-PNGcolp9hr4PJdXR4ix7XtixDrClScvtSCYW3rQG106oVMOOI+jFb+0+J3mbeL/53g1Zd6s0kJzaw6Ri68GmAA==",
"license": "MIT"
},
"node_modules/@lezer/highlight": {
"version": "1.1.6",
"resolved": "https://registry.npmjs.org/@lezer/highlight/-/highlight-1.1.6.tgz",
"integrity": "sha512-cmSJYa2us+r3SePpRCjN5ymCqCPv+zyXmDl0ciWtVaNiORT/MxM7ZgOMQZADD0o51qOaOg24qc/zBViOIwAjJg==",
"version": "1.2.3",
"resolved": "https://registry.npmjs.org/@lezer/highlight/-/highlight-1.2.3.tgz",
"integrity": "sha512-qXdH7UqTvGfdVBINrgKhDsVTJTxactNNxLk7+UMwZhU13lMHaOBlJe9Vqp907ya56Y3+ed2tlqzys7jDkTmW0g==",
"license": "MIT",
"dependencies": {
"@lezer/common": "^1.0.0"
"@lezer/common": "^1.3.0"
}
},
"node_modules/@lezer/json": {
@ -614,13 +632,25 @@
}
},
"node_modules/@lezer/lr": {
"version": "1.3.14",
"resolved": "https://registry.npmjs.org/@lezer/lr/-/lr-1.3.14.tgz",
"integrity": "sha512-z5mY4LStlA3yL7aHT/rqgG614cfcvklS+8oFRFBYrs4YaWLJyKKM4+nN6KopToX0o9Hj6zmH6M5kinOYuy06ug==",
"version": "1.4.7",
"resolved": "https://registry.npmjs.org/@lezer/lr/-/lr-1.4.7.tgz",
"integrity": "sha512-wNIFWdSUfX9Jc6ePMzxSPVgTVB4EOfDIwLQLWASyiUdHKaMsiilj9bYiGkGQCKVodd0x6bgQCV207PILGFCF9Q==",
"license": "MIT",
"dependencies": {
"@lezer/common": "^1.0.0"
}
},
"node_modules/@lezer/yaml": {
"version": "1.0.3",
"resolved": "https://registry.npmjs.org/@lezer/yaml/-/yaml-1.0.3.tgz",
"integrity": "sha512-GuBLekbw9jDBDhGur82nuwkxKQ+a3W5H0GfaAthDXcAu+XdpS43VlnxA9E9hllkpSP5ellRDKjLLj7Lu9Wr6xA==",
"license": "MIT",
"dependencies": {
"@lezer/common": "^1.2.0",
"@lezer/highlight": "^1.0.0",
"@lezer/lr": "^1.4.0"
}
},
"node_modules/@marijn/find-cluster-break": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/@marijn/find-cluster-break/-/find-cluster-break-1.0.2.tgz",

View file

@ -25,6 +25,7 @@
"dependencies": {
"@codemirror/commands": "^6.10.0",
"@codemirror/lang-json": "^6.0.2",
"@codemirror/lang-yaml": "^6.1.1",
"@codemirror/state": "^6.5.2",
"@codemirror/theme-one-dark": "^6.1.3",
"@codemirror/view": "^6.38.6",

View file

@ -2,7 +2,10 @@ export const VIEW_TYPE_JSON = "json";
export const VIEW_TYPE_XML = "xml";
export const VIEW_TYPE_TXT = "txt";
export const VIEW_TYPE_MARKDOWN = "markdown";
export const VIEW_TYPE_YAML = "yaml";
export const EXT_JSON = "json";
export const EXT_XML = "xml";
export const EXT_TXT = "txt";
export const EXT_YAML = "yaml";
export const EXT_YML = "yml";

View file

@ -5,6 +5,8 @@
doCreateXml: boolean;
doLoadJson: boolean;
doCreateJson: boolean;
doLoadYaml: boolean;
doCreateYaml: boolean;
doAutosaveFiles: boolean;
lineWrapping: boolean;
}
@ -16,6 +18,8 @@ export const DEFAULT_SETTINGS: LoaderPluginSettings = {
doCreateXml: true,
doLoadJson: true,
doCreateJson: true,
doLoadYaml: true,
doCreateYaml: true,
doAutosaveFiles: true,
lineWrapping: true
}

View file

@ -72,6 +72,24 @@ export default class LoaderSettingTab extends PluginSettingTab {
await this.plugin.saveSettings();
}));
new Setting(containerEl)
.setName('Load .yaml/.yml files')
.addToggle(toggle => toggle
.setValue(this.plugin.settings.doLoadYaml)
.onChange(async (value) => {
this.plugin.settings.doLoadYaml = value;
await this.plugin.saveSettings();
}));
new Setting(containerEl)
.setName('Create .yaml files')
.addToggle(toggle => toggle
.setValue(this.plugin.settings.doCreateYaml)
.onChange(async (value) => {
this.plugin.settings.doCreateYaml = value;
await this.plugin.saveSettings();
}));
new Setting(containerEl)
.setName('Enable autosave for files')
.addToggle(toggle => toggle

View file

@ -4,6 +4,7 @@ import * as constants from './constants'
import {path} from "./utils";
import JsonView from "./views/json-view";
import TxtView from "./views/txt-view";
import YamlView from "./views/yaml-view";
import {DEFAULT_SETTINGS, LoaderPluginSettings} from "./loader-plugin-settings";
export default class LoaderPlugin extends Plugin {
@ -18,6 +19,8 @@ export default class LoaderPlugin extends Plugin {
this.tryRegisterXml();
this.tryRegisterYaml();
// This adds a settings tab so the user can configure various aspects of the plugin
this.addSettingTab(new LoaderSettingTab(this.app, this));
}
@ -51,6 +54,15 @@ export default class LoaderPlugin extends Plugin {
}
}
private tryRegisterYaml(): void {
if (this.settings.doLoadYaml) {
this.registerView(constants.VIEW_TYPE_YAML, (leaf: WorkspaceLeaf) => new YamlView(leaf, this));
this.registerExtensions([constants.EXT_YAML, constants.EXT_YML], constants.VIEW_TYPE_YAML);
}
if (this.settings.doCreateYaml)
this.registerContextMenuCommand(constants.EXT_YAML);
}
onunload(): void {
}

View file

@ -1,13 +1,15 @@
import {App} from "obsidian";
import BaseView from "../views/base-view";
import {VIEW_TYPE_JSON, VIEW_TYPE_TXT} from "../constants";
import {VIEW_TYPE_JSON, VIEW_TYPE_TXT, VIEW_TYPE_YAML} from "../constants";
import JsonView from "../views/json-view";
import TxtView from "../views/txt-view";
import YamlView from "../views/yaml-view";
export function getLoaderViews(app: App): BaseView[] {
const leaves = [
...app.workspace.getLeavesOfType(VIEW_TYPE_JSON).filter(l => l.view instanceof JsonView),
...app.workspace.getLeavesOfType(VIEW_TYPE_TXT).filter(l => l.view instanceof TxtView),
...app.workspace.getLeavesOfType(VIEW_TYPE_YAML).filter(l => l.view instanceof YamlView),
];
return leaves.map(l => l.view as BaseView);
}

41
src/views/yaml-view.ts Normal file
View file

@ -0,0 +1,41 @@
import { WorkspaceLeaf } from "obsidian";
import { yaml } from "@codemirror/lang-yaml";
import { Extension } from "@codemirror/state";
import { HighlightStyle, syntaxHighlighting } from "@codemirror/language";
import { tags } from "@lezer/highlight";
import { VIEW_TYPE_YAML } from '../constants'
import LoaderPlugin from "../main";
import { getIndentByTabExtension } from "../services/indentation-provider"
import BaseView from "./base-view";
const yamlDarkHighlight = HighlightStyle.define([
{ tag: tags.propertyName, color: "#e5c07b" }, // keys - warm yellow/gold
{ tag: tags.string, color: "#98c379" }, // string values - green
{ tag: tags.number, color: "#d19a66" }, // numbers - orange
{ tag: tags.bool, color: "#d19a66" }, // booleans - orange
{ tag: tags.null, color: "#d19a66" }, // null - orange
{ tag: tags.comment, color: "#7f848e" }, // comments - gray
]);
export default class YamlView extends BaseView {
constructor(leaf: WorkspaceLeaf, plugin: LoaderPlugin) {
super(leaf, plugin);
}
getViewType(): string {
return VIEW_TYPE_YAML;
}
protected getEditorExtensions(): Extension[] {
const extensions: Extension[] = [
getIndentByTabExtension(),
yaml()
];
if (document.body.classList.contains('theme-dark')) {
extensions.push(syntaxHighlighting(yamlDarkHighlight));
}
return extensions;
}
}