Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 3 additions & 3 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
Expand Up @@ -87,17 +87,17 @@ jobs:
- name: set env
if: ${{ github.event_name == 'pull_request' && github.repository == 'deepflowio/docs' && github.event.pull_request.base.ref == 'main' }}
run: |
echo "IMAGE_TAG_PREFIX=${{ github.event.pull_request.head.ref }}"|sed 's|main|latest|' >> $GITHUB_ENV
echo "IMAGE_TAG_PREFIX=${{ github.event.pull_request.head.ref }}"|sed 's|main|latest|; s|/|-|g' >> $GITHUB_ENV

- name: set env
if: ${{ github.event_name == 'push' && github.repository == 'deepflowio/docs'}}
run: |
echo "IMAGE_TAG_PREFIX=${{ github.ref_name }}"|sed 's|main|latest|' >> $GITHUB_ENV
echo "IMAGE_TAG_PREFIX=${{ github.ref_name }}"|sed 's|main|latest|; s|/|-|g' >> $GITHUB_ENV

- name: set env
if: ${{ github.event_name == 'workflow_dispatch' && github.repository == 'deepflowio/docs'}}
run: |
echo "IMAGE_TAG_PREFIX=${{ github.ref_name }}"|sed 's|main|latest|' >> $GITHUB_ENV
echo "IMAGE_TAG_PREFIX=${{ github.ref_name }}"|sed 's|main|latest|; s|/|-|g' >> $GITHUB_ENV

- name: Build and push docs image
if: ${{ github.repository == 'deepflowio/docs'}}
Expand Down
Binary file added .vitepress/theme/assets/docs-logo-dark.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file added .vitepress/theme/assets/docs-logo-light.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
80 changes: 80 additions & 0 deletions .vitepress/theme/components/DocBreadcrumb.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
<script setup lang="ts">
import { computed } from 'vue'
import { useData, useRoute, withBase } from 'vitepress'
import type { DefaultTheme } from 'vitepress'

const { theme, page, lang } = useData()
const route = useRoute()
const isZh = computed(() => lang.value.startsWith('zh'))

