Skip to content

Commit 9010a5f

Browse files
committed
move some things
1 parent f178045 commit 9010a5f

File tree

3 files changed

+57
-43
lines changed

3 files changed

+57
-43
lines changed

src/Highlighter.ts

Lines changed: 53 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,15 @@
11
import { ExpressiveCodeEngine, ExpressiveCodeTheme } from '@expressive-code/core';
22
import type ShikiPlugin from 'src/main';
3-
import { bundledLanguages, createHighlighter, type DynamicImportLanguageRegistration, type LanguageRegistration, type Highlighter } from 'shiki/index.mjs';
3+
import {
4+
bundledLanguages,
5+
createHighlighter,
6+
type DynamicImportLanguageRegistration,
7+
type LanguageRegistration,
8+
type Highlighter,
9+
type TokensResult,
10+
type BundledLanguage,
11+
type ThemedToken,
12+
} from 'shiki/index.mjs';
413
import { ThemeMapper } from 'src/themes/ThemeMapper';
514
import { pluginShiki } from '@expressive-code/plugin-shiki';
615
import { pluginCollapsibleSections } from '@expressive-code/plugin-collapsible-sections';
@@ -178,6 +187,20 @@ export class CodeHighlighter {
178187
return this.plugin.loadedSettings.theme.endsWith('.json');
179188
}
180189

190+
/**
191+
* Returns a list of languages registrations that need to be loaded into Shiki and EC.
192+
*/
193+
getLoadedLanguageRegistrations(): (DynamicImportLanguageRegistration | LanguageRegistration)[] {
194+
return [...Object.values(bundledLanguages), ...this.customLanguages];
195+
}
196+
197+
/**
198+
* All languages that are safe to use with Obsidian's `registerMarkdownCodeBlockProcessor`.
199+
*/
200+
obsidianSafeLanguageNames(): string[] {
201+
return this.loadedLanguages.filter(lang => !languageNameBlacklist.has(lang));
202+
}
203+
181204
/**
182205
* Highlights code with EC and renders it to the passed container element.
183206
*/
@@ -191,11 +214,36 @@ export class CodeHighlighter {
191214
container.innerHTML = toHtml(this.themeMapper.fixAST(result.renderedGroupAst));
192215
}
193216

