@sugarat/theme 0.2.28 → 0.2.30
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/node.d.ts +2 -1
- package/package.json +3 -3
- package/src/components/BlogApp.vue +0 -1
- package/src/components/BlogHomeTags.vue +5 -4
- package/src/components/BlogHotArticle.vue +18 -9
- package/src/components/BlogItem.vue +40 -31
- package/src/components/BlogRecommendArticle.vue +5 -3
- package/src/composables/config/blog.ts +5 -0
- package/src/composables/config/index.ts +2 -1
- package/src/index.ts +3 -1
- package/src/utils/client/index.ts +5 -0
- package/src/components/BlogSearch.vue +0 -419
- package/src/components/LogoPagefind.vue +0 -55
package/node.d.ts
CHANGED
|
@@ -308,7 +308,7 @@ declare namespace Theme {
|
|
|
308
308
|
pagesData: PageData[];
|
|
309
309
|
srcDir?: string;
|
|
310
310
|
author?: string;
|
|
311
|
-
hotArticle?: HotArticle;
|
|
311
|
+
hotArticle?: HotArticle | false;
|
|
312
312
|
home?: HomeBlog;
|
|
313
313
|
/**
|
|
314
314
|
* 本地全文搜索定制
|
|
@@ -390,6 +390,7 @@ declare namespace Theme {
|
|
|
390
390
|
* 详见 https://oml2d.com/options/Options.html
|
|
391
391
|
*/
|
|
392
392
|
oml2d?: Options;
|
|
393
|
+
homeTags?: boolean;
|
|
393
394
|
}
|
|
394
395
|
interface BackToTop {
|
|
395
396
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@sugarat/theme",
|
|
3
|
-
"version": "0.2.
|
|
3
|
+
"version": "0.2.30",
|
|
4
4
|
"description": "简约风的 Vitepress 博客主题,sugarat vitepress blog theme",
|
|
5
5
|
"author": "sugar",
|
|
6
6
|
"license": "MIT",
|
|
@@ -42,11 +42,11 @@
|
|
|
42
42
|
"gray-matter": "^4.0.3",
|
|
43
43
|
"markdown-it-task-checkbox": "^1.0.6",
|
|
44
44
|
"mermaid": "^10.2.4",
|
|
45
|
-
"oh-my-live2d": "^0.
|
|
45
|
+
"oh-my-live2d": "^0.15.2",
|
|
46
46
|
"swiper": "^11.0.5",
|
|
47
47
|
"vitepress-markdown-timeline": "^1.2.1",
|
|
48
48
|
"vitepress-plugin-mermaid": "2.0.13",
|
|
49
|
-
"vitepress-plugin-pagefind": "0.2.
|
|
49
|
+
"vitepress-plugin-pagefind": "0.2.14",
|
|
50
50
|
"vitepress-plugin-rss": "0.2.2",
|
|
51
51
|
"vitepress-plugin-tabs": "0.2.0"
|
|
52
52
|
},
|
|
@@ -9,7 +9,6 @@ import BlogHomeBanner from './BlogHomeBanner.vue'
|
|
|
9
9
|
import BlogList from './BlogList.vue'
|
|
10
10
|
import BlogComment from './BlogComment.vue'
|
|
11
11
|
|
|
12
|
-
// import BlogSearch from './BlogSearch.vue'
|
|
13
12
|
import BlogSidebar from './BlogSidebar.vue'
|
|
14
13
|
import BlogImagePreview from './BlogImagePreview.vue'
|
|
15
14
|
import BlogArticleAnalyze from './BlogArticleAnalyze.vue'
|
|
@@ -2,16 +2,17 @@
|
|
|
2
2
|
import { computed, watch } from 'vue'
|
|
3
3
|
import { ElTag } from 'element-plus'
|
|
4
4
|
import { useBrowserLocation, useDark, useUrlSearchParams } from '@vueuse/core'
|
|
5
|
-
import {
|
|
5
|
+
import { useRoute, useRouter } from 'vitepress'
|
|
6
6
|
import {
|
|
7
7
|
useActiveTag,
|
|
8
8
|
useArticles,
|
|
9
|
-
|
|
9
|
+
useConfig,
|
|
10
|
+
useCurrentPageNum,
|
|
10
11
|
} from '../composables/config/blog'
|
|
11
12
|
|
|
12
13
|
const route = useRoute()
|
|
13
14
|
const docs = useArticles()
|
|
14
|
-
|
|
15
|
+
const showTags = useConfig()?.config?.blog?.homeTags ?? true
|
|
15
16
|
const tags = computed(() => {
|
|
16
17
|
return [...new Set(docs.value.map(v => v.meta.tag || []).flat(3))]
|
|
17
18
|
})
|
|
@@ -77,7 +78,7 @@ watch(
|
|
|
77
78
|
</script>
|
|
78
79
|
|
|
79
80
|
<template>
|
|
80
|
-
<div v-if="tags.length" class="card tags" data-pagefind-ignore="all">
|
|
81
|
+
<div v-if="showTags && tags.length" class="card tags" data-pagefind-ignore="all">
|
|
81
82
|
<!-- 头部 -->
|
|
82
83
|
<div class="card-header">
|
|
83
84
|
<span class="title svg-icon"><svg
|
|
@@ -2,15 +2,20 @@
|
|
|
2
2
|
import { computed, ref } from 'vue'
|
|
3
3
|
import { ElButton, ElLink } from 'element-plus'
|
|
4
4
|
import { withBase } from 'vitepress'
|
|
5
|
-
import { useArticles, useBlogConfig } from '../composables/config/blog'
|
|
6
|
-
import { formatShowDate } from '../utils/client'
|
|
5
|
+
import { useArticles, useBlogConfig, useCleanUrls } from '../composables/config/blog'
|
|
6
|
+
import { formatShowDate, wrapperCleanUrls } from '../utils/client'
|
|
7
7
|
import { fireSVG } from '../constants/svg'
|
|
8
8
|
|
|
9
|
-
const { hotArticle } = useBlogConfig()
|
|
10
|
-
|
|
11
|
-
const
|
|
12
|
-
|
|
13
|
-
|
|
9
|
+
const { hotArticle: _hotArticle } = useBlogConfig()
|
|
10
|
+
|
|
11
|
+
const hotArticle = computed(() =>
|
|
12
|
+
_hotArticle === false ? undefined : _hotArticle
|
|
13
|
+
)
|
|
14
|
+
|
|
15
|
+
const title = computed(() => hotArticle.value?.title || (`<span class="svg-icon">${fireSVG}</span>` + ' 精选文章'))
|
|
16
|
+
const nextText = computed(() => hotArticle.value?.nextText || '换一组')
|
|
17
|
+
const pageSize = computed(() => hotArticle.value?.pageSize || 9)
|
|
18
|
+
const empty = computed(() => hotArticle.value?.empty ?? '暂无精选内容')
|
|
14
19
|
|
|
15
20
|
const docs = useArticles()
|
|
16
21
|
|
|
@@ -27,10 +32,14 @@ function changePage() {
|
|
|
27
32
|
currentPage.value = newIdx + 1
|
|
28
33
|
}
|
|
29
34
|
|
|
35
|
+
const cleanUrls = useCleanUrls()
|
|
30
36
|
const currentWikiData = computed(() => {
|
|
31
37
|
const startIdx = (currentPage.value - 1) * pageSize.value
|
|
32
38
|
const endIdx = startIdx + pageSize.value
|
|
33
|
-
return recommendList.value.slice(startIdx, endIdx)
|
|
39
|
+
return recommendList.value.slice(startIdx, endIdx).map(v => ({
|
|
40
|
+
...v,
|
|
41
|
+
route: wrapperCleanUrls(cleanUrls, v.route)
|
|
42
|
+
}))
|
|
34
43
|
})
|
|
35
44
|
|
|
36
45
|
const showChangeBtn = computed(() => {
|
|
@@ -39,7 +48,7 @@ const showChangeBtn = computed(() => {
|
|
|
39
48
|
</script>
|
|
40
49
|
|
|
41
50
|
<template>
|
|
42
|
-
<div v-if="recommendList.length || empty" class="card recommend" data-pagefind-ignore="all">
|
|
51
|
+
<div v-if="_hotArticle !== false && (recommendList.length || empty) " class="card recommend" data-pagefind-ignore="all">
|
|
43
52
|
<!-- 头部 -->
|
|
44
53
|
<div class="card-header">
|
|
45
54
|
<span class="title" v-html="title" />
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
<script lang="ts" setup>
|
|
2
2
|
import { withBase } from 'vitepress'
|
|
3
3
|
import { computed } from 'vue'
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
4
|
+
import { formatShowDate, wrapperCleanUrls } from '../utils/client'
|
|
5
|
+
import { useCleanUrls } from '../composables/config/blog'
|
|
6
6
|
|
|
7
7
|
const props = defineProps<{
|
|
8
8
|
route: string
|
|
@@ -16,36 +16,25 @@ const props = defineProps<{
|
|
|
16
16
|
cover?: string | boolean
|
|
17
17
|
pin?: number
|
|
18
18
|
}>()
|
|
19
|
-
const { width } = useWindowSize()
|
|
20
|
-
const inMobile = computed(() => width.value <= 500)
|
|
21
19
|
const showTime = computed(() => {
|
|
22
20
|
return formatShowDate(props.date)
|
|
23
21
|
})
|
|
24
22
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
// while (parent) {
|
|
29
|
-
// if (parent.hasAttribute('preventDefault')) {
|
|
30
|
-
// return true
|
|
31
|
-
// }
|
|
32
|
-
// parent = parent.parentElement
|
|
33
|
-
// }
|
|
34
|
-
|
|
35
|
-
// return false
|
|
36
|
-
// }
|
|
23
|
+
const cleanUrls = useCleanUrls()
|
|
24
|
+
const link = computed(() => withBase(wrapperCleanUrls(!!cleanUrls, props.route)))
|
|
37
25
|
</script>
|
|
38
26
|
|
|
39
27
|
<template>
|
|
40
|
-
|
|
28
|
+
<!-- TODO: 响应式优化使用纯 CSS -->
|
|
29
|
+
<a class="blog-item" :href="link">
|
|
41
30
|
<i v-if="!!pin" class="pin" />
|
|
42
31
|
<!-- 标题 -->
|
|
43
|
-
<p
|
|
32
|
+
<p class="title mobile-visible">{{ title }}</p>
|
|
44
33
|
<div class="info-container">
|
|
45
34
|
<!-- 左侧信息 -->
|
|
46
35
|
<div class="info-part">
|
|
47
36
|
<!-- 标题 -->
|
|
48
|
-
<p
|
|
37
|
+
<p class="title pc-visible">{{ title }}</p>
|
|
49
38
|
<!-- 简短描述 -->
|
|
50
39
|
<p v-if="!descriptionHTML && !!description" class="description">
|
|
51
40
|
{{ description }}
|
|
@@ -54,21 +43,17 @@ const showTime = computed(() => {
|
|
|
54
43
|
<div class="description-html" v-html="descriptionHTML" />
|
|
55
44
|
</template>
|
|
56
45
|
<!-- 底部补充描述 -->
|
|
57
|
-
<div
|
|
46
|
+
<div class="badge-list pc-visible">
|
|
58
47
|
<span v-if="author" class="split">{{ author }}</span>
|
|
59
48
|
<span class="split">{{ showTime }}</span>
|
|
60
49
|
<span v-if="tag?.length" class="split">{{ tag.join(' · ') }}</span>
|
|
61
50
|
</div>
|
|
62
51
|
</div>
|
|
63
52
|
<!-- 右侧封面图 -->
|
|
64
|
-
<div
|
|
65
|
-
v-if="cover"
|
|
66
|
-
class="cover-img"
|
|
67
|
-
:style="`background-image: url(${withBase(`${cover}`)});`"
|
|
68
|
-
/>
|
|
53
|
+
<div v-if="cover" class="cover-img" :style="`background-image: url(${withBase(`${cover}`)});`" />
|
|
69
54
|
</div>
|
|
70
55
|
<!-- 底部补充描述 -->
|
|
71
|
-
<div
|
|
56
|
+
<div class="badge-list mobile-visible">
|
|
72
57
|
<span v-if="author" class="split">{{ author }}</span>
|
|
73
58
|
<span class="split">{{ showTime }}</span>
|
|
74
59
|
<span v-if="tag?.length" class="split">{{ tag.join(' · ') }}</span>
|
|
@@ -86,19 +71,19 @@ const showTime = computed(() => {
|
|
|
86
71
|
left: -4px;
|
|
87
72
|
opacity: 0.5;
|
|
88
73
|
}
|
|
74
|
+
|
|
89
75
|
.blog-item:hover .pin {
|
|
90
76
|
opacity: 1;
|
|
91
77
|
}
|
|
78
|
+
|
|
92
79
|
.blog-item .pin::before {
|
|
93
80
|
content: '';
|
|
94
81
|
position: absolute;
|
|
95
82
|
width: 120%;
|
|
96
83
|
height: 30px;
|
|
97
|
-
background-image: linear-gradient(
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
var(--blog-theme-color)
|
|
101
|
-
);
|
|
84
|
+
background-image: linear-gradient(45deg,
|
|
85
|
+
var(--blog-theme-color),
|
|
86
|
+
var(--blog-theme-color));
|
|
102
87
|
transform: rotate(-45deg) translateY(-20px);
|
|
103
88
|
display: flex;
|
|
104
89
|
align-items: center;
|
|
@@ -120,10 +105,12 @@ const showTime = computed(() => {
|
|
|
120
105
|
cursor: pointer;
|
|
121
106
|
display: flex;
|
|
122
107
|
flex-direction: column;
|
|
108
|
+
|
|
123
109
|
&:hover {
|
|
124
110
|
box-shadow: var(--box-shadow-hover);
|
|
125
111
|
}
|
|
126
112
|
}
|
|
113
|
+
|
|
127
114
|
.info-container {
|
|
128
115
|
display: flex;
|
|
129
116
|
align-items: center;
|
|
@@ -133,11 +120,13 @@ const showTime = computed(() => {
|
|
|
133
120
|
.info-part {
|
|
134
121
|
flex: 1;
|
|
135
122
|
}
|
|
123
|
+
|
|
136
124
|
.title {
|
|
137
125
|
font-size: 18px;
|
|
138
126
|
font-weight: 600;
|
|
139
127
|
margin-bottom: 8px;
|
|
140
128
|
}
|
|
129
|
+
|
|
141
130
|
.description {
|
|
142
131
|
color: var(--description-font-color);
|
|
143
132
|
font-size: 14px;
|
|
@@ -149,13 +138,16 @@ const showTime = computed(() => {
|
|
|
149
138
|
-webkit-line-clamp: 2;
|
|
150
139
|
-webkit-box-orient: vertical;
|
|
151
140
|
}
|
|
141
|
+
|
|
152
142
|
.description-html {
|
|
153
143
|
font-size: 14px;
|
|
154
144
|
}
|
|
145
|
+
|
|
155
146
|
.badge-list {
|
|
156
147
|
font-size: 13px;
|
|
157
148
|
color: var(--badge-font-color);
|
|
158
149
|
margin-top: 8px;
|
|
150
|
+
|
|
159
151
|
.split:not(:last-child) {
|
|
160
152
|
&::after {
|
|
161
153
|
content: '';
|
|
@@ -167,6 +159,7 @@ const showTime = computed(() => {
|
|
|
167
159
|
}
|
|
168
160
|
}
|
|
169
161
|
}
|
|
162
|
+
|
|
170
163
|
.cover-img {
|
|
171
164
|
width: 120px;
|
|
172
165
|
height: 80px;
|
|
@@ -176,11 +169,27 @@ const showTime = computed(() => {
|
|
|
176
169
|
background-size: 120px 80px;
|
|
177
170
|
}
|
|
178
171
|
|
|
172
|
+
.pc-visible {
|
|
173
|
+
display: block;
|
|
174
|
+
}
|
|
175
|
+
|
|
176
|
+
.mobile-visible {
|
|
177
|
+
display: none;
|
|
178
|
+
}
|
|
179
|
+
|
|
179
180
|
@media screen and (max-width: 500px) {
|
|
180
181
|
.cover-img {
|
|
181
182
|
width: 100px;
|
|
182
183
|
height: 60px;
|
|
183
184
|
background-size: 100px 60px;
|
|
184
185
|
}
|
|
186
|
+
|
|
187
|
+
.pc-visible {
|
|
188
|
+
display: none;
|
|
189
|
+
}
|
|
190
|
+
|
|
191
|
+
.mobile-visible {
|
|
192
|
+
display: block;
|
|
193
|
+
}
|
|
185
194
|
}
|
|
186
195
|
</style>
|
|
@@ -2,8 +2,8 @@
|
|
|
2
2
|
import { computed, onMounted, ref } from 'vue'
|
|
3
3
|
import { useRoute, withBase } from 'vitepress'
|
|
4
4
|
import { ElButton, ElLink } from 'element-plus'
|
|
5
|
-
import { formatShowDate } from '../utils/client'
|
|
6
|
-
import { useArticles, useBlogConfig } from '../composables/config/blog'
|
|
5
|
+
import { formatShowDate, wrapperCleanUrls } from '../utils/client'
|
|
6
|
+
import { useArticles, useBlogConfig, useCleanUrls } from '../composables/config/blog'
|
|
7
7
|
import { recommendSVG } from '../constants/svg'
|
|
8
8
|
import type { Theme } from '../composables/config/index'
|
|
9
9
|
|
|
@@ -145,6 +145,8 @@ onMounted(() => {
|
|
|
145
145
|
const currentPageNum = Math.floor(currentPageIndex / pageSize.value) + 1
|
|
146
146
|
currentPage.value = currentPageNum
|
|
147
147
|
})
|
|
148
|
+
|
|
149
|
+
const cleanUrls = useCleanUrls()
|
|
148
150
|
</script>
|
|
149
151
|
|
|
150
152
|
<template>
|
|
@@ -170,7 +172,7 @@ onMounted(() => {
|
|
|
170
172
|
<ElLink
|
|
171
173
|
type="info" class="title" :class="{
|
|
172
174
|
current: isCurrentDoc(v.route),
|
|
173
|
-
}" :href="v.route"
|
|
175
|
+
}" :href="wrapperCleanUrls(cleanUrls, v.route)"
|
|
174
176
|
>
|
|
175
177
|
{{ v.meta.title }}
|
|
176
178
|
</ElLink>
|
|
@@ -340,7 +340,7 @@ export namespace Theme {
|
|
|
340
340
|
pagesData: PageData[]
|
|
341
341
|
srcDir?: string
|
|
342
342
|
author?: string
|
|
343
|
-
hotArticle?: HotArticle
|
|
343
|
+
hotArticle?: HotArticle | false
|
|
344
344
|
home?: HomeBlog
|
|
345
345
|
/**
|
|
346
346
|
* 本地全文搜索定制
|
|
@@ -423,6 +423,7 @@ export namespace Theme {
|
|
|
423
423
|
* 详见 https://oml2d.com/options/Options.html
|
|
424
424
|
*/
|
|
425
425
|
oml2d?: Oml2dOptions
|
|
426
|
+
homeTags?: boolean
|
|
426
427
|
}
|
|
427
428
|
|
|
428
429
|
export interface BackToTop {
|
package/src/index.ts
CHANGED
|
@@ -31,7 +31,9 @@ export const BlogTheme: Theme = {
|
|
|
31
31
|
DefaultTheme.enhanceApp(ctx)
|
|
32
32
|
ctx.app.component('TimelinePage', TimelinePage)
|
|
33
33
|
ctx.app.component('UserWorksPage', UserWorksPage)
|
|
34
|
-
ctx.app.component('Mermaid'
|
|
34
|
+
if (!ctx.app.component('Mermaid')) {
|
|
35
|
+
ctx.app.component('Mermaid', Mermaid as any)
|
|
36
|
+
}
|
|
35
37
|
}
|
|
36
38
|
}
|
|
37
39
|
|
|
@@ -172,3 +172,8 @@ export function getImageUrl(
|
|
|
172
172
|
} // 如果 ThemeableImage 类型不是上述情况,则返回空字符串
|
|
173
173
|
return ''
|
|
174
174
|
}
|
|
175
|
+
|
|
176
|
+
export function wrapperCleanUrls(cleanUrls: boolean, route: string) {
|
|
177
|
+
const tempUrl = route.replace(/\.html$/, '')
|
|
178
|
+
return cleanUrls ? tempUrl : `${tempUrl}.html`
|
|
179
|
+
}
|
|
@@ -1,419 +0,0 @@
|
|
|
1
|
-
<script lang="ts" setup>
|
|
2
|
-
// @ts-nocheck
|
|
3
|
-
import { computed, nextTick, onBeforeMount, onMounted, ref, watch } from 'vue'
|
|
4
|
-
import { Command } from 'vue-command-palette'
|
|
5
|
-
import { useRoute, useRouter, withBase } from 'vitepress'
|
|
6
|
-
import { useMagicKeys, useWindowSize } from '@vueuse/core'
|
|
7
|
-
import { chineseSearchOptimize, formatDate } from '../utils/client'
|
|
8
|
-
import { useArticles, useBlogConfig } from '../composables/config/blog'
|
|
9
|
-
import type { Theme } from '../composables/config'
|
|
10
|
-
import LogoPagefind from './LogoPagefind.vue'
|
|
11
|
-
|
|
12
|
-
const searchResult = ref<Theme.PageData[]>([])
|
|
13
|
-
|
|
14
|
-
const windowSize = useWindowSize()
|
|
15
|
-
|
|
16
|
-
const isMinimized = computed(() => windowSize.width.value < 760)
|
|
17
|
-
const flexValue = computed(() => (isMinimized.value ? 0 : 1))
|
|
18
|
-
const { search: searchConfig } = useBlogConfig()
|
|
19
|
-
|
|
20
|
-
const headingText = computed(() => {
|
|
21
|
-
return searchConfig?.heading
|
|
22
|
-
? searchConfig.heading.replace(
|
|
23
|
-
/\{\{searchResult\}\}/,
|
|
24
|
-
searchResult.value.length
|
|
25
|
-
)
|
|
26
|
-
: `共: ${searchResult.value.length} 个搜索结果`
|
|
27
|
-
})
|
|
28
|
-
const openSearch = computed(() =>
|
|
29
|
-
searchConfig instanceof Object
|
|
30
|
-
? searchConfig.mode ?? true
|
|
31
|
-
: searchConfig ?? true
|
|
32
|
-
)
|
|
33
|
-
|
|
34
|
-
function addInlineScript() {
|
|
35
|
-
const scriptText = `import('${withBase('/_pagefind/pagefind.js')}')
|
|
36
|
-
.then((module) => {
|
|
37
|
-
window.__pagefind__ = module
|
|
38
|
-
})
|
|
39
|
-
.catch(() => {
|
|
40
|
-
console.log('not load /_pagefind/pagefind.js')
|
|
41
|
-
})`
|
|
42
|
-
const inlineScript = document.createElement('script')
|
|
43
|
-
inlineScript.innerHTML = scriptText
|
|
44
|
-
document.head.appendChild(inlineScript)
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
onBeforeMount(() => {
|
|
48
|
-
if (openSearch.value === 'pagefind') {
|
|
49
|
-
addInlineScript()
|
|
50
|
-
}
|
|
51
|
-
})
|
|
52
|
-
|
|
53
|
-
const metaKey = ref('')
|
|
54
|
-
onMounted(() => {
|
|
55
|
-
metaKey.value = /(Mac|iPhone|iPod|iPad)/i.test(navigator?.platform)
|
|
56
|
-
? '⌘'
|
|
57
|
-
: 'Ctrl'
|
|
58
|
-
})
|
|
59
|
-
const searchModal = ref(false)
|
|
60
|
-
const searchWords = ref('')
|
|
61
|
-
const docs = useArticles()
|
|
62
|
-
const docsMap = computed(() => {
|
|
63
|
-
const map = new Map<string, Theme.PageData.meta>()
|
|
64
|
-
docs.value.forEach((doc) => {
|
|
65
|
-
map.set(withBase(doc.route.replace(/index$/, '')), doc.meta)
|
|
66
|
-
})
|
|
67
|
-
return map
|
|
68
|
-
})
|
|
69
|
-
|
|
70
|
-
const keys = useMagicKeys({
|
|
71
|
-
passive: false,
|
|
72
|
-
onEventFired(e) {
|
|
73
|
-
if (e.ctrlKey && e.key === 'k' && e.type === 'keydown')
|
|
74
|
-
e.preventDefault()
|
|
75
|
-
}
|
|
76
|
-
})
|
|
77
|
-
const CmdK = keys['Meta+K']
|
|
78
|
-
const CtrlK = keys['Ctrl+K']
|
|
79
|
-
// eslint-disable-next-line dot-notation, prefer-destructuring
|
|
80
|
-
const Escape = keys['Escape']
|
|
81
|
-
|
|
82
|
-
watch(CtrlK, (v) => {
|
|
83
|
-
if (v) {
|
|
84
|
-
searchModal.value = true
|
|
85
|
-
}
|
|
86
|
-
})
|
|
87
|
-
watch(CmdK, (v) => {
|
|
88
|
-
if (v) {
|
|
89
|
-
searchModal.value = true
|
|
90
|
-
}
|
|
91
|
-
})
|
|
92
|
-
watch(Escape, (v) => {
|
|
93
|
-
if (v) {
|
|
94
|
-
searchModal.value = false
|
|
95
|
-
}
|
|
96
|
-
})
|
|
97
|
-
|
|
98
|
-
function inlineSearch() {
|
|
99
|
-
if (!searchWords.value) {
|
|
100
|
-
searchResult.value = []
|
|
101
|
-
return
|
|
102
|
-
}
|
|
103
|
-
searchResult.value = docs.value
|
|
104
|
-
.filter(v =>
|
|
105
|
-
`${v.meta.description}${v.meta.title}`.includes(searchWords.value)
|
|
106
|
-
)
|
|
107
|
-
.map((v) => {
|
|
108
|
-
return {
|
|
109
|
-
...v,
|
|
110
|
-
meta: {
|
|
111
|
-
...v.meta,
|
|
112
|
-
description:
|
|
113
|
-
v.meta?.description?.replace(
|
|
114
|
-
new RegExp(`(${searchWords.value})`, 'g'),
|
|
115
|
-
'<mark>$1</mark>'
|
|
116
|
-
) || ''
|
|
117
|
-
}
|
|
118
|
-
}
|
|
119
|
-
})
|
|
120
|
-
searchResult.value.sort((a, b) => {
|
|
121
|
-
return +new Date(b.meta.date) - +new Date(a.meta.date)
|
|
122
|
-
})
|
|
123
|
-
}
|
|
124
|
-
|
|
125
|
-
watch(
|
|
126
|
-
() => searchWords.value,
|
|
127
|
-
async () => {
|
|
128
|
-
if (openSearch.value === 'pagefind') {
|
|
129
|
-
// dev-server兜底
|
|
130
|
-
// @ts-expect-error
|
|
131
|
-
if (!window?.__pagefind__?.search) {
|
|
132
|
-
inlineSearch()
|
|
133
|
-
}
|
|
134
|
-
else {
|
|
135
|
-
// @ts-expect-error
|
|
136
|
-
await window?.__pagefind__
|
|
137
|
-
?.search?.(chineseSearchOptimize(searchWords.value))
|
|
138
|
-
.then(async (search: any) => {
|
|
139
|
-
const result = await Promise.all(
|
|
140
|
-
search.results.map((v: any) => v.data())
|
|
141
|
-
)
|
|
142
|
-
searchResult.value = result.map((result) => {
|
|
143
|
-
const { url, excerpt } = result
|
|
144
|
-
const targetRoute = url.replace(/\.html$/, '')
|
|
145
|
-
const meta = docsMap.value.get(targetRoute)
|
|
146
|
-
if (meta) {
|
|
147
|
-
return {
|
|
148
|
-
route: targetRoute,
|
|
149
|
-
meta: {
|
|
150
|
-
...meta,
|
|
151
|
-
description: excerpt
|
|
152
|
-
}
|
|
153
|
-
}
|
|
154
|
-
}
|
|
155
|
-
return {
|
|
156
|
-
route: url,
|
|
157
|
-
meta: {
|
|
158
|
-
...result.meta,
|
|
159
|
-
description: excerpt
|
|
160
|
-
}
|
|
161
|
-
}
|
|
162
|
-
})
|
|
163
|
-
})
|
|
164
|
-
}
|
|
165
|
-
}
|
|
166
|
-
else {
|
|
167
|
-
inlineSearch()
|
|
168
|
-
}
|
|
169
|
-
nextTick(() => {
|
|
170
|
-
// hack 原组件实现
|
|
171
|
-
document.querySelectorAll('div[aria-disabled="true"]').forEach((v) => {
|
|
172
|
-
v.setAttribute('aria-disabled', 'false')
|
|
173
|
-
})
|
|
174
|
-
})
|
|
175
|
-
}
|
|
176
|
-
)
|
|
177
|
-
|
|
178
|
-
function handleClickMask(e: any) {
|
|
179
|
-
if (e.target === e.currentTarget) {
|
|
180
|
-
searchModal.value = false
|
|
181
|
-
}
|
|
182
|
-
}
|
|
183
|
-
watch(
|
|
184
|
-
() => searchModal.value,
|
|
185
|
-
(newValue) => {
|
|
186
|
-
if (newValue) {
|
|
187
|
-
nextTick(() => {
|
|
188
|
-
document
|
|
189
|
-
.querySelector('div[command-dialog-mask]')
|
|
190
|
-
?.addEventListener('click', handleClickMask)
|
|
191
|
-
})
|
|
192
|
-
}
|
|
193
|
-
else {
|
|
194
|
-
document
|
|
195
|
-
.querySelector('div[command-dialog-mask]')
|
|
196
|
-
?.removeEventListener('click', handleClickMask)
|
|
197
|
-
}
|
|
198
|
-
}
|
|
199
|
-
)
|
|
200
|
-
|
|
201
|
-
// 搜索结果分页?
|
|
202
|
-
// const pageSize = ref(6)
|
|
203
|
-
// const currentPage = ref(0)
|
|
204
|
-
// const showSearchResult = computed(() => {
|
|
205
|
-
// // 合法性处理
|
|
206
|
-
// const pageIdx =
|
|
207
|
-
// currentPage.value % Math.ceil(searchResult.value.length / pageSize.value)
|
|
208
|
-
// const startIdx = pageIdx * pageSize.value
|
|
209
|
-
// return searchResult.value.slice(startIdx, startIdx + pageSize.value)
|
|
210
|
-
// })
|
|
211
|
-
|
|
212
|
-
const router = useRouter()
|
|
213
|
-
const route = useRoute()
|
|
214
|
-
function handleSelect(target: any) {
|
|
215
|
-
searchModal.value = false
|
|
216
|
-
if (!route.path.startsWith(target.value)) {
|
|
217
|
-
// searchWords.value = ''
|
|
218
|
-
router.go(target.value)
|
|
219
|
-
}
|
|
220
|
-
}
|
|
221
|
-
</script>
|
|
222
|
-
|
|
223
|
-
<template>
|
|
224
|
-
<div v-if="openSearch" class="blog-search" data-pagefind-ignore="all">
|
|
225
|
-
<div class="nav-search-btn-wait" @click="searchModal = true">
|
|
226
|
-
<svg width="14" height="14" viewBox="0 0 20 20">
|
|
227
|
-
<path
|
|
228
|
-
d="M14.386 14.386l4.0877 4.0877-4.0877-4.0877c-2.9418 2.9419-7.7115 2.9419-10.6533 0-2.9419-2.9418-2.9419-7.7115 0-10.6533 2.9418-2.9419 7.7115-2.9419 10.6533 0 2.9419 2.9418 2.9419 7.7115 0 10.6533z"
|
|
229
|
-
stroke="currentColor"
|
|
230
|
-
fill="none"
|
|
231
|
-
fill-rule="evenodd"
|
|
232
|
-
stroke-linecap="round"
|
|
233
|
-
stroke-linejoin="round"
|
|
234
|
-
/>
|
|
235
|
-
</svg>
|
|
236
|
-
<span v-if="!isMinimized" class="search-tip">{{
|
|
237
|
-
searchConfig?.btnPlaceholder || '搜索'
|
|
238
|
-
}}</span>
|
|
239
|
-
<span v-if="!isMinimized" class="metaKey"> {{ metaKey }} K </span>
|
|
240
|
-
</div>
|
|
241
|
-
<Command.Dialog :visible="searchModal" theme="algolia">
|
|
242
|
-
<template #header>
|
|
243
|
-
<Command.Input
|
|
244
|
-
v-model:value="searchWords"
|
|
245
|
-
:placeholder="searchConfig?.placeholder || '请输入要搜素的内容'"
|
|
246
|
-
/>
|
|
247
|
-
</template>
|
|
248
|
-
<template #body>
|
|
249
|
-
<div class="search-dialog">
|
|
250
|
-
<Command.List>
|
|
251
|
-
<Command.Empty v-if="!searchResult.length">
|
|
252
|
-
{{
|
|
253
|
-
searchConfig?.emptyText || 'No results found.'
|
|
254
|
-
}}
|
|
255
|
-
</Command.Empty>
|
|
256
|
-
<Command.Group v-else :heading="headingText">
|
|
257
|
-
<Command.Item
|
|
258
|
-
v-for="item in searchResult"
|
|
259
|
-
:key="item.route"
|
|
260
|
-
:data-value="item.route"
|
|
261
|
-
@select="handleSelect"
|
|
262
|
-
>
|
|
263
|
-
<div class="link">
|
|
264
|
-
<div class="title">
|
|
265
|
-
<span>{{ item.meta.title }}</span>
|
|
266
|
-
<span class="date">
|
|
267
|
-
{{ formatDate(item.meta.date, 'yyyy-MM-dd') }}</span>
|
|
268
|
-
</div>
|
|
269
|
-
<div class="des" v-html="item.meta.description" />
|
|
270
|
-
</div>
|
|
271
|
-
</Command.Item>
|
|
272
|
-
</Command.Group>
|
|
273
|
-
</Command.List>
|
|
274
|
-
</div>
|
|
275
|
-
</template>
|
|
276
|
-
<template v-if="searchResult.length" #footer>
|
|
277
|
-
<div class="command-palette-logo">
|
|
278
|
-
<a
|
|
279
|
-
v-if="openSearch === 'pagefind'"
|
|
280
|
-
href="https://github.com/cloudcannon/pagefind"
|
|
281
|
-
target="_blank"
|
|
282
|
-
rel="noopener noreferrer"
|
|
283
|
-
>
|
|
284
|
-
<span class="command-palette-Label">Search by</span>
|
|
285
|
-
<LogoPagefind style="width: 77px" />
|
|
286
|
-
</a>
|
|
287
|
-
</div>
|
|
288
|
-
<ul class="command-palette-commands">
|
|
289
|
-
<li>
|
|
290
|
-
<kbd class="command-palette-commands-key"><svg width="15" height="15" aria-label="Enter key" role="img">
|
|
291
|
-
<g
|
|
292
|
-
fill="none"
|
|
293
|
-
stroke="currentColor"
|
|
294
|
-
stroke-linecap="round"
|
|
295
|
-
stroke-linejoin="round"
|
|
296
|
-
stroke-width="1.2"
|
|
297
|
-
>
|
|
298
|
-
<path
|
|
299
|
-
d="M12 3.53088v3c0 1-1 2-2 2H4M7 11.53088l-3-3 3-3"
|
|
300
|
-
/>
|
|
301
|
-
</g></svg></kbd><span class="command-palette-Label">to select</span>
|
|
302
|
-
</li>
|
|
303
|
-
<li>
|
|
304
|
-
<kbd class="command-palette-commands-key"><svg width="15" height="15" aria-label="Arrow down" role="img">
|
|
305
|
-
<g
|
|
306
|
-
fill="none"
|
|
307
|
-
stroke="currentColor"
|
|
308
|
-
stroke-linecap="round"
|
|
309
|
-
stroke-linejoin="round"
|
|
310
|
-
stroke-width="1.2"
|
|
311
|
-
>
|
|
312
|
-
<path d="M7.5 3.5v8M10.5 8.5l-3 3-3-3" />
|
|
313
|
-
</g></svg></kbd><kbd class="command-palette-commands-key"><svg width="15" height="15" aria-label="Arrow up" role="img">
|
|
314
|
-
<g
|
|
315
|
-
fill="none"
|
|
316
|
-
stroke="currentColor"
|
|
317
|
-
stroke-linecap="round"
|
|
318
|
-
stroke-linejoin="round"
|
|
319
|
-
stroke-width="1.2"
|
|
320
|
-
>
|
|
321
|
-
<path d="M7.5 11.5v-8M10.5 6.5l-3-3-3 3" />
|
|
322
|
-
</g></svg></kbd><span class="command-palette-Label">to navigate</span>
|
|
323
|
-
</li>
|
|
324
|
-
<li>
|
|
325
|
-
<kbd class="command-palette-commands-key"><svg width="15" height="15" aria-label="Escape key" role="img">
|
|
326
|
-
<g
|
|
327
|
-
fill="none"
|
|
328
|
-
stroke="currentColor"
|
|
329
|
-
stroke-linecap="round"
|
|
330
|
-
stroke-linejoin="round"
|
|
331
|
-
stroke-width="1.2"
|
|
332
|
-
>
|
|
333
|
-
<path
|
|
334
|
-
d="M13.6167 8.936c-.1065.3583-.6883.962-1.4875.962-.7993 0-1.653-.9165-1.653-2.1258v-.5678c0-1.2548.7896-2.1016 1.653-2.1016.8634 0 1.3601.4778 1.4875 1.0724M9 6c-.1352-.4735-.7506-.9219-1.46-.8972-.7092.0246-1.344.57-1.344 1.2166s.4198.8812 1.3445.9805C8.465 7.3992 8.968 7.9337 9 8.5c.032.5663-.454 1.398-1.4595 1.398C6.6593 9.898 6 9 5.963 8.4851m-1.4748.5368c-.2635.5941-.8099.876-1.5443.876s-1.7073-.6248-1.7073-2.204v-.4603c0-1.0416.721-2.131 1.7073-2.131.9864 0 1.6425 1.031 1.5443 2.2492h-2.956"
|
|
335
|
-
/>
|
|
336
|
-
</g></svg></kbd><span class="command-palette-Label">to close</span>
|
|
337
|
-
</li>
|
|
338
|
-
</ul>
|
|
339
|
-
</template>
|
|
340
|
-
</Command.Dialog>
|
|
341
|
-
</div>
|
|
342
|
-
</template>
|
|
343
|
-
|
|
344
|
-
<style lang="scss" scoped>
|
|
345
|
-
.blog-search {
|
|
346
|
-
flex: v-bind(flexValue);
|
|
347
|
-
display: flex;
|
|
348
|
-
padding-left: 32px;
|
|
349
|
-
.nav-search-btn-wait {
|
|
350
|
-
cursor: pointer;
|
|
351
|
-
display: flex;
|
|
352
|
-
align-items: center;
|
|
353
|
-
justify-content: center;
|
|
354
|
-
padding: 6px;
|
|
355
|
-
box-sizing: border-box;
|
|
356
|
-
border: 1px solid transparent;
|
|
357
|
-
border-radius: 6px;
|
|
358
|
-
transition: .2s border;
|
|
359
|
-
|
|
360
|
-
.metaKey {
|
|
361
|
-
margin-left: 10px;
|
|
362
|
-
font-size: 12px;
|
|
363
|
-
}
|
|
364
|
-
|
|
365
|
-
&:hover {
|
|
366
|
-
border: 1px solid var(--vp-c-brand-1);
|
|
367
|
-
border-radius: 6px;
|
|
368
|
-
}
|
|
369
|
-
|
|
370
|
-
.search-tip {
|
|
371
|
-
color: #909399;
|
|
372
|
-
font-size: 12px;
|
|
373
|
-
padding-left: 10px;
|
|
374
|
-
}
|
|
375
|
-
}
|
|
376
|
-
}
|
|
377
|
-
</style>
|
|
378
|
-
|
|
379
|
-
<style lang="scss">
|
|
380
|
-
@import '../styles/scss/global.scss';
|
|
381
|
-
@import '../styles/scss/algolia.scss';
|
|
382
|
-
|
|
383
|
-
div[command-group] {
|
|
384
|
-
display: block !important;
|
|
385
|
-
}
|
|
386
|
-
div[command-item] {
|
|
387
|
-
display: flex !important;
|
|
388
|
-
}
|
|
389
|
-
.search-dialog {
|
|
390
|
-
div[command-item] > div.link {
|
|
391
|
-
width: 100%;
|
|
392
|
-
}
|
|
393
|
-
div[command-item] .title {
|
|
394
|
-
display: flex;
|
|
395
|
-
justify-content: space-between;
|
|
396
|
-
}
|
|
397
|
-
|
|
398
|
-
div[command-item] .des {
|
|
399
|
-
text-overflow: ellipsis;
|
|
400
|
-
overflow: hidden;
|
|
401
|
-
word-break: keep-all;
|
|
402
|
-
white-space: nowrap;
|
|
403
|
-
}
|
|
404
|
-
|
|
405
|
-
div[command-item] .date {
|
|
406
|
-
min-width: 80px;
|
|
407
|
-
}
|
|
408
|
-
div[command-item] mark {
|
|
409
|
-
background: none;
|
|
410
|
-
color: var(--vp-c-brand-1);
|
|
411
|
-
}
|
|
412
|
-
|
|
413
|
-
div[command-item][aria-selected='true'] mark,
|
|
414
|
-
div[command-item]:hover mark {
|
|
415
|
-
color: inherit;
|
|
416
|
-
text-decoration: underline;
|
|
417
|
-
}
|
|
418
|
-
}
|
|
419
|
-
</style>
|
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
<template>
|
|
2
|
-
<svg
|
|
3
|
-
width="594"
|
|
4
|
-
height="112"
|
|
5
|
-
viewBox="0 0 594 112"
|
|
6
|
-
fill="none"
|
|
7
|
-
xmlns="http://www.w3.org/2000/svg"
|
|
8
|
-
>
|
|
9
|
-
<path
|
|
10
|
-
d="M147.8 111.2H164V77.5998H164.6C164.6 77.5998 170.6 87.1998 183.2 87.1998C197 87.1998 209.6 74.5998 209.6 56.5998C209.6 38.5998 197 25.9998 183.2 25.9998C170.6 25.9998 164.6 35.5998 164.6 35.5998H164V27.1998H147.8V111.2ZM178.4 72.1998C170 72.1998 163.4 65.5998 163.4 56.5998C163.4 47.5998 170 40.9998 178.4 40.9998C186.8 40.9998 193.4 47.5998 193.4 56.5998C193.4 65.5998 186.8 72.1998 178.4 72.1998Z"
|
|
11
|
-
fill="black"
|
|
12
|
-
/>
|
|
13
|
-
<path
|
|
14
|
-
d="M230.628 87.1998C242.028 87.1998 248.028 78.7998 248.028 78.7998H248.628V85.9998C252.228 85.9998 264.828 85.9998 264.828 85.9998V49.3998C264.828 36.1998 254.628 25.9998 239.628 25.9998C224.028 25.9998 215.628 37.3998 215.628 37.3998L225.228 46.9998C225.228 46.9998 230.028 40.3998 238.428 40.3998C244.428 40.3998 248.028 43.9998 248.628 48.1998L230.028 51.5598C219.228 53.4798 212.628 60.7998 212.628 70.3998C212.628 79.9998 219.828 87.1998 230.628 87.1998ZM236.028 73.9998C231.228 73.9998 228.828 71.5998 228.828 67.9998C228.828 64.9998 231.228 62.7198 235.428 61.9998L248.628 59.5998V60.7998C248.628 68.5998 243.228 73.9998 236.028 73.9998Z"
|
|
15
|
-
fill="black"
|
|
16
|
-
/>
|
|
17
|
-
<path
|
|
18
|
-
d="M299.033 111.2C317.633 111.2 330.833 97.9998 330.833 79.9998V27.1998H314.633V35.5998H314.033C314.033 35.5998 308.633 25.9998 296.033 25.9998C282.833 25.9998 270.833 37.9998 270.833 55.3998C270.833 72.7998 282.833 84.7998 296.033 84.7998C308.633 84.7998 314.033 75.1998 314.033 75.1998H314.633V79.9998C314.633 89.5998 308.033 96.1998 299.033 96.1998C289.433 96.1998 283.433 88.9998 283.433 88.9998L273.233 99.1998C273.233 99.1998 281.633 111.2 299.033 111.2ZM300.833 69.7998C293.033 69.7998 287.033 63.7998 287.033 55.3998C287.033 46.9998 293.033 40.9998 300.833 40.9998C308.633 40.9998 314.633 46.9998 314.633 55.3998C314.633 63.7998 308.633 69.7998 300.833 69.7998Z"
|
|
19
|
-
fill="black"
|
|
20
|
-
/>
|
|
21
|
-
<path
|
|
22
|
-
d="M367.986 87.1998C384.186 87.1998 393.186 77.5998 393.186 77.5998L384.786 66.1998C384.786 66.1998 379.386 72.7998 369.186 72.7998C360.186 72.7998 355.386 67.9998 353.586 62.5998H396.186C396.186 62.5998 396.786 59.5998 396.786 55.3998C396.786 39.1998 383.586 25.9998 367.386 25.9998C350.586 25.9998 336.786 39.7998 336.786 56.5998C336.786 73.3998 350.586 87.1998 367.986 87.1998ZM353.586 50.5998C355.386 45.1998 360.186 40.3998 366.786 40.3998C373.386 40.3998 378.186 45.1998 379.986 50.5998H353.586Z"
|
|
23
|
-
fill="black"
|
|
24
|
-
/>
|
|
25
|
-
<path
|
|
26
|
-
d="M406.423 85.9998H422.624V43.3998H444.224V85.9998H460.423V28.3998H422.624V24.7998C422.624 19.3998 425.624 16.3998 430.423 16.3998C433.423 16.3998 435.823 17.5998 435.823 17.5998V2.5998C435.823 2.5998 431.624 0.799805 426.224 0.799805C414.224 0.799805 406.423 8.59981 406.423 22.3998V28.3998H397.423V43.3998H406.423V85.9998ZM452.263 19.3998C457.423 19.3998 461.624 15.1998 461.624 10.3998C461.624 5.59981 457.424 1.3998 452.384 1.3998C447.224 1.3998 443.023 5.59981 443.023 10.3998C443.023 15.1998 447.223 19.3998 452.263 19.3998Z"
|
|
27
|
-
fill="black"
|
|
28
|
-
/>
|
|
29
|
-
<path
|
|
30
|
-
d="M470.652 85.9998H486.852V54.7998C486.852 46.9998 492.252 41.5998 499.452 41.5998C506.052 41.5998 510.252 45.7998 510.252 52.9998V85.9998H526.452V50.5998C526.452 35.5998 516.852 25.9998 504.852 25.9998C493.452 25.9998 487.452 35.5998 487.452 35.5998H486.852V27.1998H470.652V85.9998Z"
|
|
31
|
-
fill="black"
|
|
32
|
-
/>
|
|
33
|
-
<path
|
|
34
|
-
d="M557.819 87.1998C570.419 87.1998 576.419 77.5998 576.419 77.5998H577.019V85.9998H593.219V1.9998H577.019V35.5998H576.419C576.419 35.5998 570.419 25.9998 557.819 25.9998C544.019 25.9998 531.419 38.5998 531.419 56.5998C531.419 74.5998 544.019 87.1998 557.819 87.1998ZM562.619 72.1998C554.219 72.1998 547.619 65.5998 547.619 56.5998C547.619 47.5998 554.219 40.9998 562.619 40.9998C571.019 40.9998 577.619 47.5998 577.619 56.5998C577.619 65.5998 571.019 72.1998 562.619 72.1998Z"
|
|
35
|
-
fill="black"
|
|
36
|
-
/>
|
|
37
|
-
<path
|
|
38
|
-
fill-rule="evenodd"
|
|
39
|
-
clip-rule="evenodd"
|
|
40
|
-
d="M60 96.9999C93.1371 96.9999 120 81.8416 120 63.1428V50.8311H115.91C107.182 38.2198 85.4398 29.2856 60 29.2856C34.5602 29.2856 12.8183 38.2198 4.09026 50.8311H0V63.1428C0 81.8416 26.8629 96.9999 60 96.9999Z"
|
|
41
|
-
fill="black"
|
|
42
|
-
/>
|
|
43
|
-
<path
|
|
44
|
-
d="M116 52C116 59.317 110.727 66.7404 100.454 72.5615C90.3014 78.3149 76.0069 82 60 82C43.9931 82 29.6986 78.3149 19.5456 72.5615C9.2731 66.7404 4 59.317 4 52C4 44.6831 9.2731 37.2596 19.5456 31.4385C29.6986 25.6851 43.9931 22 60 22C76.0069 22 90.3014 25.6851 100.454 31.4385C110.727 37.2596 116 44.6831 116 52Z"
|
|
45
|
-
fill="white"
|
|
46
|
-
stroke="black"
|
|
47
|
-
stroke-width="8"
|
|
48
|
-
/>
|
|
49
|
-
<path
|
|
50
|
-
d="M57.8864 72.0605L87.2817 41.837C88.6253 40.4556 87.43 38.1599 85.5278 38.4684L26.0819 48.1083C23.9864 48.4481 23.794 51.3882 25.8273 51.9982L46.7151 58.2645C47.2181 58.4154 47.6415 58.7581 47.894 59.2185L54.6991 71.6277C55.3457 72.8069 56.9487 73.0246 57.8864 72.0605Z"
|
|
51
|
-
fill="black"
|
|
52
|
-
/>
|
|
53
|
-
<ellipse cx="58" cy="53.5" rx="7" ry="4.5" fill="white" />
|
|
54
|
-
</svg>
|
|
55
|
-
</template>
|