function normalize(path: string) {
return decodeURI(path.split(/[?#]/)[0]).replace(/\.(html|md)$/, '').replace(/\/$/, '')
}

function findPath(items: DefaultTheme.SidebarItem[], parents: DefaultTheme.SidebarItem[] = []): DefaultTheme.SidebarItem[] {
for (const item of items) {
const path = [...parents, item]
if (item.link && normalize(withBase(item.link)) === normalize(route.path)) return path
if (item.items) {
const found = findPath(item.items, path)
if (found.length) return found
}
}
return []
}

const crumbs = computed(() => {
const sidebar = theme.value.sidebar
if (!sidebar || typeof sidebar === 'string') return []
if (Array.isArray(sidebar)) return findPath(sidebar)
// A language or section may have its own sidebar; use the longest matching prefix.
const key = Object.keys(sidebar)
.filter(prefix => route.path.startsWith(withBase(prefix)))
.sort((a, b) => b.length - a.length)[0]
const value = key ? sidebar[key] : []
return findPath(Array.isArray(value) ? value : value?.items || [])
})

const title = computed(() => crumbs.value.at(-1)?.text || page.value.title)
const parents = computed(() => crumbs.value.slice(0, -1))
</script>

<template>
<nav class="doc-breadcrumb" :aria-label="isZh ? '文档路径' : 'Breadcrumb'">
<a :href="withBase(isZh ? '/zh/' : '/')">{{ isZh ? '文档' : 'Docs' }}</a>
<template v-for="(item, index) in parents" :key="index">
<span class="separator" aria-hidden="true">/</span>
<a v-if="item.link" :href="withBase(item.link)">{{ item.text }}</a>
<span v-else>{{ item.text }}</span>
</template>
<span class="separator" aria-hidden="true">/</span>
<span class="current" aria-current="page">{{ title }}</span>
</nav>
</template>

<style scoped>
.doc-breadcrumb {
display: flex;
flex-wrap: wrap;
align-items: center;
gap: 8px;
max-width: var(--df-md-reading-width);
margin: 0 auto 28px;
color: var(--df-md-text-3);
font-family: var(--df-md-font-sans);
font-size: 13px;
line-height: 1.6;
overflow-wrap: anywhere;
}
.doc-breadcrumb a { color: inherit; text-decoration: none; }
.doc-breadcrumb a:hover { color: var(--df-md-primary-6); }
.separator { color: var(--df-md-border-3); }
.current { color: var(--df-md-text-1); }
.doc-breadcrumb a:focus-visible {
outline: 2px solid var(--df-md-primary-6);
outline-offset: 3px;
}
@media (max-width: 959px) {
.doc-breadcrumb { margin-top: 8px; margin-bottom: 24px; }
}
</style>
45 changes: 37 additions & 8 deletions .vitepress/theme/components/DocHeader.vue
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,30 @@
<!-- doc-only 变体(build:doc-only)专属顶栏:常规构建也渲染本组件,但由
custom.css 隐藏(html.doc-only 未标记时 .doc-header 不显示),与
SiteNavbar 的显隐同由构建期写入 head 的 html 类驱动,无需构建开关。
布局:左 logo / 中搜索 / 右语言切换 + 明暗主题切换。
布局:左文档 Logo 和 Docs / 中搜索 / 右语言切换 + 明暗主题切换。
搜索/语言/主题的实现与 SidebarActions 一致:点击唤起 VitePress 本地
搜索、router 切换中英路径、翻转 isDark。配色走 VitePress 主题变量,
随明暗主题自适应(区别于刻意的深色品牌导航 SiteNavbar) -->
<header class="doc-header">
<div class="doc-header-inner">
<a class="doc-brand" :href="docsHref" aria-label="DeepFlow Docs">
<img class="doc-brand-logo" :src="withBase('/img/logo.png')" alt="DeepFlow" />
<span class="doc-brand-name">DeepFlow</span>
<a class="doc-brand" :href="docsHref" aria-label="Docs">
<img
class="doc-brand-logo doc-brand-logo-on-light"
:src="darkLogo"
width="24"
height="24"
alt=""
aria-hidden="true"
/>
<img
class="doc-brand-logo doc-brand-logo-on-dark"
:src="lightLogo"
width="24"
height="24"
alt=""
aria-hidden="true"
/>
<span class="doc-brand-name">Docs</span>
</a>

<div class="doc-search-trigger">
Expand Down Expand Up @@ -78,7 +93,9 @@

<script setup lang="ts">
import { computed, ref } from 'vue'
import { useData, useRouter, withBase } from 'vitepress'
import { useData, useRouter } from 'vitepress'
import darkLogo from '../assets/docs-logo-dark.png'
import lightLogo from '../assets/docs-logo-light.png'

const { lang, site, isDark } = useData()
const router = useRouter()
Expand Down Expand Up @@ -146,7 +163,7 @@ function openSearch() {
padding: 0 20px;
}

/* 左:logo(彩色图标明暗主题均可用)+ 站名 */
/* 左:文档 Logo + 站名。深色图案用于浅色主题,浅色图案用于深色主题。 */
.doc-brand {
display: inline-flex;
align-items: center;
Expand All @@ -157,8 +174,20 @@ function openSearch() {
}
.doc-brand-logo {
display: block;
width: 28px;
height: 28px;
flex-shrink: 0;
width: 24px;
height: 24px;
object-fit: contain;
}
/* Follow the html class set before the first frame to avoid hydration flicker. */
.doc-brand-logo-on-dark {
display: none;
}
:global(html.dark .doc-brand-logo-on-light) {
display: none;
}
:global(html.dark .doc-brand-logo-on-dark) {
display: block;
}
.doc-brand-name {
font-size: 17px;
Expand Down
4 changes: 2 additions & 2 deletions .vitepress/theme/components/EmbeddedSidebarButton.vue
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<template>
<!-- 嵌入式(iframe)模式下导航栏被隐藏,移动端用内容区左上角的悬浮按钮
<!-- 嵌入式(iframe)模式下导航栏被隐藏,移动端用面包屑同行的目录按钮
展开侧边栏。默认隐藏,显隐规则在 custom.css 的 html.embedded 部分,
经 doc-top 插槽渲染(仅文档页存在,首页等无侧边栏页面天然没有) -->
经 doc-before 插槽渲染(仅文档页存在,首页等无侧边栏页面天然没有) -->
<button
type="button"
class="embedded-sidebar-button"
Expand Down
Loading
Loading