Математика должна быть цитируемой

Discourse Math был значительно обновлён в январе 2026 года до новой официальной версии, включённой в ядро, с MathJax 4.1 по умолчанию и KaTeX в качестве альтернативы. В документации к плагину также отмечается, что KaTeX включает расширение CopyTex для копирования исходного кода LaTeX.

Стоит ли добавить небольшой патч темы, улучшающий выделение цитат в постах с большим количеством математики?

Для сайтов, heavily использующих MathJax, таких как «Physics with Ethan», наиболее практичное решение выглядит так:
1. перехватить выделенный HTML до того, как Discourse преобразует его обратно в Markdown,
2. найти элементы-обёртки для математики,
3. заменить их исходным TeX-кодом, заключённым в $...$ или $$...$$,
4. затем позволить Discourse продолжить формирование цитаты.

Вот возможный скрипт компонента темы, с которого можно начать, если стоит задача модифицировать раздел <head> или область JS темы Horizon (или Default).


<script type="text/discourse-plugin" version="1.0">
  apiInitializer("1.34.0", (api) => {
    function texFromMathElement(el) {
      // MathJax v3/v4 обычно хранит исходный код в дочернем элементе annotation.
      const annotation =
        el.querySelector('annotation[encoding="application/x-tex"]') ||
        el.querySelector('annotation');

      if (annotation?.textContent?.trim()) {
        const tex = annotation.textContent.trim();

        // Эвристика: блочные обёртки математики часто являются контейнерами отображения.
        const isBlock =
          el.tagName === "MJX-CONTAINER" &&
          (el.getAttribute("display") === "true" ||
            el.getAttribute("display") === "block");

        return isBlock ? `$$\n${tex}\n$$` : `$${tex}$`;
      }

      return null;
    }

    function patchMathInFragment(fragment) {
      const candidates = fragment.querySelectorAll(
        "mjx-container, .math, .katex, .MathJax"
      );

      candidates.forEach((node) => {
        const replacement = texFromMathElement(node);
        if (!replacement) {
          return;
        }

        const textNode = document.createTextNode(replacement);
        node.replaceWith(textNode);
      });

      return fragment;
    }

    api.modifyClass("component:quote-button", {
      pluginId: "ethan-math-quote-fix",

      _selectionChanged() {
        this._super(...arguments);

        try {
          const selection = window.getSelection();
          if (!selection || selection.rangeCount === 0) {
            return;
          }

          const range = selection.getRangeAt(0);
          const fragment = range.cloneContents();
          patchMathInFragment(fragment);

          const container = document.createElement("div");
          container.appendChild(fragment);

          // Заменяем буфер, который Discourse позже преобразует в Markdown цитаты.
          if (this.quoteState) {
            this.quoteState.buffer = container.innerHTML;
          }
        } catch (e) {
          // Тихо игнорируем ошибки, чтобы обычное цитирование продолжало работать.
          console.warn("Math quote patch failed:", e);
        }
      },
    });
  });
</script>

Несколько важных оговорок:
• Это практический патч, а не решение, уже опубликованное Meta. Основная стратегия выведена из пути цитирования, проходящего через выделенный HTML и функцию toMarkdown.
• Наиболее вероятно, что он поможет при использовании провайдера MathJax, который сейчас является провайдером по умолчанию в Discourse Math и тем, который я обычно использую.
• Скрипту могут потребоваться небольшие корректировки селекторов в зависимости от того, как отрендеренная математика оказывается в виде mjx-container, .MathJax или другой обёртки. Я бы протестировал это на тестовом сайте — это была бы новая стандартная установка.
• Вряд ли он будет идеален для каждого краевого случая, особенно при смешанных выделениях inline/block или вложенных цитируемых материалах.

Поскольку Discourse теперь официально поддерживает KaTeX с CopyTex, другой путь — сменить провайдера, если моя главная проблема — копирование исходного кода LaTeX, а не точность рендеринга. Это не решит автоматически проблему выделения при цитировании, но означает, что для отрендеренной математики уже есть более удобный для копирования путь.

Для моего сайта с большим количеством MathJax, «Physics with Ethan», я сейчас думаю так:
• оставить MathJax, если кто-то не предложит перейти на KaTeX?,
• возможно, добавить патч для выделения цитат в тему Horizon, используя код выше (на тестовом сайте).
• рассматривать это как локальное улучшение удобства использования до тех пор, пока не появится официальное решение на стороне upstream. Тот факт, что тема функции 2020 года всё ещё открыта в 2026 году, говорит о том, что upstream может оставаться медленным в этом вопросе.

3 лайка