mirror of
https://github.com/notion-enhancer/notion-enhancer.git
synced 2025-04-05 05:09:03 +00:00
* Basic Functionality * Added smooth scrolling option * Added scroll down distance option * Button hide/show animation * Add percentage distance option * Calculate percentage every update (as opposed to every page change) * Calculate percentage height based on scroller and content height * Licensing and Conventions * Hide button on initialization if top distance is set * Fixed bug with button visibility when opening pages
124 lines
4.7 KiB
JavaScript
124 lines
4.7 KiB
JavaScript
/*
|
|
* scroll-to-top
|
|
* (c) 2020 dragonwocky <thedragonring.bod@gmail.com> (https://dragonwocky.me/)
|
|
* (c) 2020 CloudHill
|
|
* under the MIT license
|
|
*/
|
|
|
|
"use strict";
|
|
|
|
const { createElement } = require("../../pkg/helpers.js");
|
|
|
|
module.exports = {
|
|
id: "0a958f5a-17c5-48b5-8713-16190cae1959",
|
|
tags: ["extension"],
|
|
name: "scroll-to-top",
|
|
desc: "add a scroll to top button.",
|
|
version: "1.0.0",
|
|
author: "CloudHill",
|
|
options: [
|
|
{
|
|
key: "smooth",
|
|
label: "smooth scrolling",
|
|
type: "toggle",
|
|
value: true,
|
|
},
|
|
{
|
|
key: "top",
|
|
label: "scroll down distance to show button",
|
|
type: "input",
|
|
value: 80,
|
|
},
|
|
{
|
|
key: "percent",
|
|
label: "set distance as a percentage",
|
|
type: "toggle",
|
|
value: true,
|
|
},
|
|
],
|
|
hacks: {
|
|
"renderer/preload.js"(store, __exports) {
|
|
document.addEventListener("readystatechange", (event) => {
|
|
if (document.readyState !== "complete") return false;
|
|
const attempt_interval = setInterval(enhance, 500);
|
|
function enhance() {
|
|
if (!document.querySelector(".notion-frame")) return;
|
|
clearInterval(attempt_interval);
|
|
|
|
const $container = document.createElement('div');
|
|
const $help = document.querySelector('.notion-help-button');
|
|
const $scroll = createElement(
|
|
'<div class="notion-scroll-button" role="button">🠙</div>' // 🠙;
|
|
)
|
|
|
|
$container.className = "bottom-right-buttons";
|
|
$help.after($container);
|
|
$container.append($scroll);
|
|
$container.append($help);
|
|
|
|
if (store().top > 0)
|
|
$scroll.classList.add('hidden');
|
|
|
|
$scroll.addEventListener('click', () => {
|
|
document
|
|
.querySelector('.notion-frame > .notion-scroller')
|
|
.scroll({
|
|
top: 0,
|
|
left: 0,
|
|
behavior: store().smooth ? 'smooth' : 'auto',
|
|
});
|
|
})
|
|
|
|
let queue = [];
|
|
let $scroller = document.querySelector('.notion-frame > .notion-scroller');
|
|
let top = store().top || 0;
|
|
|
|
const observer = new MutationObserver((list, observer) => {
|
|
if (!queue.length) requestAnimationFrame(() => process(queue));
|
|
queue.push(...list);
|
|
});
|
|
observer.observe(document.body, {
|
|
childList: true,
|
|
subtree: true,
|
|
});
|
|
|
|
function process(list) {
|
|
queue = [];
|
|
setScrollDistance();
|
|
|
|
for (let { addedNodes } of list) {
|
|
if (
|
|
addedNodes[0] && (
|
|
addedNodes[0].className === 'notion-page-content' ||
|
|
addedNodes[0].className === 'notion-scroller'
|
|
) && (top > 0)
|
|
) {
|
|
$scroll.classList.add('hidden');
|
|
|
|
$scroller = document.querySelector('.notion-frame > .notion-scroller');
|
|
setScrollDistance();
|
|
|
|
$scroller.addEventListener('scroll', (event) => {
|
|
if (Math.ceil(event.target.scrollTop) < $scroller.top_distance)
|
|
$scroll.classList.add('hidden');
|
|
else
|
|
$scroll.classList.remove('hidden');
|
|
});
|
|
}
|
|
}
|
|
}
|
|
|
|
function setScrollDistance() {
|
|
$scroller.top_distance = top;
|
|
if (top > 0 && store().percent) {
|
|
let content_height = Array.from($scroller.children)
|
|
.reduce((h, c) => h + c.offsetHeight, 0);
|
|
$scroller.top_distance *= (content_height - $scroller.offsetHeight) / 100;
|
|
}
|
|
}
|
|
}
|
|
});
|
|
}
|
|
},
|
|
};
|