Fix preview avatar: use persistent DOM element instead of innerHTML manipulation.
Move the preview author header (avatar + name + timestamp) inside the preview div as a persistent child element that JS shows/hides, rather than serializing it via innerHTML which was failing to render the image.
This commit is contained in:
parent
a42ed0dc7a
commit
ac5970044e
2 changed files with 58 additions and 51 deletions
|
|
@ -2,6 +2,23 @@
|
|||
// previewTimer must live outside the functions.
|
||||
var previewTimer = null;
|
||||
|
||||
function updatePreviewAuthor(previewDiv) {
|
||||
// Show the persistent .preview-author header when preview has content.
|
||||
// For anonymous users, sync the displayed name from the input field.
|
||||
var author = previewDiv.querySelector('.preview-author');
|
||||
if (!author) return;
|
||||
author.style.display = '';
|
||||
var form = previewDiv.closest('form');
|
||||
if (form) {
|
||||
var nameInput = form.querySelector('[name="anonymous_name"]');
|
||||
if (nameInput) {
|
||||
var name = nameInput.value.trim() || 'Anonymous';
|
||||
var strong = author.querySelector('.preview-anon-name');
|
||||
if (strong) strong.textContent = name;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function previewAjax(textarea, div, show_raw, mathjax) {
|
||||
// set div to raw textarea while waiting for remote Markdown rendering.
|
||||
if (show_raw) {
|
||||
|
|
@ -9,12 +26,14 @@ function previewAjax(textarea, div, show_raw, mathjax) {
|
|||
var el = document.getElementById(textarea);
|
||||
var busted_textarea = el.value.replace(/&/g, '&').replace(/</g, '<');
|
||||
var rawHtml = '<span class="preview-raw-markdown">' + busted_textarea + '</span>';
|
||||
// Wrap raw preview as a live node for reply forms.
|
||||
var form = el.closest('form');
|
||||
if (form && isReplyForm(form)) {
|
||||
rawHtml = wrapPreviewAsNode(rawHtml, form);
|
||||
var previewDiv = document.getElementById(div);
|
||||
var contentDiv = previewDiv.querySelector('.preview-content');
|
||||
if (contentDiv) {
|
||||
contentDiv.innerHTML = rawHtml;
|
||||
updatePreviewAuthor(previewDiv);
|
||||
} else {
|
||||
previewDiv.innerHTML = rawHtml;
|
||||
}
|
||||
document.getElementById(div).innerHTML = rawHtml;
|
||||
}
|
||||
if (previewTimer) {
|
||||
clearTimeout(previewTimer);
|
||||
|
|
@ -38,13 +57,14 @@ function sendPreview(textarea, div, mathjax) {
|
|||
})
|
||||
.then(function(response) { return response.text(); })
|
||||
.then(function(html) {
|
||||
// Wrap rendered preview as a live node for reply forms.
|
||||
var textareaEl = document.getElementById(textarea);
|
||||
var form = textareaEl ? textareaEl.closest('form') : null;
|
||||
if (form && isReplyForm(form)) {
|
||||
html = wrapPreviewAsNode(html, form);
|
||||
var previewDiv = document.getElementById(div);
|
||||
var contentDiv = previewDiv.querySelector('.preview-content');
|
||||
if (contentDiv) {
|
||||
contentDiv.innerHTML = html;
|
||||
updatePreviewAuthor(previewDiv);
|
||||
} else {
|
||||
previewDiv.innerHTML = html;
|
||||
}
|
||||
document.getElementById(div).innerHTML = html;
|
||||
if (mathjax && typeof MathJax !== 'undefined') {
|
||||
setTimeout(function() {
|
||||
MathJax.Hub.Queue(["Typeset", MathJax.Hub, div]);
|
||||
|
|
@ -53,29 +73,6 @@ function sendPreview(textarea, div, mathjax) {
|
|||
});
|
||||
}
|
||||
|
||||
function isReplyForm(form) {
|
||||
var action = form.getAttribute('action') || '';
|
||||
return action.indexOf('/reply') !== -1;
|
||||
}
|
||||
|
||||
function wrapPreviewAsNode(html, form) {
|
||||
// Clone the hidden preview header (avatar + author + "just now")
|
||||
// and wrap content in node-data div so it looks like a live comment.
|
||||
var header = form.querySelector('.preview-header');
|
||||
if (!header || !header.innerHTML.trim()) return html;
|
||||
|
||||
var headerHtml = header.innerHTML;
|
||||
|
||||
// For anonymous users, update the displayed name from the input field.
|
||||
var nameInput = form.querySelector('[name="anonymous_name"]');
|
||||
if (nameInput) {
|
||||
var name = nameInput.value.trim() || 'Anonymous';
|
||||
headerHtml = headerHtml.replace('>Anonymous<', '>' + escapeHtml(name) + '<');
|
||||
}
|
||||
|
||||
return headerHtml + '<div class="node-data">' + html + '</div>';
|
||||
}
|
||||
|
||||
// CSS-based toggle for smoother animations.
|
||||
function toggle(target, button, off_text, on_text) {
|
||||
if (typeof on_text === 'undefined') on_text = 'hide';
|
||||
|
|
@ -291,7 +288,16 @@ function initAjaxCommentForms() {
|
|||
if (textarea) textarea.value = '';
|
||||
// Clear the preview.
|
||||
var preview = form.querySelector('.preview');
|
||||
if (preview) preview.innerHTML = '';
|
||||
if (preview) {
|
||||
var contentDiv = preview.querySelector('.preview-content');
|
||||
if (contentDiv) {
|
||||
contentDiv.innerHTML = '';
|
||||
}
|
||||
var authorDiv = preview.querySelector('.preview-author');
|
||||
if (authorDiv) {
|
||||
authorDiv.style.display = 'none';
|
||||
}
|
||||
}
|
||||
submitBtn.disabled = false;
|
||||
submitBtn.value = originalLabel;
|
||||
})
|
||||
|
|
|
|||
|
|
@ -26,24 +26,25 @@
|
|||
{% set submit_button_value = request.namespace.submit_button_text or 'save message' %}
|
||||
{% include 'submit.j2' %}
|
||||
|
||||
<div class="preview-header js-only" style="display:none">
|
||||
{% if request.user and request.user.authenticated %}
|
||||
<img src="{{ request.user.avatar_uri(size=request.avatar_size) }}" class="avatar nested-avatar" align="left" />
|
||||
<span class="author-and-date">
|
||||
<strong>{{ request.user.name }}</strong>
|
||||
<span class="date">just now</span>
|
||||
</span>
|
||||
{% elif request.namespace.allow_anonymous %}
|
||||
<span class="author-and-date">
|
||||
<strong class="preview-anon-name">Anonymous</strong>
|
||||
<span class="date">just now</span>
|
||||
</span>
|
||||
{% endif %}
|
||||
</div>
|
||||
|
||||
<details class="preview-details js-only" open>
|
||||
<summary class="action link preview-toggle"><span class="when-open">hide preview ▲</span><span class="when-closed">show preview ▼</span></summary>
|
||||
<div id='preview-{{ node.id }}' name='preview' class='preview js-only'></div>
|
||||
<div id='preview-{{ node.id }}' name='preview' class='preview js-only'>
|
||||
<div class="preview-author" style="display:none">
|
||||
{% if request.user and request.user.authenticated %}
|
||||
<img src="{{ request.user.avatar_uri(size=request.avatar_size) }}" class="avatar nested-avatar" align="left" />
|
||||
<span class="author-and-date">
|
||||
<strong>{{ request.user.name }}</strong>
|
||||
<span class="date">just now</span>
|
||||
</span>
|
||||
{% elif request.namespace.allow_anonymous %}
|
||||
<span class="author-and-date">
|
||||
<strong class="preview-anon-name">Anonymous</strong>
|
||||
<span class="date">just now</span>
|
||||
</span>
|
||||
{% endif %}
|
||||
</div>
|
||||
<div class="preview-content node-data"></div>
|
||||
</div>
|
||||
</details>
|
||||
|
||||
{% include 'csrf.j2' %}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue