extension: word counter (moved to panel)

This commit is contained in:
dragonwocky 2021-10-18 17:28:28 +11:00
parent d5c45a8771
commit 1f9537b755
8 changed files with 559 additions and 159 deletions

View File

@ -23,5 +23,6 @@
"collapse-properties",
"scroll-to-top",
"indentation-lines",
"focus-mode"
"focus-mode",
"word-counter"
]

View File

@ -4,6 +4,97 @@
* (https://notion-enhancer.github.io/) under the MIT license
*/
/** layout **/
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
> div
> div:nth-child(3)[style*='width: 900px'],
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
+ div
> :nth-child(1)[style*='width: 900px'],
.notion-frame
> .notion-scroller.vertical.horizontal
> :nth-child(2)
> :nth-child(2)[style*='display: flex; width: 100%; justify-content: center;']
> :nth-child(1)[style*='width: 900px'] {
width: var(--theme--page-width) !important;
}
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
> div
> div:nth-child(3):not([style*='width: 900px']),
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
+ div
> :nth-child(1):not([style*='width: 900px']),
.notion-frame
> .notion-scroller.vertical.horizontal
> :nth-child(2)
> :nth-child(2)[style*='display: flex; width: 100%; justify-content: center;']
> :nth-child(1):not([style*='width: 900px']) {
width: var(--theme--page-width_full) !important;
}
.notion-page-content [style*='width: 100%; max-width:'][style*='align-self: center;'] {
max-width: 100% !important;
}
.notion-frame [style*='padding-right: calc(96px + env(safe-area-inset-right));'] {
padding-right: var(--theme--page-padding) !important;
}
.notion-frame [style*='padding-left: calc(96px + env(safe-area-inset-left));'] {
padding-left: var(--theme--page-padding) !important;
}
[style^='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 30vh;'],
[style^='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 30vh;']
img {
height: var(--theme--page_banner-height) !important;
background: transparent !important;
}
.notion-peek-renderer > :nth-child(2) {
max-width: var(--theme--page_preview-width) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='padding-left: calc(126px + env(safe-area-inset-left));'] {
padding-left: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='padding-right: calc(126px + env(safe-area-inset-right));'] {
padding-right: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='margin-left: calc(126px + env(safe-area-inset-left));'] {
margin-left: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='margin-right: calc(126px + env(safe-area-inset-right));'] {
margin-right: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer .notion-page-content {
padding-left: var(--theme--page_preview-padding) !important;
padding-right: var(--theme--page_preview-padding) !important;
width: 100%;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 20vh;'],
.notion-peek-renderer
.notion-scroller.vertical
[style*='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 20vh;']
img {
height: var(--theme--page_preview_banner-height) !important;
background: transparent !important;
}
/* typography */
[style*='Segoe UI'] {
@ -25,6 +116,19 @@
border-radius: 0px !important;
}
/** scrollbars **/
::-webkit-scrollbar-track,
::-webkit-scrollbar-corner {
background: var(--theme--scrollbar_track) !important;
}
::-webkit-scrollbar-thumb {
background: var(--theme--scrollbar_thumb) !important;
}
::-webkit-scrollbar-thumb:hover {
background: var(--theme--scrollbar_thumb-hover) !important;
}
/** consistent corner button styling **/
.notion-overlay-container
@ -54,3 +158,59 @@
box-shadow: var(--theme--ui_shadow, rgba(15, 15, 15, 0.15)) 0px 0px 0px 1px,
var(--theme--ui_shadow, rgba(15, 15, 15, 0.15)) 0px 2px 4px !important;
}
/* backgrounds */
.notion-discussion-input > div > div[style*='background'],
.notion-body.dark
.notion-default-overlay-container
[style*='grid-template-columns: [boolean-start] 60px [boolean-end property-start] 120px [property-end opererator-start] 110px [operator-end value-start] auto [value-end menu-start] 32px [menu-end];']
[style*='grid-column: property-start / value-end; background: rgba(255, 255, 255, 0.02);'],
.notion-body:not(.dark)
.notion-default-overlay-container
[style*='grid-template-columns: [boolean-start] 60px [boolean-end property-start] 120px [property-end opererator-start] 110px [operator-end value-start] auto [value-end menu-start] 32px [menu-end];']
[style*='grid-column: property-start / value-end; background: rgba(0, 0, 0, 0.02);'],
.notion-board-view [style*='width: 20px; margin-left: -20px; margin-top: -8px;'],
.notion-page-block > div > div > div[style*='background-color: white;'],
.line-numbers.notion-code-block + div .notion-focusable:not(:hover),
.notion-overlay-container
[style*='position: relative; max-width: calc(100vw - 24px); box-shadow:']
> [style*='display: flex; align-items: center; padding: 8px 10px; width: 100%; background:'],
.notion-default-overlay-container
> div:nth-child(3)
> div
> div:nth-child(2)
> div:nth-child(2)
> div
> div
> div
> div
> div
> div:nth-child(2)[style*='position: absolute; display: inline-flex; min-width: 100%; height: 32px; z-index: 1; background:'],
.notion-default-overlay-container
> div:nth-child(2)
> div
> div:nth-child(2)
> div:nth-child(2)
> div
> div
> div
> div
> div
> div:nth-child(2)[style*='position: absolute; display: inline-flex; min-width: 100%; height: 32px; z-index: 1; background:'],
.notion-frame .notion-scroller[style*='background:'],
.notion-page-template-modal .notion-scroller[style*='background:'],
.notion-peek-renderer .notion-scroller[style*='background:'],
.notion-frame > div > div > div[style*='max-width: 100%'][style*='background-color'],
.notion-peek-renderer
> div
> .notion-scroller
> div
> div[style*='max-width: 100%'][style*='background-color'],
.notion-page-template-modal
> div
> .notion-scroller
> div
> div[style*='max-width: 100%'][style*='background-color'] {
background: transparent !important;
}

View File

@ -4,97 +4,6 @@
* (https://notion-enhancer.github.io/) under the MIT license
*/
/** layout **/
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
> div
> div:nth-child(3)[style*='width: 900px'],
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
+ div
> :nth-child(1)[style*='width: 900px'],
.notion-frame
> .notion-scroller.vertical.horizontal
> :nth-child(2)
> :nth-child(2)[style*='display: flex; width: 100%; justify-content: center;']
> :nth-child(1)[style*='width: 900px'] {
width: var(--theme--page-width) !important;
}
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
> div
> div:nth-child(3):not([style*='width: 900px']),
.notion-frame
> .notion-scroller.vertical.horizontal
> .pseudoSelection
+ div
> :nth-child(1):not([style*='width: 900px']),
.notion-frame
> .notion-scroller.vertical.horizontal
> :nth-child(2)
> :nth-child(2)[style*='display: flex; width: 100%; justify-content: center;']
> :nth-child(1):not([style*='width: 900px']) {
width: var(--theme--page-width_full) !important;
}
.notion-page-content [style*='width: 100%; max-width:'][style*='align-self: center;'] {
max-width: 100% !important;
}
.notion-frame [style*='padding-right: calc(96px + env(safe-area-inset-right));'] {
padding-right: var(--theme--page-padding) !important;
}
.notion-frame [style*='padding-left: calc(96px + env(safe-area-inset-left));'] {
padding-left: var(--theme--page-padding) !important;
}
[style^='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 30vh;'],
[style^='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 30vh;']
img {
height: var(--theme--page_banner-height) !important;
background: transparent !important;
}
.notion-peek-renderer > :nth-child(2) {
max-width: var(--theme--page_preview-width) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='padding-left: calc(126px + env(safe-area-inset-left));'] {
padding-left: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='padding-right: calc(126px + env(safe-area-inset-right));'] {
padding-right: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='margin-left: calc(126px + env(safe-area-inset-left));'] {
margin-left: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='margin-right: calc(126px + env(safe-area-inset-right));'] {
margin-right: var(--theme--page_preview-padding) !important;
}
.notion-peek-renderer .notion-page-content {
padding-left: var(--theme--page_preview-padding) !important;
padding-right: var(--theme--page_preview-padding) !important;
width: 100%;
}
.notion-peek-renderer
.notion-scroller.vertical
[style*='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 20vh;'],
.notion-peek-renderer
.notion-scroller.vertical
[style*='position: relative; width: 100%; display: flex; flex-direction: column; align-items: center; height: 20vh;']
img {
height: var(--theme--page_preview_banner-height) !important;
background: transparent !important;
}
/* backgrounds */
.OnboardingHighlight + div > [style*='background-color'] {
@ -256,60 +165,6 @@ body,
background: var(--theme--bg_card) !important;
}
.notion-discussion-input > div > div[style*='background'],
.notion-body.dark
.notion-default-overlay-container
[style*='grid-template-columns: [boolean-start] 60px [boolean-end property-start] 120px [property-end opererator-start] 110px [operator-end value-start] auto [value-end menu-start] 32px [menu-end];']
[style*='grid-column: property-start / value-end; background: rgba(255, 255, 255, 0.02);'],
.notion-body:not(.dark)
.notion-default-overlay-container
[style*='grid-template-columns: [boolean-start] 60px [boolean-end property-start] 120px [property-end opererator-start] 110px [operator-end value-start] auto [value-end menu-start] 32px [menu-end];']
[style*='grid-column: property-start / value-end; background: rgba(0, 0, 0, 0.02);'],
.notion-board-view [style*='width: 20px; margin-left: -20px; margin-top: -8px;'],
.notion-page-block > div > div > div[style*='background-color: white;'],
.line-numbers.notion-code-block + div .notion-focusable:not(:hover),
.notion-overlay-container
[style*='position: relative; max-width: calc(100vw - 24px); box-shadow:']
> [style*='display: flex; align-items: center; padding: 8px 10px; width: 100%; background:'],
.notion-default-overlay-container
> div:nth-child(3)
> div
> div:nth-child(2)
> div:nth-child(2)
> div
> div
> div
> div
> div
> div:nth-child(2)[style*='position: absolute; display: inline-flex; min-width: 100%; height: 32px; z-index: 1; background:'],
.notion-default-overlay-container
> div:nth-child(2)
> div
> div:nth-child(2)
> div:nth-child(2)
> div
> div
> div
> div
> div
> div:nth-child(2)[style*='position: absolute; display: inline-flex; min-width: 100%; height: 32px; z-index: 1; background:'],
.notion-frame .notion-scroller[style*='background:'],
.notion-page-template-modal .notion-scroller[style*='background:'],
.notion-peek-renderer .notion-scroller[style*='background:'],
.notion-frame > div > div > div[style*='max-width: 100%'][style*='background-color'],
.notion-peek-renderer
> div
> .notion-scroller
> div
> div[style*='max-width: 100%'][style*='background-color'],
.notion-page-template-modal
> div
> .notion-scroller
> div
> div[style*='max-width: 100%'][style*='background-color'] {
background: transparent !important;
}
.notion-timeline-view
> div
> div
@ -331,19 +186,6 @@ body,
) !important;
}
/** scrollbars **/
::-webkit-scrollbar-track,
::-webkit-scrollbar-corner {
background: var(--theme--scrollbar_track) !important;
}
::-webkit-scrollbar-thumb {
background: var(--theme--scrollbar_thumb) !important;
}
::-webkit-scrollbar-thumb:hover {
background: var(--theme--scrollbar_thumb-hover) !important;
}
/** ui **/
.notion-page-mention-token.notion-enable-hover:hover {

59
repo/word-counter/app.css Normal file
View File

@ -0,0 +1,59 @@
/*
* word counter
* (c) 2020 dragonwocky <thedragonring.bod@gmail.com> (https://dragonwocky.me/)
* under the MIT license
*/
#word-counter-details {
width: 100%;
margin-bottom: 2em;
}
#word-counter-details > div {
display: flex;
flex-wrap: wrap;
margin: -0.5em;
}
#word-counter-details > div > p {
margin: 0.5em;
cursor: pointer;
font-size: var(--theme--font_label-size);
color: var(--theme--text);
border-radius: 3px;
padding: 0.25rem 0.5rem;
background: var(--theme--interactive_hover);
border: 1px solid transparent;
}
#word-counter-details > div > p:hover {
background: transparent;
border: 1px solid var(--theme--interactive_hover);
}
#word-counter-details > div > span {
max-width: 10em;
padding: 0.4rem 0.5rem 0.25rem 0.5rem;
font-size: calc(var(--theme--font_label-size) * 0.8);
color: var(--theme--text_ui_info);
}
#word-counter-details > div > p > svg {
height: 1em;
width: 1em;
margin: 0 0 -2px 0.3em;
color: var(--theme--text_ui_info);
}
#word-counter-details-tooltip {
pointer-events: none;
position: absolute;
padding: 0.25em 0.5em;
border-radius: 3px;
box-shadow: var(--theme--box-shadow_strong);
border-right-width: 1px;
font-size: calc(var(--theme--font_label-size) * 0.8);
background: var(--theme--interactive_hover);
opacity: 0;
transition: opacity 120ms ease-in;
}
#word-counter-details-tooltip.active {
opacity: 1;
}

