From 109b80dc3ae36305a8a2adbb0a3fd012fdf6dfa3 Mon Sep 17 00:00:00 2001 From: Wei Gao Date: Sun, 27 Oct 2019 23:37:03 +0800 Subject: [PATCH 1/3] change(v2): refactor dark toggle into a theme --- CHANGELOG-2.x.md | 14 ++++---- .../src/hooks/theme.js | 34 +++++++++++++++++++ .../src/theme/Navbar/index.js | 32 ++++++----------- 3 files changed, 52 insertions(+), 28 deletions(-) create mode 100644 packages/docusaurus-theme-classic/src/hooks/theme.js diff --git a/CHANGELOG-2.x.md b/CHANGELOG-2.x.md index cdc9f020ceb3..7ae5ecdecec7 100644 --- a/CHANGELOG-2.x.md +++ b/CHANGELOG-2.x.md @@ -5,13 +5,14 @@ - Slightly adjust search icon position to be more aligned on small width device. - Convert sitemap plugin to TypeScript. - Significantly reduce main bundle size and initial HTML payload on production build. Generated JS files from webpack is also shorter in name. +- Refactor dark toggle into a hook. ## 2.0.0-alpha.31 -- Footer is now sticky/ pinned to the bottom of the viewport in desktop browsers. +- Footer is now sticky/ pinned to the bottom of the viewport in desktop browsers. - Footer is now also displayed in docs page for consistency. - Remove empty doc sidebar container if sidebar for a particular doc page does not exist. Otherwise, it will cause an additional empty space. -- Default PostCSS loader now only polyfills stage 3+ features (previously it was stage 2) like Create React App. Stage 2 CSS is considered relatively unstable and subject to change while Stage 3 features will likely become a standard. +- Default PostCSS loader now only polyfills stage 3+ features (previously it was stage 2) like Create React App. Stage 2 CSS is considered relatively unstable and subject to change while Stage 3 features will likely become a standard. - Fix search bar focus bug. When you put the focus on search input, previously the focus will remain although we have clicked to other area outside of the search input. - New themeConfig option `sidebarCollapsible`. It is on by default. If explicitly set to `false`, all doc items in sidebar is expanded. Otherwise, it will still be a collapsible sidebar. - Disable adding hashes to the generated class names of CSS modules in dev mode. Generating unique identifiers takes some time, which can be saved since including paths to files in class names is enough to avoid collisions. @@ -27,11 +28,12 @@ - Fix babel transpilation include/exclude logic to be more efficient. This also fix a very weird bug `TypeError: Cannot assign to read only property 'exports' of object '#'`.([#1868](https://github.com/facebook/docusaurus/pull/1868)) -If you are still encountering the error. Please check whether you use `module.exports` for your `.js` file instead of doing `export` (mixing CJS and ES). See https://github.com/webpack/webpack/issues/4039#issuecomment-477779322 and https://github.com/webpack/webpack/issues/4039#issuecomment-273804003 for more context. +If you are still encountering the error. Please check whether you use `module.exports` for your `.js` file instead of doing `export` (mixing CJS and ES). See https://github.com/webpack/webpack/issues/4039#issuecomment-477779322 and https://github.com/webpack/webpack/issues/4039#issuecomment-273804003 for more context. ## 2.0.0-alpha.29 -**HOTFIX for 2.0.0-alpha.28**. +**HOTFIX for 2.0.0-alpha.28**. + - Fix missing `core-js` dependencies on `@docusaurus/core`. - Fix wrong `@babel/env` preset configuration that causes build compilation error. - New UI for webpack compilation progress bar. @@ -46,7 +48,7 @@ If you are still encountering the error. Please check whether you use `module.ex - Fix logo URL in footer to be appended with baseUrl automatically. - Add the option `--no-open` for `start` command. - Set `@babel/env` useBuiltins to `usage`. This will automatically use browserlist and import polyfills required. -- Modified TerserWebpackPlugin `terserOptions` for better cross-browser compatibility. +- Modified TerserWebpackPlugin `terserOptions` for better cross-browser compatibility. - **BREAKING** `withBaseUrl` is renamed to `useBaseUrl` because its a React Hooks. Make sure you import/rename it correctly. Eg: `import useBaseUrl from '@docusaurus/useBaseUrl`; - Fix potential security vulnerability because we're exposing the directory structure of the host machine. - Upgrade dependencies. @@ -56,7 +58,7 @@ If you are still encountering the error. Please check whether you use `module.ex - Add `@theme/Tabs` which can be used to implement multi-language code tabs. - Implement `custom_edit_url` and `hide_title` markdown header for docusaurus v1 feature parity. - Reduce memory usage and slightly faster production build. -- Misc dependency upgrades. +- Misc dependency upgrades. ## 2.0.0-alpha.26 diff --git a/packages/docusaurus-theme-classic/src/hooks/theme.js b/packages/docusaurus-theme-classic/src/hooks/theme.js new file mode 100644 index 000000000000..826b2c2ffc8c --- /dev/null +++ b/packages/docusaurus-theme-classic/src/hooks/theme.js @@ -0,0 +1,34 @@ +/** + * Copyright (c) 2017-present, Facebook, Inc. + * + * This source code is licensed under the MIT license found in the + * LICENSE file in the root directory of this source tree. + */ +import * as React from 'react'; + +const useTheme = defaultTheme => { + const [theme, setTheme] = React.useState(defaultTheme); + React.useEffect(() => { + try { + setTheme(localStorage.getItem('theme')); + } catch (err) { + console.error(err); + } + }, [setTheme]); + + const setThemeSyncWithLocalStorage = React.useCallback( + nextTheme => { + try { + localStorage.setItem('theme', nextTheme); + setTheme(nextTheme); + } catch (err) { + console.error(err); + } + }, + [setTheme], + ); + + return [theme, setThemeSyncWithLocalStorage]; +}; + +export default useTheme; diff --git a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js index 15f1f2bb8a10..67f52b34bbc1 100644 --- a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js +++ b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js @@ -5,7 +5,7 @@ * LICENSE file in the root directory of this source tree. */ -import React, {useCallback, useState, useEffect} from 'react'; +import React, {useCallback, useState} from 'react'; import Toggle from 'react-toggle'; import Link from '@docusaurus/Link'; @@ -17,6 +17,8 @@ import SearchBar from '@theme/SearchBar'; import classnames from 'classnames'; +import useTheme from '../../hooks/theme'; + import styles from './styles.module.css'; function NavLink(props) { @@ -47,11 +49,11 @@ function Navbar() { const context = useDocusaurusContext(); const [sidebarShown, setSidebarShown] = useState(false); const [isSearchBarExpanded, setIsSearchBarExpanded] = useState(false); - const currentTheme = + const [theme, setTheme] = useTheme( typeof document !== 'undefined' ? document.querySelector('html').getAttribute('data-theme') - : ''; - const [theme, setTheme] = useState(currentTheme); + : '', + ); const {siteConfig = {}} = context; const {baseUrl, themeConfig = {}} = siteConfig; const {algolia, navbar = {}} = themeConfig; @@ -64,24 +66,10 @@ function Navbar() { setSidebarShown(false); }, [setSidebarShown]); - useEffect(() => { - try { - const localStorageTheme = localStorage.getItem('theme'); - setTheme(localStorageTheme); - } catch (err) { - console.error(err); - } - }, []); - - const onToggleChange = e => { - const nextTheme = e.target.checked ? 'dark' : ''; - setTheme(nextTheme); - try { - localStorage.setItem('theme', nextTheme); - } catch (err) { - console.error(err); - } - }; + const onToggleChange = useCallback( + e => setTheme(e.target.checked ? 'dark' : ''), + [setTheme], + ); const logoUrl = useBaseUrl(logo.src); return ( From f6c6bb2cf989e7b8d29bf6d2142f6824b875b86d Mon Sep 17 00:00:00 2001 From: Wei Gao Date: Mon, 28 Oct 2019 01:46:16 +0800 Subject: [PATCH 2/3] follow how themes resolve files --- .../docusaurus-theme-classic/src/theme/Navbar/index.js | 2 +- .../src/{ => theme}/hooks/theme.js | 8 ++++++-- 2 files changed, 7 insertions(+), 3 deletions(-) rename packages/docusaurus-theme-classic/src/{ => theme}/hooks/theme.js (78%) diff --git a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js index 67f52b34bbc1..33a4dd1aeea3 100644 --- a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js +++ b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js @@ -17,7 +17,7 @@ import SearchBar from '@theme/SearchBar'; import classnames from 'classnames'; -import useTheme from '../../hooks/theme'; +import useTheme from '@theme/hooks/theme'; import styles from './styles.module.css'; diff --git a/packages/docusaurus-theme-classic/src/hooks/theme.js b/packages/docusaurus-theme-classic/src/theme/hooks/theme.js similarity index 78% rename from packages/docusaurus-theme-classic/src/hooks/theme.js rename to packages/docusaurus-theme-classic/src/theme/hooks/theme.js index 826b2c2ffc8c..60e27c52cd20 100644 --- a/packages/docusaurus-theme-classic/src/hooks/theme.js +++ b/packages/docusaurus-theme-classic/src/theme/hooks/theme.js @@ -6,8 +6,12 @@ */ import * as React from 'react'; -const useTheme = defaultTheme => { - const [theme, setTheme] = React.useState(defaultTheme); +const useTheme = () => { + const [theme, setTheme] = React.useState( + typeof document !== 'undefined' + ? document.querySelector('html').getAttribute('data-theme') + : '', + ); React.useEffect(() => { try { setTheme(localStorage.getItem('theme')); From c61cbf02bbf48208f0e47fce90f28052faa7e4bb Mon Sep 17 00:00:00 2001 From: Wei Gao Date: Mon, 28 Oct 2019 01:53:44 +0800 Subject: [PATCH 3/3] let theme hook to pick up default theme by itself --- packages/docusaurus-theme-classic/src/theme/Navbar/index.js | 6 +----- 1 file changed, 1 insertion(+), 5 deletions(-) diff --git a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js index 33a4dd1aeea3..fd4f323679cb 100644 --- a/packages/docusaurus-theme-classic/src/theme/Navbar/index.js +++ b/packages/docusaurus-theme-classic/src/theme/Navbar/index.js @@ -49,11 +49,7 @@ function Navbar() { const context = useDocusaurusContext(); const [sidebarShown, setSidebarShown] = useState(false); const [isSearchBarExpanded, setIsSearchBarExpanded] = useState(false); - const [theme, setTheme] = useTheme( - typeof document !== 'undefined' - ? document.querySelector('html').getAttribute('data-theme') - : '', - ); + const [theme, setTheme] = useTheme(); const {siteConfig = {}} = context; const {baseUrl, themeConfig = {}} = siteConfig; const {algolia, navbar = {}} = themeConfig;