Я продолжал постепенно разбираться в этом. Для того чтобы задать свой вопрос, требуется много предварительной настройки:
SVG
У меня есть веб-сервер, который генерирует SVG. В данном случае он создает очень простой тестовый SVG…
<svg xmlns="http://www.w3.org/2000/svg" stroke-linejoin="round" viewBox="0 0 100 100">
<path d="M50,4L4,50L50,96L96,50Z" stroke="#40638C" stroke-width="3"></path>
<path d="M50,5L5,50L50,95L95,50Z" stroke="#333" fill="#40638C" stroke-width="3"></path>
<path d="M37,42c-1,0,11-20,13-20c1,0,15,20,13,20h-9c0,8,9,22,12,25l-4,4l-8,-7v13h-10v-35z" stroke="#40495E" fill="#40495E"></path>
<path d="M35,40c-1,0,11-20,13-20c1,0,15,20,13,20h-9c0,8,9,22,12,25l-4,4l-8,-7v13h-10v-35z" stroke="#333" fill="#555"></path>
</svg>
Это просто стилизованный знак «слияния». Обратите внимание, что он содержит четыре элемента PATH.
Инлайнинг
Чтобы вставить SVG в пост, я использую JavaScript, добавленный через мою тему.
Конечная цель — создать полноценный плагин. Но сейчас я просто пытаюсь создать proof-of-concept. Поэтому код просто вставлен в секцию <head> кастомизации моей темы:
<script type="text/discourse-plugin" version="0.8">
var UMB = {
svgload: function(base, target) {
var url = base + $(target).text();
$(target).html('');
$.ajax({
method: "GET",
url: url,
async: false,
dataType: "text",
success: function(data) { $(target).append(data); }
});
alert('loaded!');
$(target).children('path').each(function(){alert('here is a path element');});
},
}
$.fn.umbdv = function() {
this.each(
function() {
UMB.svgload('__URL_REDACTED__', this);
}
);
return this;
};
api.decorateCooked(
$elem => $elem.children('.cooked div[data-custom="umbdv"]').umbdv(),
{ id: 'umbdv' }
);
</script>
Где…
var UMB = { — это просто глобальная переменная, которая избавляет меня от необходимости писать огромные анонимные функции повсюду.
$.fn.umbdv = — это [как я понимаю] «плагин», расширяющий JQuery.
api.decorateCooked( позволяет мне манипулировать постом до того, как он будет отправлен в браузер.
Вызов
Затем в теме я пишу…
<div data-custom="umbdv">/vtest</div>
Для этого DIV вызывается UMB.svgload('__URL_REDACTED__', this).
UMB.svgload() корректно распознает строку /vtest, формирует URL и выполняет AJAX-запрос. Он успешно выполняет append(data), и бип — мой SVG становится инлайн-элементом…
Затем срабатывает мой alert() внутри UMB.svgload(), как и ожидалось. (Это, очевидно, отладочный хак, верно? :))
Вопрос (наконец)
У меня есть тема ТОЛЬКО ДЛЯ СОТРУДНИКОВ на моем хостинге Discourse, где можно увидеть это в действии. (Я обращаюсь к сотрудникам Discourse/поддержке, которые могут войти в мою установку как администраторы.)
https://forum.moversmindset.com/t/svg-experimentation-in-progress/1109
Почему…
$(target).children('path').each(function(){alert('here is a path element');});
…не выбирает ни один из элементов PATH?
Ничего не происходит — никаких ошибок. Ничего.
Далее
Куда я пойду, если этот тривиальный proof-of-concept с alert() заработает…
Я знаю, что фрагмент DOM, с которым я «работаю», еще не подключен к фактическому документу DOM (в момент вызова UMB.svgload()). Поэтому я ожидаю, что $(target)… будет тем, что мне нужно.
В конечном итоге я буду встраивать намного более сложные SVG, и мне понадобятся более сложные селекторы JQuery. Я хочу находить множество элементов внутри $(target) и прикреплять обработчики событий (например, onclick), которые будут вызывать другие глобальные функции UMB.….