From 98a67381db1a8dad1e84384aad87f6ad2e06f7d0 Mon Sep 17 00:00:00 2001 From: EnixCoda Date: Tue, 12 Jul 2022 01:15:48 +0800 Subject: [PATCH] refactor: raise Gitako out of document body --- src/components/SideBar.tsx | 5 +- src/components/SideBarBodyWrapper.tsx | 22 ++++--- src/content.tsx | 3 +- src/styles/index.scss | 24 ++++---- src/utils/DOMHelper.ts | 84 +++++---------------------- src/utils/hooks/usePJAX.ts | 4 +- 6 files changed, 46 insertions(+), 96 deletions(-) diff --git a/src/components/SideBar.tsx b/src/components/SideBar.tsx index 5bb8b8c..6f5e536 100644 --- a/src/components/SideBar.tsx +++ b/src/components/SideBar.tsx @@ -127,8 +127,11 @@ export function SideBar() { collapsed: !shouldShow, })} baseSize={baseSize} + // TODO: move sidebarToggleMode inside onLeave={sidebarToggleMode === 'float' ? () => setShowSideBar(false) : undefined} - sizeVariableMountPoint={sidebarToggleMode === 'persistent' ? document.body : undefined} + sizeVariableMountPoint={ + sidebarToggleMode === 'persistent' ? DOMHelper.gitakoDescriptionTarget : undefined + } >
(null) useDebounce(() => configContext.onChange({ sideBarWidth: size }), 100, [size]) const applySizeToCSSVariables = React.useCallback(function apply( @@ -66,13 +66,6 @@ export function SideBarBodyWrapper({ sizeVariableMountPoint ? `${size}px` : undefined, sizeVariableMountPoint, ) - - if (bodyWrapperRef.current) - setCSSVariable( - '--gitako-width', - sizeVariableMountPoint ? undefined : `${size}px`, - bodyWrapperRef.current, - ) }, []) @@ -95,9 +88,15 @@ export function SideBarBodyWrapper({ } }, [width, sizeVariableMountPoint, applySizeToCSSVariables]) + const applyLatestSizeToCSSVariables = React.useCallback( + () => applySizeToCSSVariables(sizeVariableMountPoint, size), + [sizeVariableMountPoint, size], + ) React.useEffect(() => { - applySizeToCSSVariables(sizeVariableMountPoint, size) - }, [sizeVariableMountPoint, size, applySizeToCSSVariables]) + applyLatestSizeToCSSVariables() + }, [applyLatestSizeToCSSVariables]) + + useOnPJAXDone(applyLatestSizeToCSSVariables) const onMouseLeave = React.useCallback( (e: React.MouseEvent) => { @@ -112,11 +111,10 @@ export function SideBarBodyWrapper({ blockLeaveRef.current = state === 'resizing' }, []) - const defaultSideBarWidth = React.useMemo(() => getDefaultConfigs().sideBarWidth, []); + const defaultSideBarWidth = React.useMemo(() => getDefaultConfigs().sideBarWidth, []) return (
) } diff --git a/src/styles/index.scss b/src/styles/index.scss index 205d04a..beafa12 100644 --- a/src/styles/index.scss +++ b/src/styles/index.scss @@ -99,7 +99,7 @@ $minimal-z-index: max( mask-position: center; } -.#{$name}-ready { +[data-#{$name}-ready='true'] { // github // code folding start .blob-wrapper table .blob-num { @@ -232,16 +232,18 @@ $minimal-z-index: max( } } -.with-gitako-spacing { - @media screen { - margin-left: var(--gitako-width); - } +html[data-with-gitako-spacing='true'] { + body { + @media screen { + margin-left: var(--gitako-width); + } - // gitee - &.git-project { - width: auto; // shrink width - .site-content { - min-width: 1040px; + // gitee + &.git-project { + width: auto; // shrink width + .site-content { + min-width: 1040px; + } } } } @@ -425,6 +427,7 @@ $minimal-z-index: max( display: flex; flex-direction: column; background: var(--color-bg-subtle); + font-size: 14px; .octicon-wrapper { display: inline-block; @@ -638,6 +641,7 @@ $minimal-z-index: max( overflow: hidden; text-overflow: ellipsis; align-items: center; + font-size: 14px; } &:not(:hover) { diff --git a/src/utils/DOMHelper.ts b/src/utils/DOMHelper.ts index b53bb6c..409a629 100644 --- a/src/utils/DOMHelper.ts +++ b/src/utils/DOMHelper.ts @@ -3,33 +3,24 @@ */ export const rootElementID = 'gitako-root' - -export function setGitakoBodyClass(className: string, enable: boolean) { - const classList = document.body.classList - if (enable) classList.add(className) - else classList.remove(className) -} +export const gitakoDescriptionTarget = document.documentElement /** * when gitako is ready, make page's header narrower * or cancel it */ export function markGitakoReadyState(ready: boolean) { - const readyClassName = 'gitako-ready' - return setGitakoBodyClass(readyClassName, ready) + const readyAttributeName = 'data-gitako-ready' + return gitakoDescriptionTarget.setAttribute(readyAttributeName, `${ready}`) } /** * if should show gitako, then move body right to make space for showing gitako * otherwise, hide the space */ -export const bodySpacingClassName = 'with-gitako-spacing' +export const spacingAttributeName = 'data-with-gitako-spacing' export function setBodyIndent(shouldShowGitako: boolean) { - if (shouldShowGitako) { - document.body.classList.add(bodySpacingClassName) - } else { - document.body.classList.remove(bodySpacingClassName) - } + gitakoDescriptionTarget.setAttribute(spacingAttributeName, `${shouldShowGitako}`) } export function $(selector: string): HTMLElement | null @@ -56,20 +47,20 @@ export function $(selector: string, existCallback?: any, otherwise?: any) { /** * DOM Structure after calling the `insert*MountPoint` functions * - * - * - *
- *
- *
- *
- *
- *
- * - * + * + * + * + *
+ *
+ *
+ *
+ *
+ *
+ * */ +const mountPointContainer = document.documentElement export function insertMountPoint() { - const mountPointContainer = document.body // TODO: when replace this, refactor root of `$` return $(formatID(rootElementID), undefined, () => { const element = document.createElement('div') element.setAttribute('id', rootElementID) @@ -186,46 +177,3 @@ export function formatClass(className: string) { export function parseIntFromElement(e: HTMLElement): number { return parseInt((e.innerText || '').replace(/[^0-9]/g, '')) } - -/** - * Unlike the good-old-PJAX-time, now GitHub replaces whole body element after redirecting using turbo. - * If move Gitako mount point from `body` to `html`, Gitako style would break because it inherits style from GitHub body. - * The temporary solution is recovery Gitako elements once the body is removed. - */ -export function persistGitakoElements(mountPointElement = insertMountPoint()) { - mountPointElement.setAttribute('data-turbo-permanent', '') - - const observer = new MutationObserver(mutations => { - for (const { addedNodes, removedNodes } of mutations) { - const [addedBody, removedBody] = [addedNodes, removedNodes].map(findBodyElement) - if (addedBody && removedBody) { - // hard-coded list due to limited time - // TODO: refactor in a better practice - - // migrate gitako attributes, e.g. class - const propertiesNeedToMigrate = ['--gitako-width'] - for (const property of propertiesNeedToMigrate) { - const oldValue = removedBody.style.getPropertyValue(property) - if (oldValue) addedBody.style.setProperty(property, oldValue) - } - const cssClassesNeedToMigrate = [bodySpacingClassName] - for (const cssClass of cssClassesNeedToMigrate) { - if (removedBody.classList.contains(cssClass)) addedBody.classList.add(cssClass) - } - - // move gitako elements - if (!addedBody.contains(mountPointElement)) addedBody.appendChild(mountPointElement) - if (removedBody.contains(mountPointElement)) removedBody.removeChild(mountPointElement) - } - } - - function findBodyElement(addedNodes: NodeList) { - return Array.from(addedNodes).find(addedNode => addedNode instanceof HTMLBodyElement) as - | HTMLBodyElement - | undefined - } - }) - observer.observe(document.documentElement, { - childList: true, - }) -} diff --git a/src/utils/hooks/usePJAX.ts b/src/utils/hooks/usePJAX.ts index 8dbda16..e0fd283 100644 --- a/src/utils/hooks/usePJAX.ts +++ b/src/utils/hooks/usePJAX.ts @@ -58,9 +58,7 @@ export const loadWithPJAX = (url: string, element: HTMLElement) => { export function useOnPJAXDone(callback: () => void) { useEvent('pjax:end', callback, document) // legacy support - // 'turbo:render' should be the best timing but GitHub has attached a mutation observer on body to block that - // TODO: fire at turbo:render - useEvent('turbo:load', callback, document) + useEvent('turbo:render', callback, document) } export function useRedirectedEvents(