Добавлена функция рендеринга вложенных токенов в markdown, улучшена обработка текстовых элементов и ссылок с поддержкой кастомных рендереров. Обновлены компоненты для корректного отображения вложенных структур в списках и ссылках.

This commit is contained in:
Fovway 2025-11-04 12:33:51 +07:00
parent a5f4e87056
commit bdd932bbbb

View File

@ -23,12 +23,66 @@ const spoilerExtension = {
},
};
// Функция для рендеринга вложенных токенов
function renderTokens(tokens: any[], renderer: any): string {
return tokens.map((token) => {
// Используем кастомный renderer если он есть
if (renderer[token.type]) {
return renderer[token.type](token);
}
// Fallback для встроенных типов токенов
if (token.type === 'text') {
return token.text || '';
}
if (token.type === 'strong') {
return `<strong>${renderTokens(token.tokens || [], renderer)}</strong>`;
}
if (token.type === 'em') {
return `<em>${renderTokens(token.tokens || [], renderer)}</em>`;
}
if (token.type === 'codespan') {
return `<code>${token.text || ''}</code>`;
}
if (token.type === 'del') {
return `<del>${renderTokens(token.tokens || [], renderer)}</del>`;
}
if (token.type === 'link') {
// Для ссылок используем кастомный renderer если доступен
if (renderer.link) {
return renderer.link(token);
}
// Fallback для встроенных ссылок
const href = token.href || '';
const title = token.title ? ` title="${token.title}"` : '';
const text = token.tokens && token.tokens.length > 0
? renderTokens(token.tokens, renderer)
: (token.text || '');
return `<a href="${href}"${title}>${text}</a>`;
}
if (token.type === 'spoiler') {
// Для спойлеров используем кастомный renderer если доступен
if (renderer.spoiler) {
return renderer.spoiler(token);
}
return `<span class="spoiler" title="Нажмите, чтобы показать">${token.text || ''}</span>`;
}
return token.text || '';
}).join('');
}
// Кастомный renderer для внешних ссылок и чекбоксов
const renderer: any = {
link(token: any) {
const href = token.href;
const title = token.title;
const text = token.text;
// Правильно обрабатываем вложенные токены для форматирования внутри ссылок
let text = '';
if (token.tokens && token.tokens.length > 0) {
text = renderTokens(token.tokens, this);
} else if (token.text) {
text = token.text;
}
try {
const url = new URL(href, window.location.href);
@ -45,15 +99,24 @@ const renderer: any = {
},
// Кастомный renderer для элементов списка с чекбоксами
listitem(token: any) {
const text = token.text;
const task = token.task;
const checked = token.checked;
// Правильно обрабатываем вложенные токены для форматирования
let content = '';
if (token.tokens && token.tokens.length > 0) {
// Рендерим вложенные токены используя наш renderer
content = renderTokens(token.tokens, this);
} else if (token.text) {
// Если токенов нет, используем текст (для обратной совместимости)
content = token.text;
}
if (task) {
const checkbox = `<input type="checkbox" ${checked ? "checked" : ""} />`;
return `<li class="task-list-item">${checkbox} ${text}</li>\n`;
return `<li class="task-list-item">${checkbox} ${content}</li>\n`;
}
return `<li>${text}</li>\n`;
return `<li>${content}</li>\n`;
},
};