View File

@ -0,0 +1,39 @@
/*
* notion-enhancer: word counter
* (c) 2021 dragonwocky <thedragonring.bod@gmail.com> (https://dragonwocky.me/)
* (https://notion-enhancer.github.io/) under the MIT license
*/
#word-counter--notice {
color: var(--theme--text_secondary);
font-size: 14px;
}
.word-counter--stat {
display: block;
background: var(--theme--ui_interactive-hover);
color: var(--theme--text);
font-size: 14px;
line-height: 1.2;
border: 1px solid transparent;
border-radius: 3px;
padding: 6px 8px;
cursor: pointer;
user-select: none;
}
.word-counter--stat:focus,
.word-counter--stat:hover {
background: transparent;
border: 1px solid var(--theme--ui_interactive-hover);
}
.word-counter--stat:active {
background: var(--theme--ui_interactive-active);
}
.word-counter--stat svg {
display: inline-block;
height: 1em;
width: 1em;
margin: 0 0.4em -2px 0;
color: var(--theme--icon_secondary);
}

View File

@ -0,0 +1,111 @@
/*
* notion-enhancer: word counter
* (c) 2021 dragonwocky <thedragonring.bod@gmail.com> (https://dragonwocky.me/)
* (https://notion-enhancer.github.io/) under the MIT license
*/
const copyToClipboard = async (str) => {
try {
await navigator.clipboard.writeText(str);
} catch {
const el = document.createElement('textarea');
el.value = str;
el.setAttribute('readonly', '');
el.style.position = 'absolute';
el.style.left = '-9999px';
document.body.appendChild(el);
el.select();
document.execCommand('copy');
document.body.removeChild(el);
}
},
humanTime = (mins) => {
let readable = '';
if (1 <= mins) {
readable += `${Math.floor(mins)} min`;
if (2 <= mins) readable += 's';
}
const secs = Math.round((mins % 1) * 60);
if (1 <= secs) {
if (1 <= mins) readable += ' ';
readable += `${secs} sec`;
if (2 <= secs) readable += 's';
}
return readable;
};
export default async function ({ web, components }, db) {
const dbNoticeText = 'Open a normal page to see word count.',
pageNoticeText = 'Click a stat to copy it.',
$notice = web.html`<span id="word-counter--notice">${dbNoticeText}</span>`;
const $wordCount = web.html`<b>12</b>`,
$characterCount = web.html`<b>12</b>`,
$sentenceCount = web.html`<b>12</b>`,
$blockCount = web.html`<b>12</b>`,
$readingTime = web.html`<b>10 mins</b>`,
$readingTooltip = web.html`${await components.feather('info')}`,
$speakingTime = web.html`<b>18 secs</b>`,
$speakingTooltip = web.html`${await components.feather('info')}`,
$statContainer = web.render(
web.html`<div></div>`,
web.render(web.html`<p class="word-counter--stat"></p>`, $wordCount, ' words'),
web.render(web.html`<p class="word-counter--stat"></p>`, $characterCount, ' characters'),
web.render(web.html`<p class="word-counter--stat"></p>`, $sentenceCount, ' sentences'),
web.render(web.html`<p class="word-counter--stat"></p>`, $blockCount, ' blocks'),
web.render(
web.html`<p class="word-counter--stat"></p>`,
$readingTooltip,
$readingTime,
' reading time'
),
web.render(
web.html`<p class="word-counter--stat"></p>`,
$speakingTooltip,
$speakingTime,
' speaking time'
)
);
$statContainer.querySelectorAll('.word-counter--stat').forEach(($stat) => {
$stat.addEventListener('click', () => copyToClipboard($stat.innerText));
});
components.setTooltip($readingTooltip, '**~ 275 wpm**');
components.setTooltip($speakingTooltip, '**~ 180 wpm**');
await components.addPanelView({
icon: await components.feather('type'),
title: 'Word Counter',
$content: web.render(web.html`<div></div>`, $notice, $statContainer),
});
let $page;
const updateStats = () => {
if (!$page) return;
const words = $page.innerText.split(/[^\w]+/).length;
$wordCount.innerText = words;
$characterCount.innerText = $page.innerText.length;
$sentenceCount.innerText = $page.innerText.split('.').length;
$blockCount.innerText = $page.querySelectorAll('[data-block-id]').length;
$readingTime.innerText = humanTime(words / 275);
$speakingTime.innerText = humanTime(words / 180);
},
pageObserver = () => {
if (document.contains($page)) {
updateStats();
} else {
$page = document.getElementsByClassName('notion-page-content')[0];
if ($page) {
$notice.innerText = pageNoticeText;
$statContainer.style.display = '';
updateStats();
} else {
$notice.innerText = dbNoticeText;
$statContainer.style.display = 'none';
}
}
};
web.addDocumentObserver(pageObserver, [
'.notion-page-content',
'.notion-collection_view_page-block',
]);
pageObserver();
}

