// retoor import { Http } from "./Http.js"; import { contentRenderer } from "./ContentRenderer.js"; export class CommentManager { constructor() { this.initCommentReply(); this.initCommentEdit(); this.initCommentDelete(); } initCommentDelete() { document.addEventListener("submit", (e) => { const form = e.target.closest(".comment-delete-form"); if (!form) return; e.preventDefault(); this.submitDelete(form); }); } async submitDelete(form) { const wrapper = form.closest(".comment"); if (!wrapper) return; const button = form.querySelector("button[type='submit']"); if (button) button.disabled = true; const anchor = wrapper.previousElementSibling && wrapper.previousElementSibling.classList.contains("comment") ? wrapper.previousElementSibling : wrapper.parentElement.closest(".comment, .comments-section, .post-card"); const anchorTop = anchor ? anchor.getBoundingClientRect().top + window.scrollY : wrapper.getBoundingClientRect().top + window.scrollY; try { await Http.send(form.action); wrapper.remove(); window.scrollTo({ top: Math.max(anchorTop, 0) }); } catch (err) { if (button) button.disabled = false; } } initCommentReply() { document.addEventListener("click", (e) => { const btn = e.target.closest("[data-action='reply']"); if (!btn) return; e.preventDefault(); this.toggleReplyForm(btn); }); } initCommentEdit() { document.addEventListener("click", (e) => { const btn = e.target.closest("[data-action='edit']"); if (!btn) return; e.preventDefault(); this.toggleEditForm(btn); }); } toggleEditForm(btn) { const body = btn.closest(".comment-body"); if (!body) return; const text = body.querySelector(":scope > .comment-text"); if (!text) return; const existing = body.querySelector(":scope > .comment-edit-form"); if (existing) { existing.remove(); text.style.display = ""; return; } const form = document.createElement("form"); form.className = "comment-form comment-edit-form"; form.method = "POST"; form.action = btn.dataset.editUrl; const textarea = document.createElement("textarea"); textarea.name = "content"; textarea.className = "emoji-picker-target"; textarea.value = text.dataset.raw || text.textContent; textarea.rows = 3; form.appendChild(textarea); const actions = document.createElement("div"); actions.className = "comment-form-actions"; const save = document.createElement("button"); save.type = "submit"; save.className = "btn btn-primary btn-sm comment-form-submit"; save.innerHTML = '💾 Save'; const cancel = document.createElement("button"); cancel.type = "button"; cancel.className = "comment-action-btn comment-form-cancel"; cancel.innerHTML = ' Cancel'; cancel.addEventListener("click", () => { form.remove(); text.style.display = ""; }); actions.appendChild(save); actions.appendChild(cancel); form.appendChild(actions); form.addEventListener("submit", (e) => { e.preventDefault(); this.submitEdit(form, text); }); text.style.display = "none"; text.insertAdjacentElement("afterend", form); const enhancer = window.app && window.app.content; if (enhancer) enhancer.initEmojiPickers(); textarea.focus(); } async submitEdit(form, text) { const save = form.querySelector("button[type='submit']"); if (save) save.disabled = true; const content = form.querySelector("textarea").value; try { const result = await Http.send(form.action, { content }); text.dataset.raw = result.content; text.textContent = result.content; contentRenderer.applyTo(text); text.querySelectorAll("img:not(.avatar-img)").forEach((img) => { img.dataset.lightbox = ""; }); form.remove(); text.style.display = ""; } catch (err) { if (save) save.disabled = false; } } toggleReplyForm(btn) { const comment = btn.closest(".comment"); if (!comment) return; const body = comment.querySelector(".comment-body"); if (!body) return; const existing = body.querySelector(":scope > .comment-reply-form"); if (existing) { existing.remove(); return; } const template = document.getElementById("comment-reply-template"); if (!template) { Http.toLogin(); return; } const container = comment.closest(".post-card, .gist-card, .comments-section"); const source = container && container.querySelector(".comment-form:not(.comment-reply-form)"); if (!source) return; const targetUid = source.querySelector('input[name="target_uid"]').value; const targetType = source.querySelector('input[name="target_type"]').value; const fragment = template.content.cloneNode(true); const form = fragment.querySelector(".comment-form"); if (!form) return; form.classList.add("comment-reply-form"); form.querySelector('input[name="target_uid"]').value = targetUid; form.querySelector('input[name="target_type"]').value = targetType; const parentInput = document.createElement("input"); parentInput.type = "hidden"; parentInput.name = "parent_uid"; parentInput.value = body.dataset.commentUid || ""; form.appendChild(parentInput); const cancel = document.createElement("button"); cancel.type = "button"; cancel.className = "comment-action-btn comment-reply-cancel comment-form-cancel"; cancel.innerHTML = ' Cancel'; cancel.addEventListener("click", () => form.remove()); form.querySelector(".comment-form-actions").appendChild(cancel); const actions = body.querySelector(":scope > .comment-actions"); actions.insertAdjacentElement("afterend", form); this.enhanceForm(form); setTimeout(() => { const textarea = form.querySelector("textarea"); if (textarea) textarea.focus(); }, 20); } enhanceForm(form) { const enhancer = window.app && window.app.content; if (enhancer) { enhancer.initEmojiPickers(); enhancer.initMentionInputs(); } const textarea = form.querySelector("textarea"); if (textarea) { textarea.addEventListener("input", () => { textarea.style.height = "auto"; textarea.style.height = `${Math.min(textarea.scrollHeight, 120)}px`; }); } form.addEventListener("submit", () => { const btn = form.querySelector("button[type='submit']"); if (btn) btn.disabled = true; }); } }