import CONFIG from './config' import CommonHead from '@/components/CommonHead' import TopNav from './components/TopNav' import Live2D from '@/components/Live2D' import { useGlobal } from '@/lib/global' import BLOG from '@/blog.config' import { isBrowser, loadExternalResource } from '@/lib/utils' import Footer from './components/Footer' import { useEffect } from 'react' import RightFloatButtons from './components/RightFloatButtons' import { useRouter } from 'next/router' import Mark from 'mark.js' import SearchNave from './components/SearchNav' import BlogPostListPage from './components/BlogPostListPage' import BlogPostListScroll from './components/BlogPostListScroll' import Hero from './components/Hero' import Announcement from './components/Announcement' import CatalogWrapper from './components/CatalogWrapper' import TagItemMiddle from './components/TagItemMiddle' import HeaderArticle from './components/HeaderArticle' import Link from 'next/link' import ArticleAdjacent from './components/ArticleAdjacent' import Comment from '@/components/Comment' import ArticleCopyright from './components/ArticleCopyright' import ShareBar from '@/components/ShareBar' import NotionPage from '@/components/NotionPage' import { ArticleInfo } from './components/ArticleInfo' import { ArticleLock } from './components/ArticleLock' import BlogPostArchive from './components/BlogPostArchive' import Card from './components/Card' import JumpToCommentButton from './components/JumpToCommentButton' import BlogListBar from './components/BlogListBar' import { Transition } from '@headlessui/react' /** * 基础布局 * 采用左右两侧布局,移动端使用顶部导航栏 * @param props * @returns {JSX.Element} * @constructor */ const LayoutBase = props => { const { children, headerSlot, meta, siteInfo, containerSlot, post } = props const { onLoading } = useGlobal() if (isBrowser()) { loadExternalResource('/css/theme-matery.css', 'css') } return (
{/* SEO相关 */} {/* 顶部导航栏 */} {/* 顶部嵌入 */} {headerSlot}
{/* 嵌入区域 */}
{containerSlot}
{children}
{/* 左下角悬浮 */}
{/* 右下角悬浮 */} {/* 页脚 */}
) } /** * 首页 * 首页就是一个文章列表,但是嵌入了Hero大图和公告 * @param {*} props * @returns */ const LayoutIndex = (props) => { return } headerSlot={CONFIG.HOME_BANNER_ENABLE && } /> } /** * 博客列表 * @param {*} props * @returns */ const LayoutPostList = (props) => { return ( }> {BLOG.POST_LIST_STYLE === 'page' ? : } ) } /** * 搜搜 * @param {*} props * @returns */ const LayoutSearch = props => { const { keyword } = props const router = useRouter() const currentSearch = keyword || router?.query?.s useEffect(() => { setTimeout(() => { if (currentSearch) { const targets = document.getElementsByClassName('replace') for (const container of targets) { if (container && container.innerHTML) { const re = new RegExp(currentSearch, 'gim') const instance = new Mark(container) instance.markRegExp(re, { element: 'span', className: 'text-red-500 border-b border-dashed' }) } } } }, 100) }) return ( {!currentSearch ? :
{BLOG.POST_LIST_STYLE === 'page' ? : }
}
) } /** * 归档 * @param {*} props * @returns */ const LayoutArchive = (props) => { const { archivePosts } = props return } >
{Object.keys(archivePosts).map(archiveTitle => ( ))}
} /** * 文章详情页 * @param {*} props * @returns */ const LayoutSlug = props => { const { post, lock, validPassword } = props return (} showCategory={false} showTag={false} floatRightBottom={}>
{/* 文章主体卡片 */}
{lock && } {!lock &&
{/* 文章信息 */} {post?.type && post?.type === 'Post' && <>

}
{/* Notion文章主体 */}
{post && }
{/* 分享 */} {/* 版权说明 */} {post?.type === 'Post' && }

{/* 评论互动 */}
}
{/* 底部文章推荐 */} {post?.type === 'Post' && } {/* 底部公告 */} {/* 右侧文章目录 */}
) } /** * 404 * @param {*} props * @returns */ const Layout404 = props => { const router = useRouter() useEffect(() => { // 延时3秒如果加载失败就返回首页 setTimeout(() => { const article = typeof document !== 'undefined' && document.getElementById('notion-article') if (!article) { router.push('/').then(() => { // console.log('找不到页面', router.asPath) }) } }, 3000) }) return (

404

页面未找到

) } /** * 分类列表 * @param {*} props * @returns */ const LayoutCategoryIndex = props => { const { categoryOptions } = props return ( } >
{categoryOptions.map(e => { return (
{e.name}({e.count})
) })}
) } /** * 标签列表 * @param {*} props * @returns */ const LayoutTagIndex = props => { const { tagOptions } = props const { locale } = useGlobal() return ( } >
{locale.COMMON.TAGS}
{tagOptions.map(tag => { return (
) })}
) } export { CONFIG as THEME_CONFIG, LayoutIndex, LayoutPostList, LayoutSearch, LayoutArchive, LayoutSlug, Layout404, LayoutCategoryIndex, LayoutTagIndex }