166
repo/word-counter/mod.js Normal file
View File

@ -0,0 +1,166 @@
/*
* word counter
* (c) 2020 dragonwocky <thedragonring.bod@gmail.com> (https://dragonwocky.me/)
* (c) 2020 admiraldus (https://github.com/admiraldus)
* under the MIT license
*/
'use strict';
const { createElement } = require('../../pkg/helpers.js');
module.exports = {
id: 'b99deb52-6955-43d2-a53b-a31540cd19a5',
tags: ['extension'],
name: 'word counter',
desc:
'add page details: word/character/sentence/block count & speaking/reading times.',
version: '0.2.0',
author: 'dragonwocky',
options: [
{
key: 'hide_page_details_text',
label: 'hide "page details" text',
type: 'toggle',
value: false,
},
],
hacks: {
'renderer/preload.js'(store, __exports) {
const copyToClipboard = (str) => {
const el = document.createElement('textarea');
el.value = str;
el.setAttribute('readonly', '');
el.style.position = 'absolute';
el.style.left = '-9999px';
document.body.appendChild(el);
el.select();
document.execCommand('copy');
document.body.removeChild(el);
},
humanTime = (mins) => {
let readable = '';
if (1 <= mins) {
readable += `${Math.floor(mins)} min`;
if (2 <= mins) readable += 's';
}
const secs = Math.round((mins % 1) * 60);
if (1 <= secs) {
if (1 <= mins) readable += ' ';
readable += `${secs} sec`;
if (2 <= secs) readable += 's';
}
return readable;
};
document.addEventListener('readystatechange', (event) => {
if (document.readyState !== 'complete') return false;
let queue = [],
$page = document.getElementsByClassName('notion-page-content')[0];
const DOCUMENT_OBSERVER = new MutationObserver((list, observer) => {
if (!queue.length) requestIdleCallback(() => handle(queue));
queue.push(...list);
}),
PAGE_OBSERVER = new MutationObserver(showPageWordDetails);
DOCUMENT_OBSERVER.observe(document.body, {
childList: true,
subtree: true,
});
function handle(list) {
queue = [];
for (let { addedNodes } of list) {
if (
addedNodes[0] &&
addedNodes[0].className === 'notion-page-content'
) {
$page = addedNodes[0];
showPageWordDetails();
PAGE_OBSERVER.disconnect();
PAGE_OBSERVER.observe($page, {
childList: true,
subtree: true,
characterData: true,
});
}
}
}
const $container = createElement(
`<div id="word-counter-details"><div></div></div>`
),
$tooltip = createElement(
`<span id="word-counter-details-tooltip"></span>`
);
function showPageWordDetails() {
const details = {
words: $page.innerText.replace(/\s+/g, ' ').split(' ').length,
characters: $page.innerText.length,
sentences: $page.innerText.split('.').length,
blocks: $page.querySelectorAll('[data-block-id]').length,
};
details['reading time'] = [
humanTime(details.words / 275),
'~275 wpm',
];
details['speaking time'] = [
humanTime(details.words / 180),
'~180 wpm',
];
$container.children[0].innerHTML = `
${store().hide_page_details_text ? '' : '<span><b>page details<br></b> (click to copy)</span>'}
${Object.keys(details).reduce(
(prev, key) =>
prev +
(Array.isArray(details[key])
? `<p>
<b>${details[key][0]}</b> ${key}
<!-- from https://fontawesome.com/icons/question-circle?style=regular -->
<svg data-tooltip="${details[key][1]}" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 512 512">
<path
fill="currentColor"
d="M256 8C119.043 8 8 119.083 8 256c0 136.997 111.043 248 248 248s248-111.003
248-248C504 119.083 392.957 8 256 8zm0 448c-110.532 0-200-89.431-200-200
0-110.495 89.472-200 200-200 110.491 0 200 89.471 200 200 0 110.53-89.431 200-200
200zm107.244-255.2c0 67.052-72.421 68.084-72.421 92.863V300c0 6.627-5.373 12-12 12h-45.647c-6.627
0-12-5.373-12-12v-8.659c0-35.745 27.1-50.034 47.579-61.516 17.561-9.845 28.324-16.541 28.324-29.579
0-17.246-21.999-28.693-39.784-28.693-23.189 0-33.894 10.977-48.942 29.969-4.057 5.12-11.46 6.071-16.666
2.124l-27.824-21.098c-5.107-3.872-6.251-11.066-2.644-16.363C184.846 131.491 214.94 112
261.794 112c49.071 0 101.45 38.304 101.45 88.8zM298 368c0 23.159-18.841
42-42 42s-42-18.841-42-42 18.841-42 42-42 42 18.841 42 42z"
></path>
</svg>
</p>`
: `<p><b>${details[key]}</b> ${key}</p>`),
''
)}`;
$page.previousElementSibling.children[0].appendChild($container);
if (!$container.offsetParent) return;
$container.offsetParent.appendChild($tooltip);
$container
.querySelectorAll('p')
.forEach((p) =>
p.addEventListener('click', (e) =>
copyToClipboard(e.target.innerText)
)
);
$container.querySelectorAll('[data-tooltip]').forEach((el) => {
el.addEventListener('mouseenter', (e) => {
$tooltip.innerText = el.getAttribute('data-tooltip');
$tooltip.style.top = el.parentElement.offsetTop + 2.5 + 'px';
$tooltip.style.left =
el.parentElement.offsetLeft +
el.parentElement.offsetWidth -
5 +
'px';
$tooltip.classList.add('active');
});
el.addEventListener('mouseleave', (e) =>
$tooltip.classList.remove('active')
);
});
}
});
},
},
};

View File

@ -0,0 +1,22 @@
{
"name": "word counter",
"id": "b99deb52-6955-43d2-a53b-a31540cd19a5",
"version": "0.3.0",
"description": "view word/character/sentence/block count & speaking/reading times in the side panel.",
"tags": ["extension", "panel"],
"authors": [
{
"name": "dragonwocky",
"email": "thedragonring.bod@gmail.com",
"homepage": "https://dragonwocky.me/",
"avatar": "https://dragonwocky.me/avatar.jpg"
}
],
"js": {
"client": ["client.mjs"]
},
"css": {
"client": ["client.css"]
},
"options": []
}