194-
getLoadedLanguageRegistrations(): (DynamicImportLanguageRegistration | LanguageRegistration)[] {
195-
return [...Object.values(bundledLanguages), ...this.customLanguages];
217+
getHighlightTokens(code: string, lang: string): TokensResult | undefined {
218+
if (!this.obsidianSafeLanguageNames().includes(lang)) {
219+
return undefined;
220+
}
221+
222+
return this.shiki.codeToTokens(code, {
223+
lang: lang as BundledLanguage,
224+
theme: this.plugin.settings.theme,
225+
});
196226
}
197227

198-
obsidianSafeLanguageNames(): string[] {
199-
return this.loadedLanguages.filter(lang => !languageNameBlacklist.has(lang));
228+
tokenToSpan(token: ThemedToken, parent: HTMLElement): void {
229+
const tokenStyle = this.getTokenStyle(token);
230+
parent.createSpan({
231+
text: token.content,
232+
cls: tokenStyle.classes.join(' '),
233+
attr: { style: tokenStyle.style },
234+
});
235+
}
236+
237+
getTokenStyle(token: ThemedToken): { style: string; classes: string[] } {
238+
const fontStyle = token.fontStyle ?? 0;
239+
240+
return {
241+
style: `color: ${token.color}`,
242+
classes: [
243+
(fontStyle & 1) !== 0 ? 'shiki-italic' : undefined,
244+
(fontStyle & 2) !== 0 ? 'shiki-bold' : undefined,
245+
(fontStyle & 4) !== 0 ? 'shiki-ul' : undefined,
246+
].filter(Boolean) as string[],
247+
};
200248
}
201249
}

src/codemirror/Cm6_ViewPlugin.ts

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -202,7 +202,7 @@ export function createCm6Plugin(plugin: ShikiPlugin) {
202202
* @param content
203203
*/
204204
buildDecorations(from: number, to: number, language: string, content: string): Range<Decoration>[] {
205-
const highlight = plugin.getHighlightTokens(content, language);
205+
const highlight = plugin.highlighter.getHighlightTokens(content, language);
206206

207207
if (!highlight) {
208208
return [];
@@ -216,7 +216,7 @@ export function createCm6Plugin(plugin: ShikiPlugin) {
216216
const token = tokens[i];
217217
const nextToken: ThemedToken | undefined = tokens[i + 1];
218218

219-
const tokenStyle = plugin.getTokenStyle(token);
219+
const tokenStyle = plugin.highlighter.getTokenStyle(token);
220220

221221
decorations.push(
222222
Decoration.mark({

src/main.ts

Lines changed: 2 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,4 @@
11
import { loadPrism, Plugin, TFile, type MarkdownPostProcessor } from 'obsidian';
2-
import { type BundledLanguage, type ThemedToken, type TokensResult } from 'shiki';
32
import { CodeBlock } from 'src/CodeBlock';
43
import { createCm6Plugin } from 'src/codemirror/Cm6_ViewPlugin';
54
import { DEFAULT_SETTINGS, type Settings } from 'src/settings/Settings';
@@ -111,7 +110,7 @@ export default class ShikiPlugin extends Plugin {
111110
for (let codeElm of inlineCodes) {
112111
let match = codeElm.textContent?.match(SHIKI_INLINE_REGEX); // format: `{lang} code`
113112
if (match) {
114-
const highlight = this.getHighlightTokens(match[2], match[1]);
113+
const highlight = this.highlighter.getHighlightTokens(match[2], match[1]);
115114
const tokens = highlight?.tokens.flat(1);
116115
if (!tokens?.length) {
117116
continue;
@@ -121,7 +120,7 @@ export default class ShikiPlugin extends Plugin {
121120
codeElm.addClass('shiki-inline');
122121

123122
for (let token of tokens) {
124-
this.tokenToSpan(token, codeElm);
123+
this.highlighter.tokenToSpan(token, codeElm);
125124
}
126125
}
127126
}
@@ -153,39 +152,6 @@ export default class ShikiPlugin extends Plugin {
153152
}
154153
}
155154

156-
getHighlightTokens(code: string, lang: string): TokensResult | undefined {
157-
if (!this.highlighter.obsidianSafeLanguageNames().includes(lang)) {
158-
return undefined;
159-
}
160-
161-
return this.highlighter.shiki.codeToTokens(code, {
162-
lang: lang as BundledLanguage,
163-
theme: this.settings.theme,
164-
});
165-
}
166-
167-
tokenToSpan(token: ThemedToken, parent: HTMLElement): void {
168-
const tokenStyle = this.getTokenStyle(token);
169-
parent.createSpan({
170-
text: token.content,
171-
cls: tokenStyle.classes.join(' '),
172-
attr: { style: tokenStyle.style },
173-
});
174-
}
175-
176-
getTokenStyle(token: ThemedToken): { style: string; classes: string[] } {
177-
let fontStyle = token.fontStyle ?? 0;
178-
179-
return {
180-
style: `color: ${token.color}`,
181-
classes: [
182-
(fontStyle & 1) !== 0 ? 'shiki-italic' : undefined,
183-
(fontStyle & 2) !== 0 ? 'shiki-bold' : undefined,
184-
(fontStyle & 4) !== 0 ? 'shiki-ul' : undefined,
185-
].filter(Boolean) as string[],
186-
};
187-
}
188-
189155
async loadSettings(): Promise<void> {
190156
this.settings = Object.assign({}, DEFAULT_SETTINGS, await this.loadData()) as Settings;
191157
}

0 commit comments

Comments
 (0)