From 0462cf63587400413025ab8a12c5f5af691c46e2 Mon Sep 17 00:00:00 2001 From: David McArthur Date: Thu, 19 Dec 2024 16:17:58 +0000 Subject: [PATCH] better pages UI with scaling --- packages/paged/src/pagedjs/chunker/chunker.js | 16 +- packages/paged/src/pagedjs/chunker/page.js | 22 +- packages/paged/src/pagedjs/index.scss | 239 ++++++++++-------- packages/paged/src/pagedjs/interface.scss | 25 +- .../src/pagedjs/modules/header-footer.js | 4 +- packages/paged/src/pagedjs/utils/css.js | 8 - packages/paged/src/pages.ts | 2 - .../markdown-to-mdx/mdx-handlers/index.tsx | 12 +- .../mdx-handlers/math/index.tsx | 19 +- .../mdx-handlers/math/maths-provider.tsx | 4 +- .../components/dark-mode-toggle/styles.scss | 83 ------ .../components/print-button/print-button.scss | 117 +++++++++ .../components/print-button/print-button.tsx | 60 +++++ packages/runtime/src/index.ts | 1 - packages/runtime/src/print-view.tsx | 67 ++++- packages/runtime/src/providers/index.tsx | 19 +- .../src/providers/loading-provider.tsx | 33 --- .../runtime/src/providers/view-provider.tsx | 106 +++++--- packages/runtime/src/runtime.tsx | 44 ++-- packages/runtime/src/sidebar/index.tsx | 39 +-- packages/runtime/src/sidebar/menu/index.tsx | 10 +- packages/runtime/src/sidebar/sidebar.scss | 9 + packages/runtime/src/sidebar/views/print.tsx | 3 - .../src/sidebar/views/table-of-contents.tsx | 10 +- .../src/sidebar/views/view-options.tsx | 9 +- .../runtime/src/styles/content/index.scss | 14 +- packages/runtime/src/styles/index.scss | 1 + packages/runtime/src/styles/pages.scss | 10 + packages/runtime/src/styles/structure.scss | 20 +- packages/runtime/src/styles/ui.scss | 31 +-- packages/runtime/src/view-switcher.tsx | 9 +- src/app.tsx | 3 +- 32 files changed, 611 insertions(+), 438 deletions(-) delete mode 100644 packages/paged/src/pagedjs/utils/css.js delete mode 100644 packages/runtime/src/components/dark-mode-toggle/styles.scss create mode 100644 packages/runtime/src/components/print-button/print-button.scss create mode 100644 packages/runtime/src/components/print-button/print-button.tsx delete mode 100644 packages/runtime/src/providers/loading-provider.tsx delete mode 100644 packages/runtime/src/sidebar/views/print.tsx create mode 100644 packages/runtime/src/styles/pages.scss diff --git a/packages/paged/src/pagedjs/chunker/chunker.js b/packages/paged/src/pagedjs/chunker/chunker.js index 0503a34..f93c218 100644 --- a/packages/paged/src/pagedjs/chunker/chunker.js +++ b/packages/paged/src/pagedjs/chunker/chunker.js @@ -36,6 +36,11 @@ export default class Chunker { previousAtPage.remove() } + const previousRenderArea = renderTo.querySelector('#pagedjs_render_area') + if (previousRenderArea) { + previousRenderArea.remove() + } + const size = this.config.paper.selectedSize const paper = this.config.paper.sizes[size] @@ -44,6 +49,12 @@ export default class Chunker { this.style.innerHTML = `@page { size: ${size}; margin: 0; padding: 0; }` renderTo.appendChild(this.style); + this.pageRenderArea = document.createElement("div"); + this.pageRenderArea.id = 'pagedjs_render_area' + this.pageRenderArea.style.setProperty('--pagedjs-width', paper.width); + this.pageRenderArea.style.setProperty('--pagedjs-height', paper.height); + renderTo.appendChild(this.pageRenderArea); + this.pagesArea = document.createElement("div"); this.pagesArea.classList.add("pagedjs_pages"); this.pagesArea.style.setProperty('--pagedjs-width', paper.width); @@ -61,6 +72,8 @@ export default class Chunker { afterPageLayout(fragment, page) { breaks.afterPageLayout(fragment, page) headerFooter.afterPageLayout(fragment, this.config.headerFooter, this.total) + this.pageRenderArea.removeChild(fragment) + this.pagesArea.append(fragment) // fragment.classList.remove('loading') } @@ -260,7 +273,7 @@ export default class Chunker { addPage(blank) { let lastPage = this.pages[this.pages.length - 1]; // Create a new page from the template - let page = new Page(this.pagesArea, this.pageTemplate, blank); + let page = new Page(this.pageRenderArea, this.pageTemplate, blank); this.pages.push(page); @@ -354,6 +367,7 @@ export default class Chunker { destroy() { this.removePages() this.pagesArea.remove() + this.pageRenderArea.remove() this.style.remove() } } diff --git a/packages/paged/src/pagedjs/chunker/page.js b/packages/paged/src/pagedjs/chunker/page.js index 056697c..fb95cf9 100644 --- a/packages/paged/src/pagedjs/chunker/page.js +++ b/packages/paged/src/pagedjs/chunker/page.js @@ -16,33 +16,21 @@ export default class Page { create(template, after) { let clone = document.importNode(this.pageTemplate.content, true); + this.pagesArea.appendChild(clone); - let page, index; - if (after) { - this.pagesArea.insertBefore(clone, after.nextElementSibling); - index = Array.prototype.indexOf.call(this.pagesArea.children, after.nextElementSibling); - page = this.pagesArea.children[index]; - } else { - this.pagesArea.appendChild(clone); - page = this.pagesArea.lastChild; - } - - let pagebox = page.querySelector(".pagedjs_pagebox"); + let page = this.pagesArea.lastChild; let area = page.querySelector(".pagedjs_page_content"); - let footnotesArea = page.querySelector(".pagedjs_footnote_area"); let size = area.getBoundingClientRect(); area.style.columnWidth = Math.round(size.width) + "px"; - area.style.columnGap = "calc(var(--pagedjs-margin-right) + var(--pagedjs-margin-left))"; + this.area = area; this.width = Math.round(size.width); this.height = Math.round(size.height); this.element = page; - this.pagebox = pagebox; - this.area = area; - this.footnotesArea = footnotesArea; - + this.pagebox = page.querySelector(".pagedjs_pagebox"); + this.footnotesArea = page.querySelector(".pagedjs_footnote_area"); return page; } diff --git a/packages/paged/src/pagedjs/index.scss b/packages/paged/src/pagedjs/index.scss index 97a13e4..9f2374d 100644 --- a/packages/paged/src/pagedjs/index.scss +++ b/packages/paged/src/pagedjs/index.scss @@ -1,3 +1,4 @@ +#pagedjs_render_area, .pagedjs_pages { --pagedjs-width: 210mm; --pagedjs-height: 297mm; @@ -7,149 +8,181 @@ --pagedjs-margin-bottom: 25mm; } +#pagedjs_render_area { + opacity: 0; + pointer-events: none; +} + .pagedjs_page { - width: var(--pagedjs-width); - height: var(--pagedjs-height); + width: var(--pagedjs-width); + height: var(--pagedjs-height); } @media print { - .pagedjs_page { - page-break-after: always; - break-after: page; - } + .pagedjs_page { + page-break-after: always; + break-after: page; + } } .pagedjs_sheet { - position: relative; - width: var(--pagedjs-width); - height: var(--pagedjs-height); - overflow: hidden; - display: grid; - grid-template-columns: [sheet-center] var(--pagedjs-width); - grid-template-rows: [sheet-middle] var(--pagedjs-height); + position: relative; + width: var(--pagedjs-width); + height: var(--pagedjs-height); + overflow: hidden; + display: grid; + grid-template-columns: [sheet-center] var(--pagedjs-width); + grid-template-rows: [sheet-middle] var(--pagedjs-height); } .pagedjs_pagebox { - position: relative; - width: var(--pagedjs-width); - height: var(--pagedjs-height); - display: grid; - grid-template-columns: + position: relative; + width: var(--pagedjs-width); + height: var(--pagedjs-height); + display: grid; + grid-template-columns: [left] var(--pagedjs-margin-left) - [center] calc(var(--pagedjs-width) - var(--pagedjs-margin-left) - var(--pagedjs-margin-right)) + [center] calc( + var(--pagedjs-width) - var(--pagedjs-margin-left) - var( + --pagedjs-margin-right + ) + ) [right] var(--pagedjs-margin-right); - grid-template-rows: + grid-template-rows: [header] var(--pagedjs-margin-top) - [page] calc(var(--pagedjs-height) - var(--pagedjs-margin-top) - var(--pagedjs-margin-bottom)) + [page] calc( + var(--pagedjs-height) - var(--pagedjs-margin-top) - var( + --pagedjs-margin-bottom + ) + ) [footer] var(--pagedjs-margin-bottom); - grid-column: sheet-center; - grid-row: sheet-middle; + grid-column: sheet-center; + grid-row: sheet-middle; } .pagedjs_area { - grid-column: center; - grid-row: page; - width: 100%; - height: 100%; + grid-column: center; + grid-row: page; + width: 100%; + height: 100%; } .pagedjs_page_content { - width: 100%; - height: 100%; - position: relative; - column-fill: auto; + width: 100%; + height: 100%; + position: relative; + column-fill: auto; + column-gap: calc( + var(--pagedjs-margin-right) + var(--pagedjs-margin-left) + ); } .pagedjs_page_content > div { - height: inherit; + height: inherit; } /* margins ------ */ .pagedjs_margin-top { - width: calc(var(--pagedjs-width) - var(--pagedjs-margin-left) - var(--pagedjs-margin-right)); - height: var(--pagedjs-margin-top); - grid-column: center; - grid-row: header; - flex-wrap: nowrap; - display: grid; - grid-template-columns: repeat(3, 1fr); - grid-template-rows: 100%; + width: calc( + var(--pagedjs-width) - var(--pagedjs-margin-left) - var( + --pagedjs-margin-right + ) + ); + height: var(--pagedjs-margin-top); + grid-column: center; + grid-row: header; + flex-wrap: nowrap; + display: grid; + grid-template-columns: repeat(3, 1fr); + grid-template-rows: 100%; } .pagedjs_margin-top-left-corner { - width: var(--pagedjs-margin-left); - height: var(--pagedjs-margin-top); - grid-column: left; - grid-row: header; + width: var(--pagedjs-margin-left); + height: var(--pagedjs-margin-top); + grid-column: left; + grid-row: header; } .pagedjs_margin-top-right-corner { - width: var(--pagedjs-margin-right); - height: var(--pagedjs-margin-top); - grid-column: right; - grid-row: header; + width: var(--pagedjs-margin-right); + height: var(--pagedjs-margin-top); + grid-column: right; + grid-row: header; } .pagedjs_margin-top-left-corner { - width: var(--pagedjs-margin-left); + width: var(--pagedjs-margin-left); } .pagedjs_margin-top-right-corner { - width: var(--pagedjs-margin-right); + width: var(--pagedjs-margin-right); } .pagedjs_margin-right { - height: calc(var(--pagedjs-height) - var(--pagedjs-margin-top) - var(--pagedjs-margin-bottom)); - width: var(--pagedjs-margin-right); - right: 0; - grid-column: right; - grid-row: page; - display: grid; - grid-template-rows: repeat(3, 33.3333%); - grid-template-columns: 100%; + height: calc( + var(--pagedjs-height) - var(--pagedjs-margin-top) - var( + --pagedjs-margin-bottom + ) + ); + width: var(--pagedjs-margin-right); + right: 0; + grid-column: right; + grid-row: page; + display: grid; + grid-template-rows: repeat(3, 33.3333%); + grid-template-columns: 100%; } .pagedjs_margin-bottom { - width: calc(var(--pagedjs-width) - var(--pagedjs-margin-left) - var(--pagedjs-margin-right)); - height: var(--pagedjs-margin-bottom); - grid-column: center; - grid-row: footer; - display: grid; - grid-template-columns: repeat(3, 1fr); - grid-template-rows: 100%; + width: calc( + var(--pagedjs-width) - var(--pagedjs-margin-left) - var( + --pagedjs-margin-right + ) + ); + height: var(--pagedjs-margin-bottom); + grid-column: center; + grid-row: footer; + display: grid; + grid-template-columns: repeat(3, 1fr); + grid-template-rows: 100%; } .pagedjs_margin-bottom-left-corner { - width: var(--pagedjs-margin-left); - height: var(--pagedjs-margin-bottom); - grid-column: left; - grid-row: footer; + width: var(--pagedjs-margin-left); + height: var(--pagedjs-margin-bottom); + grid-column: left; + grid-row: footer; } .pagedjs_margin-bottom-right-corner { - width: var(--pagedjs-margin-right); - height: var(--pagedjs-margin-bottom); - grid-column: right; - grid-row: footer; + width: var(--pagedjs-margin-right); + height: var(--pagedjs-margin-bottom); + grid-column: right; + grid-row: footer; } .pagedjs_margin-bottom-left-corner { - width: var(--pagedjs-margin-left); + width: var(--pagedjs-margin-left); } .pagedjs_margin-bottom-right-corner { - width: var(--pagedjs-margin-right); + width: var(--pagedjs-margin-right); } .pagedjs_margin-left { - height: calc(var(--pagedjs-height) - var(--pagedjs-margin-top) - var(--pagedjs-margin-bottom)); - width: var(--pagedjs-margin-left); - grid-column: left; - grid-row: page; - display: grid; - grid-template-rows: repeat(3, 33.33333%); - grid-template-columns: 100%; + height: calc( + var(--pagedjs-height) - var(--pagedjs-margin-top) - var( + --pagedjs-margin-bottom + ) + ); + width: var(--pagedjs-margin-left); + grid-column: left; + grid-row: page; + display: grid; + grid-template-rows: repeat(3, 33.33333%); + grid-template-columns: 100%; } .pagedjs_margin-top > div, @@ -168,7 +201,7 @@ } .pagedjs_margin { - font-size: 0.8rem; + font-size: 0.8em; text-transform: uppercase; white-space: nowrap; @@ -191,48 +224,48 @@ /* breaks ------ */ .pagedjs_area > div [data-split-to] { - margin-bottom: unset !important; - padding-bottom: unset !important; + margin-bottom: unset !important; + padding-bottom: unset !important; } .pagedjs_area > div [data-split-from] { - text-indent: unset !important; - margin-top: unset !important; - padding-top: unset !important; - initial-letter: unset !important; + text-indent: unset !important; + margin-top: unset !important; + padding-top: unset !important; + initial-letter: unset !important; } .pagedjs_area > div [data-split-from] > *::first-letter, .pagedjs_area > div [data-split-from]::first-letter { - color: unset !important; - font-size: unset !important; - font-weight: unset !important; - font-family: unset !important; - color: unset !important; - line-height: unset !important; - float: unset !important; - padding: unset !important; - margin: unset !important; + color: unset !important; + font-size: unset !important; + font-weight: unset !important; + font-family: unset !important; + color: unset !important; + line-height: unset !important; + float: unset !important; + padding: unset !important; + margin: unset !important; } .pagedjs_area > div [data-split-to]:not([data-footnote-call]):after, .pagedjs_area > div [data-split-to]:not([data-footnote-call])::after { - content: unset !important; + content: unset !important; } .pagedjs_area > div [data-split-from]:not([data-footnote-call]):before, .pagedjs_area > div [data-split-from]:not([data-footnote-call])::before { - content: unset !important; + content: unset !important; } .pagedjs_area > div li[data-split-from]:first-of-type { - list-style: none !important; + list-style: none !important; } .pagedjs_clear-after::after { - content: none !important; + content: none !important; } [data-align-last-split-element='justify'] { - text-align-last: justify !important; + text-align-last: justify !important; } diff --git a/packages/paged/src/pagedjs/interface.scss b/packages/paged/src/pagedjs/interface.scss index 46e4d04..c131186 100644 --- a/packages/paged/src/pagedjs/interface.scss +++ b/packages/paged/src/pagedjs/interface.scss @@ -3,12 +3,18 @@ $gap: 1em; margin: 0 auto; + #pagedjs_render_area, .pagedjs_pages { + $width: calc(var(--pagedjs-width) + ($gap * 2)); display: flex; - width: calc(var(--pagedjs-width) + ($gap * 2)); + width: $width; flex: 0; flex-wrap: wrap; - margin: 0 auto; + margin-left: calc(((100% - $width) / 2)); + } + + .pagedjs_pages { + transform-origin: center 0; } .pagedjs_page { @@ -19,17 +25,10 @@ } &.double { - &.loading { - visibility: hidden; - } - - &:not(.loading) { - width: calc(((var(--pagedjs-width) * 2) + ($gap * 2)) / 2); - .pagedjs_pages { - width: calc((var(--pagedjs-width) * 2) + ($gap * 2)); - transform: scale(0.5); - transform-origin: 0 0; - } + .pagedjs_pages { + $width: calc((var(--pagedjs-width) * 2) + ($gap * 2)); + width: $width; + margin-left: calc(((100% - $width) / 2)); } .pagedjs_page { diff --git a/packages/paged/src/pagedjs/modules/header-footer.js b/packages/paged/src/pagedjs/modules/header-footer.js index 8280b25..e183076 100644 --- a/packages/paged/src/pagedjs/modules/header-footer.js +++ b/packages/paged/src/pagedjs/modules/header-footer.js @@ -1,5 +1,3 @@ -import { cleanPseudoContent } from "../utils/css.js"; - export function afterPageLayout(fragment, headerFooter, pageNum, total) { if (pageNum === 1 && headerFooter.firstPage) { renderMargins(fragment, headerFooter.firstPage, pageNum, total) @@ -85,6 +83,6 @@ function getRollingTitle(fragment, rollingTitleSelector) { varFirst = selected[0].textContent; } - return cleanPseudoContent(varFirst) + return varFirst } diff --git a/packages/paged/src/pagedjs/utils/css.js b/packages/paged/src/pagedjs/utils/css.js deleted file mode 100644 index 9d971a3..0000000 --- a/packages/paged/src/pagedjs/utils/css.js +++ /dev/null @@ -1,8 +0,0 @@ -export function cleanPseudoContent(el, trim = "\"' ") { - if(el == null) return; - return el - .replace(new RegExp(`^[${trim}]+`), "") - .replace(new RegExp(`[${trim}]+$`), "") - .replace(/["']/g, match => "\\" + match) - .replace(/[\n]/g, match => "\\00000A"); -} diff --git a/packages/paged/src/pages.ts b/packages/paged/src/pages.ts index 194e0c1..9f71d09 100644 --- a/packages/paged/src/pages.ts +++ b/packages/paged/src/pages.ts @@ -9,7 +9,6 @@ let loading = true export async function renderPages() { loading = true - pages?.classList.add('loading') pagesBtn?.classList.add('loading') // console.log('chunking...') @@ -17,7 +16,6 @@ export async function renderPages() { console.log(`took: ${(chunks.performance / 1000).toFixed(2)}s`) loading = false - pages?.classList.remove('loading') pagesBtn?.classList.remove('loading') pages?.dispatchEvent(new Event("pages-loaded")); } diff --git a/packages/processor/src/markdown-to-mdx/mdx-handlers/index.tsx b/packages/processor/src/markdown-to-mdx/mdx-handlers/index.tsx index 8c42483..29cae0c 100644 --- a/packages/processor/src/markdown-to-mdx/mdx-handlers/index.tsx +++ b/packages/processor/src/markdown-to-mdx/mdx-handlers/index.tsx @@ -19,11 +19,13 @@ export function createMDXComponents(options: Partial) { // TODO: remove sectionize and use the titles section: Section, code(props) { - if ( - props.class?.includes('language-math') && - options.mathsAsTex !== true - ) { - return ; + if (props.class?.includes('language-math')) { + return ( + + ); } return ; }, diff --git a/packages/processor/src/markdown-to-mdx/mdx-handlers/math/index.tsx b/packages/processor/src/markdown-to-mdx/mdx-handlers/math/index.tsx index 7d59fe6..e8123b9 100644 --- a/packages/processor/src/markdown-to-mdx/mdx-handlers/math/index.tsx +++ b/packages/processor/src/markdown-to-mdx/mdx-handlers/math/index.tsx @@ -11,9 +11,11 @@ export type { FontName } from './mathjax'; type Props = { expr: string; + className: string; }; -export function MathJax({ expr }: Props) { +export function MathJax({ expr, className }: Props) { + // console.log(className); const ctx = useContext(MathsContext); if (ctx.mathsAsTex) { return ( @@ -24,8 +26,17 @@ export function MathJax({ expr }: Props) { }} /> ); - } else { - const children = getMathJax(expr, ctx.fontName); - return <>{render(children)}; } + + const children = getMathJax(expr, ctx.fontName); + + if (className === 'math-inline') { + return {render(children)}; + } + + if (className === 'math-display') { + return
{render(children)}
; + } + + throw new Error(`[maths] className '${className}' is not supported`); } diff --git a/packages/processor/src/markdown-to-mdx/mdx-handlers/math/maths-provider.tsx b/packages/processor/src/markdown-to-mdx/mdx-handlers/math/maths-provider.tsx index c9e111c..fda150b 100644 --- a/packages/processor/src/markdown-to-mdx/mdx-handlers/math/maths-provider.tsx +++ b/packages/processor/src/markdown-to-mdx/mdx-handlers/math/maths-provider.tsx @@ -14,8 +14,8 @@ type Maths = { export const MathsContext = createContext({ fontName: defaultFontName, - mathsAsTex: false, setFontName: () => {}, + mathsAsTex: false, setMathsAsTex: () => {}, }); @@ -30,8 +30,8 @@ export function MathsProvider({ const context = useMemo((): Maths => { return { fontName, - mathsAsTex, setFontName, + mathsAsTex, setMathsAsTex, }; }, [fontName, mathsAsTex]); diff --git a/packages/runtime/src/components/dark-mode-toggle/styles.scss b/packages/runtime/src/components/dark-mode-toggle/styles.scss deleted file mode 100644 index 63da99e..0000000 --- a/packages/runtime/src/components/dark-mode-toggle/styles.scss +++ /dev/null @@ -1,83 +0,0 @@ -#dark-theme-toggle { - $height: 2vw; - $spacing: 0.4vw; - $width: 4.5vw; - - position: fixed; - top: 2vw; - right: 2vw; - // position: relative; - - display: flex; - justify-content: space-between; - align-items: center; - width: $width; - height: $height; - border: $spacing solid var(--textColor); - background: var(--textColor); - border-radius: ($height + ($spacing * 2)) * 0.5; - overflow: hidden; - - .sun, - .moon { - width: $height; - height: $height; - border-radius: 50%; - display: flex; - justify-content: center; - align-items: center; - - svg { - display: block; - width: $height; - height: $height; - fill: var(--textColor); - } - } - - .sun svg { - transform: scale(0.8); - fill: var(--textColor); - } - - .moon svg { - transform: scale(0.7); - } - - label, - input { - position: absolute; - top: 0; - left: 0; - width: 100%; - height: 100%; - cursor: pointer; - } - - input { - margin: 0; - visibility: hidden; - } - - span { - display: none; - } - - &:not(:has(input:checked)) { - .sun { - background: var(--bg); - } - .moon svg { - fill: white; - } - } - - &:has(input:checked) { - .moon { - background: var(--bg); - } - .sun svg { - fill: white; - } - } -} diff --git a/packages/runtime/src/components/print-button/print-button.scss b/packages/runtime/src/components/print-button/print-button.scss new file mode 100644 index 0000000..c6b4617 --- /dev/null +++ b/packages/runtime/src/components/print-button/print-button.scss @@ -0,0 +1,117 @@ +#print-btn { + $d: 1.7em; + + position: relative; + width: $d; + height: $d; + border-radius: 50%; + display: flex; + justify-content: center; + align-items: center; + margin-top: 0.5em; + margin-bottom: 0.5em; + background-color: white; + // transition: background-color 0.2s; + + svg { + display: block; + width: $d; + height: $d; + transform: scale(0.6); + fill: var(--textColor); + // transition: fill 0.2s; + } + + label, + input { + position: absolute; + top: 0; + left: 0; + width: 100%; + height: 100%; + cursor: pointer; + } + + input { + margin: 0; + visibility: hidden; + } + + span { + display: none; + } + + .spinner { + $height: 3em; + $stroke: 2px; + position: absolute; + top: 0; + right: 0; + bottom: 0; + left: 0; + width: $height * 0.5; + height: $height * 0.5; + margin: auto; + opacity: 0; + + border-radius: 50%; + display: inline-block; + border-top: $stroke solid; + // border-top-color: var(--textColor); + border-top-color: white; // may as well hide the spinner on web view + border-right: $stroke solid transparent; + box-sizing: border-box; + animation: rotation 1s linear infinite; + transition: opacity 0.2s; + pointer-events: none; + } + + &.loading .spinner { + opacity: 1; + } + + &:has(input:checked) { + background-color: var(--textColor); + svg { + fill: var(--bg); + } + .spinner { + border-top-color: white; + } + } + + @keyframes rotation { + 0% { + transform: rotate(0deg); + } + 100% { + transform: rotate(360deg); + } + } +} + +#print-zoom { + input[type='range'] { + $thumb-border-width: 5px; + $track-border-width: 0; + $track-width: 6px; + $track-height: 100px; + $thumb-height: 18px; + $track-color: #0002; + + display: block; + height: $track-height; + width: $track-width; + writing-mode: vertical-lr; + margin: 0 auto; + + &::-webkit-slider-runnable-track { + background: $track-color; + width: $thumb-border-width; + } + &::-webkit-slider-thumb { + margin-left: ((-$track-border-width * 2 + $track-width) * 0.5) - + ($thumb-height * 0.5); + } + } +} diff --git a/packages/runtime/src/components/print-button/print-button.tsx b/packages/runtime/src/components/print-button/print-button.tsx new file mode 100644 index 0000000..9873599 --- /dev/null +++ b/packages/runtime/src/components/print-button/print-button.tsx @@ -0,0 +1,60 @@ +import { Print } from '../icons'; +import classNames from 'classnames'; +import { useContext } from 'preact/hooks'; + +// import { Readability } from '../../constants/readability'; +import { ViewContext } from '../../providers/view-provider'; + +import './print-button.scss'; + +// const scaleObj: Readability = { +// name: 'scale', +// min: 0.5, +// max: 1, +// increment: 0.01, +// defaultValue: 1, +// }; + +export function PrintButton() { + const { showPages, setShowPages, loading } = useContext(ViewContext); + + function handleChange(e) { + if (e.target instanceof HTMLInputElement) { + setShowPages(e.target.checked); + } + } + + return ( + <> + +
+ + +
+ ); } diff --git a/packages/runtime/src/sidebar/index.tsx b/packages/runtime/src/sidebar/index.tsx index bdbd284..22d5eb7 100644 --- a/packages/runtime/src/sidebar/index.tsx +++ b/packages/runtime/src/sidebar/index.tsx @@ -1,12 +1,9 @@ import { TableOfContents } from './views/table-of-contents'; import { ViewOptions } from './views/view-options'; - -import { useLocalStorage } from '@isos/use-local-storage'; +import { useState } from 'preact/hooks'; import HamburgerSvg from '../assets/hamburger.svg'; -import { ViewOptionsProvider } from '../providers/view-options-provider'; import { Menu, SidebarView } from './menu'; -import { Print } from './views/print'; import './sidebar.scss'; @@ -16,20 +13,9 @@ type Props = { }; export function Sidebar({ jsString, setShowSidebar }: Props) { - const [sidebarView, setSidebarView] = useLocalStorage( - 'sidebar-view', + const [sidebarView, setSidebarView] = useState( SidebarView.tableOfContents, ); - - function handleSetSidebarView(view: SidebarView) { - setSidebarView(view); - if (view === SidebarView.print) { - document.documentElement.classList.add('print-view'); - } else { - document.documentElement.classList.remove('print-view'); - } - } - return (