diff --git a/internal/ui/static/js/app.js b/internal/ui/static/js/app.js index f8c4836a..bf1dbcca 100644 --- a/internal/ui/static/js/app.js +++ b/internal/ui/static/js/app.js @@ -1,3 +1,44 @@ + +/** + * Open a new tab with the given URL. + * + * @param {string} url + */ +function openNewTab(url) { + const win = window.open(""); + win.opener = null; + win.location = url; + win.focus(); +} + +/** + * Filter visible elements based on the selector. + * + * @param {string} selector + * @returns {Array} + */ +function getVisibleElements(selector) { + const elements = document.querySelectorAll(selector); + return [...elements].filter((element) => element.offsetParent !== null); +} + +/** + * Scroll the page to the given element. + * + * @param {Element} element + * @param {boolean} evenIfOnScreen + */ +function scrollPageTo(element, evenIfOnScreen) { + const windowScrollPosition = window.scrollY; + const windowHeight = document.documentElement.clientHeight; + const viewportPosition = windowScrollPosition + windowHeight; + const itemBottomPosition = element.offsetTop + element.offsetHeight; + + if (evenIfOnScreen || viewportPosition - itemBottomPosition < 0 || viewportPosition - element.offsetTop > windowHeight) { + window.scrollTo(0, element.offsetTop - 10); + } +} + // OnClick attaches a listener to the elements that match the selector. function onClick(selector, callback, noPreventDefault) { document.querySelectorAll(selector).forEach((element) => { @@ -113,7 +154,7 @@ function showKeyboardShortcuts() { // Mark as read visible items of the current page. function markPageAsRead() { - const items = DomHelper.getVisibleElements(".items .item"); + const items = getVisibleElements(".items .item"); const entryIDs = []; items.forEach((element) => { @@ -369,14 +410,14 @@ function openOriginalLink(openLinkInCurrentTab) { if (openLinkInCurrentTab) { window.location.href = entryLink.getAttribute("href"); } else { - DomHelper.openNewTab(entryLink.getAttribute("href")); + openNewTab(entryLink.getAttribute("href")); } return; } const currentItemOriginalLink = document.querySelector(".current-item :is(a, button)[data-original-link]"); if (currentItemOriginalLink !== null) { - DomHelper.openNewTab(currentItemOriginalLink.getAttribute("href")); + openNewTab(currentItemOriginalLink.getAttribute("href")); const currentItem = document.querySelector(".current-item"); // If we are not on the list of starred items, move to the next item @@ -394,13 +435,13 @@ function openCommentLink(openLinkInCurrentTab) { if (openLinkInCurrentTab) { window.location.href = entryLink.getAttribute("href"); } else { - DomHelper.openNewTab(entryLink.getAttribute("href")); + openNewTab(entryLink.getAttribute("href")); } } } else { const currentItemCommentsLink = document.querySelector(".current-item :is(a, button)[data-comments-link]"); if (currentItemCommentsLink !== null) { - DomHelper.openNewTab(currentItemCommentsLink.getAttribute("href")); + openNewTab(currentItemCommentsLink.getAttribute("href")); } } } @@ -503,7 +544,7 @@ const BOTTOM = -9999; * @param {number} offset How many items to jump for focus. */ function goToListItem(offset) { - const items = DomHelper.getVisibleElements(".items .item"); + const items = getVisibleElements(".items .item"); if (items.length === 0) { return; } @@ -529,7 +570,7 @@ function goToListItem(offset) { const item = items[itemOffset]; item.classList.add("current-item"); - DomHelper.scrollPageTo(item); + scrollPageTo(item); item.focus(); break; @@ -540,7 +581,7 @@ function goToListItem(offset) { function scrollToCurrentItem() { const currentItem = document.querySelector(".current-item"); if (currentItem !== null) { - DomHelper.scrollPageTo(currentItem, true); + scrollPageTo(currentItem, true); } } diff --git a/internal/ui/static/js/dom_helper.js b/internal/ui/static/js/dom_helper.js deleted file mode 100644 index 7d2e82fe..00000000 --- a/internal/ui/static/js/dom_helper.js +++ /dev/null @@ -1,28 +0,0 @@ -class DomHelper { - static isVisible(element) { - return element.offsetParent !== null; - } - - static openNewTab(url) { - const win = window.open(""); - win.opener = null; - win.location = url; - win.focus(); - } - - static scrollPageTo(element, evenIfOnScreen) { - const windowScrollPosition = window.scrollY; - const windowHeight = document.documentElement.clientHeight; - const viewportPosition = windowScrollPosition + windowHeight; - const itemBottomPosition = element.offsetTop + element.offsetHeight; - - if (evenIfOnScreen || viewportPosition - itemBottomPosition < 0 || viewportPosition - element.offsetTop > windowHeight) { - window.scrollTo(0, element.offsetTop - 10); - } - } - - static getVisibleElements(selector) { - const elements = document.querySelectorAll(selector); - return [...elements].filter((element) => this.isVisible(element)); - } -} diff --git a/internal/ui/static/static.go b/internal/ui/static/static.go index 9024cee5..66f9b5ba 100644 --- a/internal/ui/static/static.go +++ b/internal/ui/static/static.go @@ -114,7 +114,6 @@ func GenerateJavascriptBundles() error { var bundles = map[string][]string{ "app": { "js/tt.js", // has to be first - "js/dom_helper.js", "js/touch_handler.js", "js/keyboard_handler.js", "js/request_builder.js",