feat(console): scrollAutoscrollTargets walks ancestors; expose on window
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
parent
35dfb6dd1f
commit
02e44a04d3
1 changed files with 23 additions and 8 deletions
|
|
@ -156,24 +156,39 @@ function bindAllConsoleForms(root) {
|
||||||
scope.forEach(bindConsoleForm);
|
scope.forEach(bindConsoleForm);
|
||||||
}
|
}
|
||||||
|
|
||||||
function scrollConsolesToBottom(root) {
|
function scrollAutoscrollTargets(root) {
|
||||||
if (!root) return;
|
if (!root) return;
|
||||||
const scope = root.matches && root.matches("[data-autoscroll]") ? [root] : [];
|
const targets = [];
|
||||||
if (root.querySelectorAll) {
|
// Case 1: root itself opts in.
|
||||||
root.querySelectorAll("[data-autoscroll]").forEach((el) => scope.push(el));
|
if (root.matches && root.matches("[data-autoscroll]")) {
|
||||||
|
targets.push(root);
|
||||||
}
|
}
|
||||||
scope.forEach((el) => {
|
// Case 2: descendants opt in.
|
||||||
|
if (root.querySelectorAll) {
|
||||||
|
root.querySelectorAll("[data-autoscroll]").forEach((el) => targets.push(el));
|
||||||
|
}
|
||||||
|
// Case 3: neither — walk up. Handles htmx:load firing with the inserted
|
||||||
|
// child as the root after hx-swap="beforeend" on a console line.
|
||||||
|
if (targets.length === 0 && root.closest) {
|
||||||
|
const up = root.closest("[data-autoscroll]");
|
||||||
|
if (up) targets.push(up);
|
||||||
|
}
|
||||||
|
targets.forEach((el) => {
|
||||||
el.scrollTop = el.scrollHeight;
|
el.scrollTop = el.scrollHeight;
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Expose for tabs.js (and any future cross-module consumer). The script
|
||||||
|
// is `defer`red in base.html, so it runs before DOMContentLoaded and the
|
||||||
|
// global is defined by the time tabs.js's DCL-deferred initStrips runs.
|
||||||
|
window.scrollAutoscrollTargets = scrollAutoscrollTargets;
|
||||||
|
|
||||||
document.addEventListener("DOMContentLoaded", () => {
|
document.addEventListener("DOMContentLoaded", () => {
|
||||||
scrollConsolesToBottom(document);
|
scrollAutoscrollTargets(document);
|
||||||
bindAllConsoleForms(document);
|
bindAllConsoleForms(document);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Support HTMX-injected content (mirrors sse.js pattern).
|
|
||||||
document.addEventListener("htmx:load", (event) => {
|
document.addEventListener("htmx:load", (event) => {
|
||||||
scrollConsolesToBottom(event.detail.elt);
|
scrollAutoscrollTargets(event.detail.elt);
|
||||||
bindAllConsoleForms(event.detail.elt);
|
bindAllConsoleForms(event.detail.elt);
|
||||||
});
|
});
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue