hexo-theme-shokax 0.5.0-dev-0e1579b → 0.5.0-dev-5c5076b
Sign up to get free protection for your applications and to get access to all the features.
- package/README.md +1 -0
- package/UsageRestrictions.md +1 -1
- package/_config.yml +0 -15
- package/layout/_partials/head/head.pug +0 -12
- package/layout/page.pug +4 -0
- package/layout/post.pug +4 -0
- package/package.json +1 -1
- package/source/js/_app/components/comments.ts +0 -2
- package/source/js/_app/components/sidebar.ts +34 -35
- package/source/js/_app/globals/globalVars.ts +0 -3
- package/source/js/_app/globals/handles.ts +9 -9
- package/source/js/_app/globals/themeColor.ts +5 -6
- package/source/js/_app/globals/thirdparty.ts +2 -2
- package/source/js/_app/globals/tools.ts +4 -6
- package/source/js/_app/library/proto.ts +0 -67
- package/source/js/_app/library/vue.ts +6 -7
- package/source/js/_app/page/common.ts +8 -10
- package/source/js/_app/page/fancybox.ts +4 -5
- package/source/js/_app/page/post.ts +42 -44
- package/source/js/_app/page/search.ts +0 -1
- package/source/js/_app/page/tab.ts +8 -9
- package/source/js/_app/pjax/domInit.ts +2 -5
- package/source/js/_app/pjax/siteInit.ts +10 -14
- package/source/js/_app/player.ts +26 -27
- package/toolbox/compiler.mjs +20 -48
- package/source/js/_app/library/dom.ts +0 -28
- package/source/js/_app/library/storage.ts +0 -12
package/README.md
CHANGED
package/UsageRestrictions.md
CHANGED
@@ -16,7 +16,7 @@
|
|
16
16
|
## 处理方式
|
17
17
|
如果您违反了上述使用限制和AGPLv3的任何规定,ShokaX 项目组保留采取以下措施之一或多个的权利:
|
18
18
|
- 发出警告通知并要求立即纠正违规行为;(根据`AGPLv3 八`)
|
19
|
-
- 暂停或终止您对 ShokaX 及其子项目的使用权限并取消
|
19
|
+
- 暂停或终止您对 ShokaX 及其子项目的使用权限并取消AGPLv3授予您的权利;(根据`AGPLv3 八`)
|
20
20
|
- 取消您获取 ShokaX 社区支持和进行协作的权利;(社区管理)
|
21
21
|
- 追究法律责任,包括要求赔偿因违规行为给 ShokaX 项目组造成的损失。(依照相关法律而定)
|
22
22
|
|
package/_config.yml
CHANGED
@@ -343,21 +343,6 @@ search:
|
|
343
343
|
hits:
|
344
344
|
per_page: 10
|
345
345
|
|
346
|
-
# Dependencies: https://github.com/amehime/hexo-renderer-multi-markdown-it
|
347
|
-
pangu: false
|
348
|
-
|
349
|
-
# Quicklink Support
|
350
|
-
# For more information: https://github.com/GoogleChromeLabs/quicklink
|
351
|
-
quicklink:
|
352
|
-
# Custom a time in milliseconds by which the browser must execute prefetching.
|
353
|
-
timeout: 3000
|
354
|
-
# Default (true) will attempt to use the fetch() API if supported (rather than link[rel=prefetch]).
|
355
|
-
priority: true
|
356
|
-
|
357
|
-
# For more flexibility you can add some patterns (RegExp, Function, or Array) to ignores.
|
358
|
-
# See: https://github.com/GoogleChromeLabs/quicklink#custom-ignore-patterns
|
359
|
-
ignores:
|
360
|
-
|
361
346
|
#! ---------------------------------------------------------------
|
362
347
|
#! DO NOT EDIT THE FOLLOWING `vendors` SETTINGS
|
363
348
|
#! UNLESS YOU KNOW WHAT YOU ARE DOING
|
@@ -44,19 +44,7 @@ if fontConfig
|
|
44
44
|
!= preloadjs()
|
45
45
|
!= load_async_css()
|
46
46
|
|
47
|
-
// 临时处理
|
48
|
-
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/fancybox/3.5.7/jquery.fancybox.min.css")
|
49
|
-
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/justifiedGallery/3.8.1/css/justifiedGallery.min.css")
|
50
|
-
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/KaTeX/0.16.9/katex.min.css")
|
51
|
-
//link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/KaTeX/0.16.9/katex.min.css")
|
52
47
|
if theme.experiments.cloudflarePatch
|
53
48
|
!= _js('cf-patch.js')
|
54
49
|
|
55
50
|
include pwa.pug
|
56
|
-
|
57
|
-
- var qw = theme?.qweather?.enable
|
58
|
-
if qw
|
59
|
-
style.
|
60
|
-
img[data-v-7d48daab] {
|
61
|
-
max-width: 2em !important;
|
62
|
-
}
|
package/layout/page.pug
CHANGED
@@ -4,6 +4,10 @@ include _mixin/comment.pug
|
|
4
4
|
|
5
5
|
block head
|
6
6
|
!= _css('post.css')
|
7
|
+
// 临时处理
|
8
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/fancybox/3.5.7/jquery.fancybox.min.css")
|
9
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/justifiedGallery/3.8.1/css/justifiedGallery.min.css")
|
10
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/KaTeX/0.16.9/katex.min.css")
|
7
11
|
|
8
12
|
block title
|
9
13
|
if page.type === 'categories'
|
package/layout/post.pug
CHANGED
@@ -6,6 +6,10 @@ include _mixin/postmeta.pug
|
|
6
6
|
block head
|
7
7
|
!= _css('post.css')
|
8
8
|
!= _css('mermaid.css')
|
9
|
+
// 临时处理
|
10
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/fancybox/3.5.7/jquery.fancybox.min.css")
|
11
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/justifiedGallery/3.8.1/css/justifiedGallery.min.css")
|
12
|
+
link(rel="stylesheet" media="none" onload="this.media='all'" href="https://s4.zstatic.net/ajax/libs/KaTeX/0.16.9/katex.min.css")
|
9
13
|
|
10
14
|
block title
|
11
15
|
- var page_title = page.title
|
package/package.json
CHANGED
@@ -23,7 +23,6 @@ export const walineComment = function () {
|
|
23
23
|
}
|
24
24
|
|
25
25
|
export const walinePageview = function () {
|
26
|
-
// TODO waline 上游此模块存在问题
|
27
26
|
pageviewCount({
|
28
27
|
serverURL: CONFIG.waline.serverURL,
|
29
28
|
path: window.location.pathname
|
@@ -37,7 +36,6 @@ export const walineRecentComments = async function () {
|
|
37
36
|
serverURL: CONFIG.waline.serverURL.replace(/\/+$/, ''),
|
38
37
|
count: 10
|
39
38
|
})
|
40
|
-
// TODO 疑似 waline API 返回格式与文档不一致,需要确认是否为上游问题
|
41
39
|
// @ts-ignore
|
42
40
|
comments.data.forEach(function (item) {
|
43
41
|
let cText = (item.orig.length > 50) ? item.orig.substring(0, 50) + '...' : item.orig
|
@@ -3,14 +3,12 @@
|
|
3
3
|
import { CONFIG, Container, diffY, menuToggle, showContents, sideBar } from '../globals/globalVars'
|
4
4
|
import { clipBoard } from '../globals/tools'
|
5
5
|
import { pageScroll, transition } from '../library/anime'
|
6
|
-
import {
|
7
|
-
import initProto, { getHeight, setDisplay } from '../library/proto'
|
6
|
+
import { getHeight, setDisplay } from '../library/proto'
|
8
7
|
|
9
|
-
initProto()
|
10
8
|
export const sideBarToggleHandle = (event:Event, force?:number) => {
|
11
|
-
if (sideBar.
|
12
|
-
sideBar.
|
13
|
-
menuToggle.
|
9
|
+
if (sideBar.classList.contains('on')) {
|
10
|
+
sideBar.classList.remove('on')
|
11
|
+
menuToggle.classList.remove('close')
|
14
12
|
if (force) {
|
15
13
|
// @ts-ignore
|
16
14
|
// noinspection JSConstantReassignment
|
@@ -25,8 +23,8 @@ export const sideBarToggleHandle = (event:Event, force?:number) => {
|
|
25
23
|
sideBar.style = ''
|
26
24
|
} else {
|
27
25
|
transition(sideBar, 'slideRightIn', () => {
|
28
|
-
sideBar.
|
29
|
-
menuToggle.
|
26
|
+
sideBar.classList.add('on')
|
27
|
+
menuToggle.classList.add('close')
|
30
28
|
})
|
31
29
|
}
|
32
30
|
}
|
@@ -61,29 +59,29 @@ export const sideBarTab = () => {
|
|
61
59
|
const text = document.createTextNode(element.getAttribute('data-title'))
|
62
60
|
span.appendChild(text)
|
63
61
|
tab.appendChild(span)
|
64
|
-
tab.
|
62
|
+
tab.classList.add(item + ' item')
|
65
63
|
|
66
64
|
if (active) {
|
67
|
-
element.
|
68
|
-
tab.
|
65
|
+
element.classList.add(active)
|
66
|
+
tab.classList.add(active)
|
69
67
|
} else {
|
70
|
-
element.
|
68
|
+
element.classList.remove('active')
|
71
69
|
}
|
72
70
|
tab.addEventListener('click', (event) => {
|
73
71
|
const target = event.currentTarget as HTMLElement
|
74
|
-
if (target.
|
72
|
+
if (target.classList.contains('active')) return
|
75
73
|
|
76
|
-
sideBar.
|
77
|
-
element.
|
74
|
+
sideBar.querySelectorAll('.tab .item').forEach((element) => {
|
75
|
+
element.classList.remove('active')
|
78
76
|
})
|
79
77
|
|
80
|
-
sideBar.
|
81
|
-
element.
|
78
|
+
sideBar.querySelectorAll('.panel').forEach((element) => {
|
79
|
+
element.classList.remove('active')
|
82
80
|
})
|
83
81
|
|
84
|
-
sideBar.querySelector('.panel.' + target.className.replace(' item', '')).
|
82
|
+
sideBar.querySelector('.panel.' + target.className.replace(' item', '')).classList.add('active')
|
85
83
|
|
86
|
-
target.
|
84
|
+
target.classList.add('active')
|
87
85
|
})
|
88
86
|
|
89
87
|
list.appendChild(tab)
|
@@ -104,39 +102,39 @@ export const sidebarTOC = () => {
|
|
104
102
|
|
105
103
|
if (!target) return
|
106
104
|
|
107
|
-
if (target.
|
105
|
+
if (target.classList.contains('current')) {
|
108
106
|
return
|
109
107
|
}
|
110
108
|
|
111
|
-
|
112
|
-
element && element.
|
109
|
+
document.querySelectorAll('.toc .active').forEach((element) => {
|
110
|
+
element && element.classList.remove('active current')
|
113
111
|
})
|
114
112
|
|
115
113
|
sections.forEach((element) => {
|
116
|
-
element && element.
|
114
|
+
element && element.classList.remove('active')
|
117
115
|
})
|
118
116
|
|
119
|
-
target.
|
120
|
-
sections[index] && sections[index].
|
117
|
+
target.classList.add('active current')
|
118
|
+
sections[index] && sections[index].classList.add('active')
|
121
119
|
|
122
120
|
let parent = <Element> target.parentNode
|
123
121
|
|
124
122
|
while (!parent.matches('.contents')) {
|
125
123
|
if (parent.matches('li')) {
|
126
|
-
parent.
|
124
|
+
parent.classList.add('active')
|
127
125
|
const t = document.getElementById(decodeURIComponent(parent.querySelector('a.toc-link').getAttribute('href').replace('#', '')))
|
128
126
|
if (t) {
|
129
|
-
t.
|
127
|
+
t.classList.add('active')
|
130
128
|
}
|
131
129
|
}
|
132
130
|
parent = <Element> parent.parentNode
|
133
131
|
}
|
134
132
|
// Scrolling to center active TOC element if TOC content is taller than viewport.
|
135
|
-
if (getComputedStyle(sideBar).display !== 'none' && tocElement.
|
133
|
+
if (getComputedStyle(sideBar).display !== 'none' && tocElement.classList.contains('active')) {
|
136
134
|
pageScroll((tocElement as HTMLElement), target.offsetTop - ((tocElement as HTMLElement).offsetHeight / 4))
|
137
135
|
}
|
138
136
|
}
|
139
|
-
const navItems =
|
137
|
+
const navItems = document.querySelectorAll<HTMLElement>('.contents li')
|
140
138
|
|
141
139
|
if (navItems.length < 1) {
|
142
140
|
return
|
@@ -222,18 +220,19 @@ export const goToCommentHandle = () => {
|
|
222
220
|
}
|
223
221
|
|
224
222
|
export const menuActive = () => {
|
225
|
-
|
223
|
+
document.querySelectorAll('.menu .item:not(.title)').forEach((element) => {
|
226
224
|
const target = <HTMLAnchorElement> element.querySelector('a[href]')
|
227
|
-
const parentItem = element.parentNode.parentNode
|
225
|
+
const parentItem = element.parentNode.parentNode as HTMLElement
|
228
226
|
if (!target) return
|
229
227
|
const isSamePath = target.pathname === location.pathname || target.pathname === location.pathname.replace('index.html', '')
|
230
228
|
const isSubPath = !CONFIG.root.startsWith(target.pathname) && location.pathname.startsWith(target.pathname)
|
231
229
|
const active = !target.onclick && target.hostname === location.hostname && (isSamePath || isSubPath)
|
232
|
-
element.
|
233
|
-
if (element.parentNode.querySelector('.active') && parentItem.
|
234
|
-
parentItem.
|
230
|
+
element.classList.toggle('active', active)
|
231
|
+
if (element.parentNode.querySelector('.active') && parentItem.classList.contains('dropdown')) {
|
232
|
+
parentItem.classList.remove('active')
|
233
|
+
parentItem.classList.add('expand')
|
235
234
|
} else {
|
236
|
-
parentItem.
|
235
|
+
parentItem.classList.remove('expand')
|
237
236
|
}
|
238
237
|
})
|
239
238
|
}
|
@@ -1,7 +1,4 @@
|
|
1
|
-
import initProto from '../library/proto'
|
2
|
-
|
3
1
|
export const CONFIG = shokax_CONFIG
|
4
|
-
initProto()
|
5
2
|
export const statics = CONFIG.statics.indexOf('//') > 0 ? CONFIG.statics : CONFIG.root
|
6
3
|
export const scrollAction: { x: number, y: number } = { x: 0, y: 0 }
|
7
4
|
export let diffY = 0
|
@@ -63,12 +63,12 @@ export const scrollHandle = () => {
|
|
63
63
|
}
|
64
64
|
|
65
65
|
// 控制导航栏的显示隐藏
|
66
|
-
siteNav.
|
66
|
+
siteNav.classList.toggle('show', SHOW)
|
67
67
|
// 控制网站 logo 的显示隐藏
|
68
|
-
toolBtn.
|
68
|
+
toolBtn.classList.toggle('affix', startScroll)
|
69
69
|
// 控制侧边栏的显示隐藏,当滚动高度大于 headerHight 且窗口宽度大于 991px 时显示
|
70
|
-
siteBrand.
|
71
|
-
sideBar.
|
70
|
+
siteBrand.classList.toggle('affix', startScroll)
|
71
|
+
sideBar.classList.toggle('affix', window.scrollY > headerHight && document.body.offsetWidth >= 991)
|
72
72
|
// 初始化滚动时导航栏的显示方向
|
73
73
|
if (typeof scrollAction.y === 'undefined') {
|
74
74
|
scrollAction.y = window.scrollY
|
@@ -77,11 +77,11 @@ export const scrollHandle = () => {
|
|
77
77
|
|
78
78
|
// 控制滑动时导航栏显示
|
79
79
|
if (diffY < 0) {
|
80
|
-
siteNav.
|
81
|
-
siteNav.
|
80
|
+
siteNav.classList.remove('up')
|
81
|
+
siteNav.classList.toggle('down', SHOW)
|
82
82
|
} else if (diffY > 0) {
|
83
|
-
siteNav.
|
84
|
-
siteNav.
|
83
|
+
siteNav.classList.remove('down')
|
84
|
+
siteNav.classList.toggle('up', SHOW)
|
85
85
|
} else { /* empty */ }
|
86
86
|
scrollAction.y = window.scrollY
|
87
87
|
// 计算滚动百分比
|
@@ -91,7 +91,7 @@ export const scrollHandle = () => {
|
|
91
91
|
backToTop.querySelector('span').innerText = scrollPercent
|
92
92
|
}
|
93
93
|
// 更新百分比进度条的宽度
|
94
|
-
if (document.getElementById('sidebar').
|
94
|
+
if (document.getElementById('sidebar').classList.contains('affix') || document.getElementById('sidebar').classList.contains('on')) {
|
95
95
|
setWidth(document.querySelector('.percent'), scrollPercent)
|
96
96
|
}
|
97
97
|
}
|
@@ -1,4 +1,3 @@
|
|
1
|
-
import { $storage } from '../library/storage'
|
2
1
|
import { CONFIG, HTML } from './globalVars'
|
3
2
|
|
4
3
|
/**
|
@@ -8,12 +7,12 @@ export const changeTheme = (type?: string) => {
|
|
8
7
|
const btn = document.querySelector('.theme .ic')
|
9
8
|
if (type === 'dark') {
|
10
9
|
HTML.setAttribute('data-theme', type)
|
11
|
-
btn.
|
12
|
-
btn.
|
10
|
+
btn.classList.remove('i-sun')
|
11
|
+
btn.classList.add('i-moon')
|
13
12
|
} else {
|
14
13
|
HTML.removeAttribute('data-theme')
|
15
|
-
btn.
|
16
|
-
btn.
|
14
|
+
btn.classList.remove('i-moon')
|
15
|
+
btn.classList.add('i-sun')
|
17
16
|
}
|
18
17
|
}
|
19
18
|
|
@@ -52,7 +51,7 @@ export const themeColorListener = () => {
|
|
52
51
|
}
|
53
52
|
})
|
54
53
|
|
55
|
-
const t =
|
54
|
+
const t = localStorage.getItem('theme')
|
56
55
|
if (t) {
|
57
56
|
changeTheme(t)
|
58
57
|
} else {
|
@@ -9,7 +9,7 @@ export const Loader = {
|
|
9
9
|
lock: false,
|
10
10
|
show () {
|
11
11
|
clearTimeout(this.timer)
|
12
|
-
document.body.
|
12
|
+
document.body.classList.remove('loaded')
|
13
13
|
loadCat.setAttribute('style', 'display:block')
|
14
14
|
Loader.lock = false
|
15
15
|
},
|
@@ -26,7 +26,7 @@ export const Loader = {
|
|
26
26
|
if (CONFIG.loader.start) {
|
27
27
|
transition(loadCat, 0)
|
28
28
|
}
|
29
|
-
document.body.
|
29
|
+
document.body.classList.add('loaded')
|
30
30
|
Loader.lock = true
|
31
31
|
}
|
32
32
|
}
|
@@ -1,6 +1,4 @@
|
|
1
1
|
import { pageScroll } from '../library/anime'
|
2
|
-
import { $dom } from '../library/dom'
|
3
|
-
import { $storage } from '../library/storage'
|
4
2
|
import { BODY, CONFIG, LOCAL_HASH, LOCAL_URL, scrollAction, setLocalHash } from './globalVars'
|
5
3
|
import { createChild } from '../library/proto'
|
6
4
|
|
@@ -16,7 +14,7 @@ export const showtip = (msg: string): void | never => {
|
|
16
14
|
})
|
17
15
|
|
18
16
|
setTimeout(() => {
|
19
|
-
tipbox.
|
17
|
+
tipbox.classList.add('hide')
|
20
18
|
setTimeout(() => {
|
21
19
|
BODY.removeChild(tipbox)
|
22
20
|
}, 300)
|
@@ -27,7 +25,7 @@ export const pagePosition = () => {
|
|
27
25
|
// 判断配置项是否开启了自动记录滚动位置
|
28
26
|
if (CONFIG.auto_scroll) {
|
29
27
|
// 将当前页面的滚动位置存入本地缓存
|
30
|
-
|
28
|
+
localStorage.setItem(LOCAL_URL, String(scrollAction.y))
|
31
29
|
}
|
32
30
|
}
|
33
31
|
|
@@ -37,14 +35,14 @@ export const positionInit = (comment?: boolean) => {
|
|
37
35
|
|
38
36
|
let target = null
|
39
37
|
if (LOCAL_HASH) {
|
40
|
-
|
38
|
+
localStorage.removeItem(LOCAL_URL)
|
41
39
|
return
|
42
40
|
}
|
43
41
|
|
44
42
|
if (anchor) {
|
45
43
|
target = document.querySelector(decodeURI(anchor))
|
46
44
|
} else {
|
47
|
-
target = CONFIG.auto_scroll ? parseInt(
|
45
|
+
target = CONFIG.auto_scroll ? parseInt(localStorage.getItem(LOCAL_URL)) : 0
|
48
46
|
}
|
49
47
|
|
50
48
|
if (target) {
|
@@ -1,5 +1,3 @@
|
|
1
|
-
import { $dom } from './dom'
|
2
|
-
|
3
1
|
export const insertAfter = function (el: Element, element: HTMLElement): void {
|
4
2
|
const parent = el.parentNode
|
5
3
|
if (parent.lastChild === el) {
|
@@ -70,68 +68,3 @@ export const setDisplay = function (el: HTMLElement, d: string): HTMLElement {
|
|
70
68
|
el.style.display = d
|
71
69
|
return el
|
72
70
|
}
|
73
|
-
|
74
|
-
export default function initProto () {
|
75
|
-
Object.assign(HTMLElement.prototype, {
|
76
|
-
/**
|
77
|
-
* 找到此节点所有符合selector选择器的子节点
|
78
|
-
* @deprecated Will be removed in the v0.5
|
79
|
-
*/
|
80
|
-
find (selector: string): NodeListOf<HTMLElement> {
|
81
|
-
return $dom.all(selector, this)
|
82
|
-
},
|
83
|
-
/**
|
84
|
-
* 这个方法接受三个参数:
|
85
|
-
* type 表示操作类型('add'、'remove'、'toggle'),
|
86
|
-
* className 是一个或多个要操作的类名,
|
87
|
-
* display 是一个可选的布尔值,用于在执行切换操作时指定类名是否应显示或隐藏。
|
88
|
-
* 该方法会根据操作类型执行相应的类名操作。
|
89
|
-
* @deprecated Will be removed in the v0.5
|
90
|
-
*/
|
91
|
-
_class (type: string, className: string, display?: boolean): void {
|
92
|
-
const classNames = className.indexOf(' ') ? className.split(' ') : [className]
|
93
|
-
classNames.forEach((name) => {
|
94
|
-
if (type === 'toggle') {
|
95
|
-
this.classList.toggle(name, display)
|
96
|
-
} else {
|
97
|
-
this.classList[type](name)
|
98
|
-
}
|
99
|
-
})
|
100
|
-
},
|
101
|
-
/**
|
102
|
-
* 这个方法是对 _class 方法的封装,调用时会将操作类型设为 'add',然后执行添加类名的操作。
|
103
|
-
* 最后,它返回当前的 EventTarget,通常是 DOM 元素本身,以支持链式调用。
|
104
|
-
* @deprecated Will be removed in the v0.5
|
105
|
-
*/
|
106
|
-
addClass (className: string): EventTarget {
|
107
|
-
this._class('add', className)
|
108
|
-
return this
|
109
|
-
},
|
110
|
-
/**
|
111
|
-
* 这个方法是对 _class 方法的封装,调用时会将操作类型设为 'remove',然后执行移除类名的操作。
|
112
|
-
* 最后,它返回当前的 EventTarget,通常是 DOM 元素本身,以支持链式调用。
|
113
|
-
* @deprecated Will be removed in the v0.5
|
114
|
-
*/
|
115
|
-
removeClass (className: string): EventTarget {
|
116
|
-
this._class('remove', className)
|
117
|
-
return this
|
118
|
-
},
|
119
|
-
/**
|
120
|
-
* 这个方法是对 _class 方法的封装,调用时会将操作类型设为 'toggle',然后执行切换类名的操作。
|
121
|
-
* 如果提供了 display 参数,它将根据布尔值决定是否显示或隐藏类名。
|
122
|
-
* 最后,它返回当前的 EventTarget,通常是 DOM 元素本身,以支持链式调用。
|
123
|
-
* @deprecated Will be removed in the v0.5
|
124
|
-
*/
|
125
|
-
toggleClass (className: string, display?: boolean): EventTarget {
|
126
|
-
this._class('toggle', className, display)
|
127
|
-
return this
|
128
|
-
},
|
129
|
-
/**
|
130
|
-
* 这个方法返回一个布尔值,表示元素是否包含指定的类名。
|
131
|
-
* @deprecated Will be removed in the v0.5
|
132
|
-
*/
|
133
|
-
hasClass (className: string): boolean {
|
134
|
-
return this.classList.contains(className)
|
135
|
-
}
|
136
|
-
})
|
137
|
-
}
|
@@ -1,4 +1,3 @@
|
|
1
|
-
import { $storage } from './storage'
|
2
1
|
import { transition } from './anime'
|
3
2
|
import { BODY } from '../globals/globalVars'
|
4
3
|
import { changeTheme } from '../globals/themeColor'
|
@@ -23,19 +22,19 @@ export function initVue () {
|
|
23
22
|
})
|
24
23
|
}
|
25
24
|
|
26
|
-
if (btn.
|
25
|
+
if (btn.classList.contains('i-sun')) {
|
27
26
|
c = () => {
|
28
|
-
neko.
|
27
|
+
neko.classList.add('dark')
|
29
28
|
changeTheme('dark')
|
30
|
-
|
29
|
+
localStorage.setItem('theme', 'dark')
|
31
30
|
hideNeko()
|
32
31
|
}
|
33
32
|
} else {
|
34
|
-
neko.
|
33
|
+
neko.classList.add('dark')
|
35
34
|
c = () => {
|
36
|
-
neko.
|
35
|
+
neko.classList.remove('dark')
|
37
36
|
changeTheme()
|
38
|
-
|
37
|
+
localStorage.setItem('theme', 'light')
|
39
38
|
hideNeko()
|
40
39
|
}
|
41
40
|
}
|
@@ -1,14 +1,12 @@
|
|
1
|
-
import { $dom } from '../library/dom'
|
2
|
-
|
3
1
|
export const cardActive = () => {
|
4
2
|
if (!document.querySelector('.index.wrap')) { return }
|
5
3
|
const io = new IntersectionObserver((entries) => {
|
6
4
|
entries.forEach((article) => {
|
7
|
-
if (article.target.
|
5
|
+
if (article.target.classList.contains('show')) {
|
8
6
|
io.unobserve(article.target)
|
9
7
|
} else {
|
10
8
|
if (article.isIntersecting || article.intersectionRatio > 0) {
|
11
|
-
article.target.
|
9
|
+
article.target.classList.add('show')
|
12
10
|
io.unobserve(article.target)
|
13
11
|
}
|
14
12
|
}
|
@@ -18,25 +16,25 @@ export const cardActive = () => {
|
|
18
16
|
threshold: [0.3]
|
19
17
|
})
|
20
18
|
|
21
|
-
|
19
|
+
document.querySelectorAll('.index.wrap article.item, .index.wrap section.item').forEach((article) => {
|
22
20
|
io.observe(article)
|
23
21
|
})
|
24
22
|
|
25
|
-
document.querySelector('.index.wrap .item:first-child').
|
23
|
+
document.querySelector('.index.wrap .item:first-child').classList.add('show')
|
26
24
|
|
27
|
-
|
25
|
+
document.querySelectorAll('.cards .item').forEach((element) => {
|
28
26
|
['mouseenter', 'touchstart'].forEach((item) => {
|
29
27
|
element.addEventListener(item, () => {
|
30
28
|
const cardEle = document.querySelector('.cards .item.active')
|
31
29
|
if (cardEle) {
|
32
|
-
cardEle.
|
30
|
+
cardEle.classList.remove('active')
|
33
31
|
}
|
34
|
-
element.
|
32
|
+
element.classList.add('active')
|
35
33
|
}, { passive: true })
|
36
34
|
});
|
37
35
|
['mouseleave'].forEach((item) => {
|
38
36
|
element.addEventListener(item, () => {
|
39
|
-
element.
|
37
|
+
element.classList.remove('active')
|
40
38
|
}, { passive: true })
|
41
39
|
})
|
42
40
|
})
|
@@ -1,4 +1,3 @@
|
|
1
|
-
import { $dom } from '../library/dom'
|
2
1
|
import { insertAfter } from '../library/proto'
|
3
2
|
|
4
3
|
// TODO 使用PhotoSwipe替换Fancybox
|
@@ -6,7 +5,7 @@ export const postFancybox = (p:string) => {
|
|
6
5
|
if (document.querySelector(p + ' .md img')) {
|
7
6
|
const q = jQuery.noConflict()
|
8
7
|
|
9
|
-
|
8
|
+
document.querySelectorAll(p + ' p.gallery').forEach((element) => {
|
10
9
|
const box = document.createElement('div')
|
11
10
|
box.className = 'gallery'
|
12
11
|
box.setAttribute('data-height', String(element.getAttribute('data-height') || 220))
|
@@ -17,7 +16,7 @@ export const postFancybox = (p:string) => {
|
|
17
16
|
element.remove()
|
18
17
|
})
|
19
18
|
|
20
|
-
|
19
|
+
document.querySelectorAll(p + ' .md img:not(.emoji):not(.vemoji)').forEach((element) => {
|
21
20
|
const $image = q(element)
|
22
21
|
const imageLink = $image.attr('data-src') || $image.attr('src') // 替换
|
23
22
|
const $imageWrapLink = $image.wrap('<a class="fancybox" href="' + imageLink + '" itemscope itemtype="https://schema.org/ImageObject" itemprop="url"></a>').parent('a')
|
@@ -35,12 +34,12 @@ export const postFancybox = (p:string) => {
|
|
35
34
|
const para = document.createElement('span')
|
36
35
|
const txt = document.createTextNode(info)
|
37
36
|
para.appendChild(txt)
|
38
|
-
para.
|
37
|
+
para.classList.add(captionClass)
|
39
38
|
insertAfter(element, para)
|
40
39
|
}
|
41
40
|
})
|
42
41
|
|
43
|
-
|
42
|
+
document.querySelectorAll(p + ' div.gallery').forEach((el, i) => {
|
44
43
|
// @ts-ignore
|
45
44
|
q(el).justifiedGallery({
|
46
45
|
rowHeight: q(el).data('height') || 120,
|
@@ -1,9 +1,7 @@
|
|
1
|
-
import { $dom } from '../library/dom'
|
2
1
|
import { postFancybox } from './fancybox'
|
3
2
|
import { clipBoard, showtip } from '../globals/tools'
|
4
3
|
import { CONFIG, BODY } from '../globals/globalVars'
|
5
4
|
import { pageScroll, transition } from '../library/anime'
|
6
|
-
import { mediaPlayer } from '../player'
|
7
5
|
import { getDisplay, setDisplay, wrapObject } from '../library/proto'
|
8
6
|
|
9
7
|
export const postBeauty = () => {
|
@@ -43,31 +41,31 @@ export const postBeauty = () => {
|
|
43
41
|
}
|
44
42
|
}
|
45
43
|
|
46
|
-
|
47
|
-
let parent = element.parentNode
|
44
|
+
document.querySelectorAll('li ruby').forEach((element) => {
|
45
|
+
let parent = element.parentNode as HTMLElement
|
48
46
|
// @ts-ignore
|
49
47
|
if (element.parentNode.tagName !== 'LI') {
|
50
|
-
parent = element.parentNode.parentNode
|
48
|
+
parent = element.parentNode.parentNode as HTMLElement
|
51
49
|
}
|
52
|
-
parent.
|
50
|
+
parent.classList.add('ruby')
|
53
51
|
})
|
54
52
|
|
55
|
-
|
53
|
+
document.querySelectorAll('ol[start]').forEach((element) => {
|
56
54
|
// @ts-ignore
|
57
55
|
element.style.counterReset = 'counter ' + parseInt(element.getAttribute('start') - 1)
|
58
56
|
})
|
59
57
|
|
60
|
-
|
58
|
+
document.querySelectorAll<HTMLElement>('.md table').forEach((element) => {
|
61
59
|
wrapObject(element, {
|
62
60
|
className: 'table-container'
|
63
61
|
})
|
64
62
|
})
|
65
63
|
|
66
|
-
|
64
|
+
document.querySelectorAll('.highlight > .table-container').forEach((element) => {
|
67
65
|
element.className = 'code-container'
|
68
66
|
})
|
69
67
|
|
70
|
-
|
68
|
+
document.querySelectorAll<HTMLElement>('figure.highlight').forEach((element) => {
|
71
69
|
const code_container = element.querySelector('.code-container') as HTMLElement
|
72
70
|
const caption = element.querySelector('figcaption')
|
73
71
|
|
@@ -80,7 +78,7 @@ export const postBeauty = () => {
|
|
80
78
|
copyBtn.addEventListener('click', (event) => {
|
81
79
|
const target = <HTMLElement>event.currentTarget
|
82
80
|
let comma = ''; let code = ''
|
83
|
-
code_container.
|
81
|
+
code_container.querySelectorAll('pre').forEach((line) => {
|
84
82
|
code += comma + line.innerText
|
85
83
|
comma = '\n'
|
86
84
|
})
|
@@ -101,61 +99,61 @@ export const postBeauty = () => {
|
|
101
99
|
const breakBtn = element.querySelector('.breakline-btn')
|
102
100
|
breakBtn.addEventListener('click', (event) => {
|
103
101
|
const target = event.currentTarget as HTMLElement
|
104
|
-
if (element.
|
105
|
-
element.
|
102
|
+
if (element.classList.contains('breakline')) {
|
103
|
+
element.classList.remove('breakline')
|
106
104
|
target.querySelector('.ic').className = 'ic i-align-left'
|
107
105
|
} else {
|
108
|
-
element.
|
106
|
+
element.classList.add('breakline')
|
109
107
|
target.querySelector('.ic').className = 'ic i-align-justify'
|
110
108
|
}
|
111
109
|
})
|
112
110
|
|
113
111
|
const fullscreenBtn = element.querySelector('.fullscreen-btn')
|
114
112
|
const removeFullscreen = () => {
|
115
|
-
element.
|
113
|
+
element.classList.remove('fullscreen')
|
116
114
|
element.scrollTop = 0
|
117
|
-
BODY.
|
115
|
+
BODY.classList.remove('fullscreen')
|
118
116
|
fullscreenBtn.querySelector('.ic').className = 'ic i-expand'
|
119
117
|
}
|
120
118
|
const fullscreenHandle = () => {
|
121
|
-
if (element.
|
119
|
+
if (element.classList.contains('fullscreen')) {
|
122
120
|
removeFullscreen()
|
123
|
-
if (code_container && code_container.
|
121
|
+
if (code_container && code_container.querySelectorAll('tr').length > 15) {
|
124
122
|
const showBtn = code_container.querySelector('.show-btn')
|
125
123
|
code_container.style.maxHeight = '300px'
|
126
|
-
showBtn.
|
124
|
+
showBtn.classList.remove('open')
|
127
125
|
}
|
128
126
|
pageScroll(element)
|
129
127
|
} else {
|
130
|
-
element.
|
131
|
-
BODY.
|
128
|
+
element.classList.add('fullscreen')
|
129
|
+
BODY.classList.add('fullscreen')
|
132
130
|
fullscreenBtn.querySelector('.ic').className = 'ic i-compress'
|
133
|
-
if (code_container && code_container.
|
131
|
+
if (code_container && code_container.querySelectorAll('tr').length > 15) {
|
134
132
|
const showBtn = code_container.querySelector('.show-btn')
|
135
133
|
code_container.style.maxHeight = ''
|
136
|
-
showBtn.
|
134
|
+
showBtn.classList.add('open')
|
137
135
|
}
|
138
136
|
}
|
139
137
|
}
|
140
138
|
fullscreenBtn.addEventListener('click', fullscreenHandle)
|
141
139
|
caption && caption.addEventListener('click', fullscreenHandle)
|
142
140
|
|
143
|
-
if (code_container && code_container.
|
141
|
+
if (code_container && code_container.querySelectorAll('tr').length > 15) {
|
144
142
|
code_container.style.maxHeight = '300px'
|
145
143
|
code_container.insertAdjacentHTML('beforeend', '<div class="show-btn"><i class="ic i-angle-down"></i></div>')
|
146
144
|
const showBtn = code_container.querySelector('.show-btn')
|
147
145
|
|
148
146
|
const hideCode = () => {
|
149
147
|
code_container.style.maxHeight = '300px'
|
150
|
-
showBtn.
|
148
|
+
showBtn.classList.remove('open')
|
151
149
|
}
|
152
150
|
const showCode = () => {
|
153
151
|
code_container.style.maxHeight = ''
|
154
|
-
showBtn.
|
152
|
+
showBtn.classList.add('open')
|
155
153
|
}
|
156
154
|
|
157
155
|
showBtn.addEventListener('click', () => {
|
158
|
-
if (showBtn.
|
156
|
+
if (showBtn.classList.contains('open')) {
|
159
157
|
removeFullscreen()
|
160
158
|
hideCode()
|
161
159
|
pageScroll(code_container)
|
@@ -166,12 +164,12 @@ export const postBeauty = () => {
|
|
166
164
|
}
|
167
165
|
})
|
168
166
|
|
169
|
-
|
167
|
+
document.querySelectorAll('pre.mermaid > svg').forEach((element) => {
|
170
168
|
const temp = <SVGAElement><unknown>element
|
171
169
|
temp.style.maxWidth = ''
|
172
170
|
})
|
173
171
|
|
174
|
-
|
172
|
+
document.querySelectorAll('.reward button').forEach((element) => {
|
175
173
|
element.addEventListener('click', (event) => {
|
176
174
|
event.preventDefault()
|
177
175
|
const qr = document.getElementById('qr')
|
@@ -187,47 +185,47 @@ export const postBeauty = () => {
|
|
187
185
|
|
188
186
|
// quiz
|
189
187
|
if (__shokax_quiz__) {
|
190
|
-
|
188
|
+
document.querySelectorAll('.quiz > ul.options li').forEach((element) => {
|
191
189
|
element.addEventListener('click', () => {
|
192
|
-
if (element.
|
193
|
-
element.
|
194
|
-
element.parentNode.parentNode.
|
190
|
+
if (element.classList.contains('correct')) {
|
191
|
+
element.classList.toggle('right');
|
192
|
+
(element.parentNode.parentNode as HTMLElement).classList.add('show')
|
195
193
|
} else {
|
196
|
-
element.
|
194
|
+
element.classList.toggle('wrong')
|
197
195
|
}
|
198
196
|
})
|
199
197
|
})
|
200
198
|
|
201
|
-
|
199
|
+
document.querySelectorAll('.quiz > p').forEach((element) => {
|
202
200
|
element.addEventListener('click', () => {
|
203
|
-
element.parentNode.
|
201
|
+
(element.parentNode as HTMLElement).classList.toggle('show')
|
204
202
|
})
|
205
203
|
})
|
206
204
|
|
207
|
-
|
208
|
-
const quiz = element.parentNode
|
205
|
+
document.querySelectorAll('.quiz > p:first-child').forEach((element) => {
|
206
|
+
const quiz = element.parentNode as HTMLElement
|
209
207
|
let type = 'choice'
|
210
|
-
if (quiz.
|
208
|
+
if (quiz.classList.contains('true') || quiz.classList.contains('false')) {
|
211
209
|
type = 'true_false'
|
212
210
|
}
|
213
|
-
if (quiz.
|
211
|
+
if (quiz.classList.contains('multi')) {
|
214
212
|
type = 'multiple'
|
215
213
|
}
|
216
|
-
if (quiz.
|
214
|
+
if (quiz.classList.contains('fill')) {
|
217
215
|
type = 'gap_fill'
|
218
216
|
}
|
219
|
-
if (quiz.
|
217
|
+
if (quiz.classList.contains('essay')) {
|
220
218
|
type = 'essay'
|
221
219
|
}
|
222
220
|
element.setAttribute('data-type', LOCAL.quiz[type])
|
223
221
|
})
|
224
222
|
|
225
|
-
|
223
|
+
document.querySelectorAll('.quiz .mistake').forEach((element) => {
|
226
224
|
element.setAttribute('data-type', LOCAL.quiz.mistake)
|
227
225
|
})
|
228
226
|
}
|
229
227
|
|
230
|
-
|
228
|
+
document.querySelectorAll('div.tags a').forEach((element) => {
|
231
229
|
element.className = ['primary', 'success', 'info', 'warning', 'danger'][Math.floor(Math.random() * 5)]
|
232
230
|
})
|
233
231
|
|
@@ -101,7 +101,6 @@ export function algoliaSearch () {
|
|
101
101
|
}
|
102
102
|
})
|
103
103
|
document.querySelector('.close-btn').addEventListener('click', onPopupClose)
|
104
|
-
// window.addEventListener('pjax:success', onPopupClose)
|
105
104
|
window.addEventListener('keyup', (event) => {
|
106
105
|
if (event.key === 'Escape') {
|
107
106
|
onPopupClose()
|
@@ -1,11 +1,10 @@
|
|
1
1
|
import { pageScroll } from '../library/anime'
|
2
|
-
import { $dom } from '../library/dom'
|
3
2
|
import { createChild } from '../library/proto'
|
4
3
|
|
5
4
|
export const tabFormat = () => {
|
6
5
|
// tab
|
7
6
|
let first_tab:boolean
|
8
|
-
|
7
|
+
document.querySelectorAll('div.tab').forEach((element) => {
|
9
8
|
if (element.getAttribute('data-ready')) { return }
|
10
9
|
|
11
10
|
const id = element.getAttribute('data-id')
|
@@ -41,17 +40,17 @@ export const tabFormat = () => {
|
|
41
40
|
})
|
42
41
|
|
43
42
|
if (first_tab) {
|
44
|
-
li.
|
45
|
-
element.
|
43
|
+
li.classList.add('active')
|
44
|
+
element.classList.add('active')
|
46
45
|
}
|
47
46
|
|
48
47
|
li.addEventListener('click', (event) => {
|
49
|
-
const target = event.currentTarget
|
50
|
-
box.
|
51
|
-
el.
|
48
|
+
const target = event.currentTarget as HTMLElement
|
49
|
+
box.querySelectorAll('.active').forEach((el) => {
|
50
|
+
el.classList.remove('active')
|
52
51
|
})
|
53
|
-
element.
|
54
|
-
target.
|
52
|
+
element.classList.add('active')
|
53
|
+
target.classList.add('active')
|
55
54
|
})
|
56
55
|
|
57
56
|
box.appendChild(element)
|
@@ -9,16 +9,13 @@ import {
|
|
9
9
|
showContents,
|
10
10
|
siteHeader,
|
11
11
|
siteNav,
|
12
|
-
toolBtn
|
13
|
-
toolPlayer
|
12
|
+
toolBtn
|
14
13
|
} from '../globals/globalVars'
|
15
14
|
import { Loader } from '../globals/thirdparty'
|
16
|
-
import { $dom } from '../library/dom'
|
17
|
-
import { mediaPlayer } from '../player'
|
18
15
|
import { createChild } from '../library/proto'
|
19
16
|
|
20
17
|
export default function domInit () {
|
21
|
-
|
18
|
+
document.querySelectorAll('.overview .menu > .item').forEach((el) => {
|
22
19
|
siteNav.querySelector('.menu').appendChild(el.cloneNode(true))
|
23
20
|
})
|
24
21
|
|
@@ -1,14 +1,13 @@
|
|
1
1
|
import domInit from './domInit'
|
2
|
-
import {
|
3
|
-
import {
|
4
|
-
import {
|
5
|
-
import {
|
6
|
-
import {
|
7
|
-
import {
|
8
|
-
import {
|
9
|
-
import {
|
10
|
-
import {
|
11
|
-
import { transition } from '../library/anime'
|
2
|
+
import {siteRefresh} from './refresh'
|
3
|
+
import {cloudflareInit} from '../components/cloudflare'
|
4
|
+
import {BODY, CONFIG, setSiteSearch, siteSearch} from '../globals/globalVars'
|
5
|
+
import {autoDarkmode, themeColorListener} from '../globals/themeColor'
|
6
|
+
import {resizeHandle, scrollHandle, visibilityListener} from '../globals/handles'
|
7
|
+
import {pagePosition} from '../globals/tools'
|
8
|
+
import {initVue} from '../library/vue'
|
9
|
+
import {createChild} from '../library/proto'
|
10
|
+
import {transition} from '../library/anime'
|
12
11
|
|
13
12
|
const siteInit = async () => {
|
14
13
|
initVue()
|
@@ -39,15 +38,12 @@ const siteInit = async () => {
|
|
39
38
|
})
|
40
39
|
|
41
40
|
// Handle and trigger popup window
|
42
|
-
|
43
|
-
$dom.each('.search', (element) => {
|
44
|
-
element.addEventListener('click', () => {
|
41
|
+
document.querySelector('.search').addEventListener('click', () => {
|
45
42
|
document.body.style.overflow = 'hidden'
|
46
43
|
transition(siteSearch, 'shrinkIn', () => {
|
47
44
|
(document.querySelector('.search-input') as HTMLInputElement).focus()
|
48
45
|
}) // transition.shrinkIn
|
49
46
|
})
|
50
|
-
})
|
51
47
|
}, {once: true, capture: true})
|
52
48
|
}
|
53
49
|
|
package/source/js/_app/player.ts
CHANGED
@@ -3,7 +3,6 @@
|
|
3
3
|
import { CONFIG, originTitle } from './globals/globalVars'
|
4
4
|
import { showtip } from './globals/tools'
|
5
5
|
import { pageScroll } from './library/anime'
|
6
|
-
import { $storage } from './library/storage'
|
7
6
|
import { tabFormat } from './page/tab'
|
8
7
|
import { createChild, getLeft, getWidth, setDisplay, setWidth } from './library/proto'
|
9
8
|
|
@@ -85,7 +84,7 @@ export const mediaPlayer = (t, config?) => {
|
|
85
84
|
}
|
86
85
|
|
87
86
|
controller.btns.mode.className = 'mode ' + t.player.options.mode + ' btn'
|
88
|
-
|
87
|
+
localStorage.setItem('_PlayerMode', t.player.options.mode)
|
89
88
|
},
|
90
89
|
volume (e) {
|
91
90
|
e.preventDefault()
|
@@ -148,7 +147,7 @@ export const mediaPlayer = (t, config?) => {
|
|
148
147
|
|
149
148
|
if (current) {
|
150
149
|
if (progress.el) {
|
151
|
-
progress.el.parentNode.
|
150
|
+
progress.el.parentNode.classList.remove('current')
|
152
151
|
.removeEventListener(utils.nameMap.dragStart, progress.drag)
|
153
152
|
progress.el.remove()
|
154
153
|
}
|
@@ -163,7 +162,7 @@ export const mediaPlayer = (t, config?) => {
|
|
163
162
|
className: 'bar'
|
164
163
|
})
|
165
164
|
|
166
|
-
current.
|
165
|
+
current.classList.add('current')
|
167
166
|
|
168
167
|
current.addEventListener(utils.nameMap.dragStart, progress.drag)
|
169
168
|
|
@@ -175,7 +174,7 @@ export const mediaPlayer = (t, config?) => {
|
|
175
174
|
(progress.el as HTMLElement).setAttribute('data-ptime', utils.secondToTime(percent * source.duration))
|
176
175
|
},
|
177
176
|
seeking (type) {
|
178
|
-
if (type) { progress.el.
|
177
|
+
if (type) { progress.el.classList.add('seeking') } else { progress.el.classList.remove('seeking') }
|
179
178
|
},
|
180
179
|
percent (e, el) {
|
181
180
|
let percentage = ((e.clientX || e.changedTouches[0].clientX) - getLeft(el)) / getWidth(el)
|
@@ -301,13 +300,13 @@ export const mediaPlayer = (t, config?) => {
|
|
301
300
|
scroll () {
|
302
301
|
const item = this.current()
|
303
302
|
let li = this.el.querySelector('li.active')
|
304
|
-
li && li.
|
303
|
+
li && li.classList.remove('active')
|
305
304
|
let tab = this.el.querySelector('.tab.active')
|
306
|
-
tab && tab.
|
305
|
+
tab && tab.classList.remove('active')
|
307
306
|
li = this.el.querySelectorAll('.nav li')[item.group]
|
308
|
-
li && li.
|
307
|
+
li && li.classList.add('active')
|
309
308
|
tab = this.el.querySelectorAll('.tab')[item.group]
|
310
|
-
tab && tab.
|
309
|
+
tab && tab.classList.add('active')
|
311
310
|
|
312
311
|
pageScroll(item.el, item.el.offsetTop)
|
313
312
|
|
@@ -321,7 +320,7 @@ export const mediaPlayer = (t, config?) => {
|
|
321
320
|
},
|
322
321
|
error () {
|
323
322
|
const current = this.current()
|
324
|
-
current.el.
|
323
|
+
current.el.classList.remove('current').classList.add('error')
|
325
324
|
current.error = true
|
326
325
|
this.errnum++
|
327
326
|
}
|
@@ -342,9 +341,9 @@ export const mediaPlayer = (t, config?) => {
|
|
342
341
|
},
|
343
342
|
hide () {
|
344
343
|
const el = this.el
|
345
|
-
el.
|
344
|
+
el.classList.add('hide')
|
346
345
|
window.setTimeout(() => {
|
347
|
-
el.
|
346
|
+
el.classList.remove('show hide')
|
348
347
|
}, 300)
|
349
348
|
}
|
350
349
|
}
|
@@ -362,10 +361,10 @@ export const mediaPlayer = (t, config?) => {
|
|
362
361
|
}
|
363
362
|
},
|
364
363
|
music (event) {
|
365
|
-
if (info.el.
|
364
|
+
if (info.el.classList.contains('show')) {
|
366
365
|
info.hide()
|
367
366
|
} else {
|
368
|
-
info.el.
|
367
|
+
info.el.classList.add('show')
|
369
368
|
playlist.scroll().title()
|
370
369
|
}
|
371
370
|
}
|
@@ -409,7 +408,7 @@ export const mediaPlayer = (t, config?) => {
|
|
409
408
|
const meta = utils.parse(raw)
|
410
409
|
if (meta[0]) {
|
411
410
|
const skey = JSON.stringify(meta)
|
412
|
-
const playlist =
|
411
|
+
const playlist = localStorage.getItem(skey)
|
413
412
|
if (playlist) {
|
414
413
|
// list.push.apply(list, JSON.parse(playlist))
|
415
414
|
list.push(...JSON.parse(playlist))
|
@@ -419,7 +418,7 @@ export const mediaPlayer = (t, config?) => {
|
|
419
418
|
.then((response) => {
|
420
419
|
return response.json()
|
421
420
|
}).then((json) => {
|
422
|
-
|
421
|
+
localStorage.setItem(skey, JSON.stringify(json))
|
423
422
|
// list.push.apply(list, json)
|
424
423
|
list.push(...json)
|
425
424
|
resolve(list)
|
@@ -583,8 +582,8 @@ export const mediaPlayer = (t, config?) => {
|
|
583
582
|
|
584
583
|
source.setAttribute('src', item.url)
|
585
584
|
source.setAttribute('title', item.name + ' - ' + item.artist)
|
586
|
-
this.volume(
|
587
|
-
this.muted(
|
585
|
+
this.volume(localStorage.getItem('_PlayerVolume') || '0.7')
|
586
|
+
this.muted(localStorage.getItem('_PlayerMuted'))
|
588
587
|
|
589
588
|
progress.create()
|
590
589
|
|
@@ -625,10 +624,10 @@ export const mediaPlayer = (t, config?) => {
|
|
625
624
|
muted (status?) {
|
626
625
|
if (status === 'muted') {
|
627
626
|
source.muted = status
|
628
|
-
|
627
|
+
localStorage.setItem('_PlayerMuted', status)
|
629
628
|
controller.update(0)
|
630
629
|
} else {
|
631
|
-
|
630
|
+
localStorage.removeItem('_PlayerMuted')
|
632
631
|
source.muted = false
|
633
632
|
controller.update(source.volume)
|
634
633
|
}
|
@@ -636,7 +635,7 @@ export const mediaPlayer = (t, config?) => {
|
|
636
635
|
volume (percentage) {
|
637
636
|
if (!isNaN(percentage)) {
|
638
637
|
controller.update(percentage)
|
639
|
-
|
638
|
+
localStorage.setItem('_PlayerVolume', percentage)
|
640
639
|
source.volume = percentage
|
641
640
|
}
|
642
641
|
},
|
@@ -684,8 +683,8 @@ export const mediaPlayer = (t, config?) => {
|
|
684
683
|
const y = -(this.index - 1)
|
685
684
|
this.el.style.transform = 'translateY(' + y + 'rem)'
|
686
685
|
// this.el.style.webkitTransform = 'translateY(' + y + 'rem)';
|
687
|
-
this.el.getElementsByClassName('current')[0].
|
688
|
-
this.el.getElementsByTagName('p')[i].
|
686
|
+
this.el.getElementsByClassName('current')[0].classList.remove('current')
|
687
|
+
this.el.getElementsByTagName('p')[i].classList.add('current')
|
689
688
|
}
|
690
689
|
}
|
691
690
|
}
|
@@ -755,12 +754,12 @@ export const mediaPlayer = (t, config?) => {
|
|
755
754
|
progress.el.setAttribute('data-dtime', utils.secondToTime(source.duration))
|
756
755
|
},
|
757
756
|
onplay () {
|
758
|
-
t.parentNode.
|
757
|
+
t.parentNode.classList.add('playing')
|
759
758
|
showtip(this.getAttribute('title'))
|
760
759
|
NOWPLAYING = t
|
761
760
|
},
|
762
761
|
onpause () {
|
763
|
-
t.parentNode.
|
762
|
+
t.parentNode.classList.remove('playing')
|
764
763
|
NOWPLAYING = null
|
765
764
|
},
|
766
765
|
ontimeupdate () {
|
@@ -779,7 +778,7 @@ export const mediaPlayer = (t, config?) => {
|
|
779
778
|
if (t.player.created) { return }
|
780
779
|
|
781
780
|
t.player.options = Object.assign(option, config)
|
782
|
-
t.player.options.mode =
|
781
|
+
t.player.options.mode = localStorage.getItem('_PlayerMode') || t.player.options.mode
|
783
782
|
|
784
783
|
// 初始化button、controls以及click事件
|
785
784
|
buttons.create()
|
@@ -789,7 +788,7 @@ export const mediaPlayer = (t, config?) => {
|
|
789
788
|
// 初始化播放列表、预览、控件按钮等
|
790
789
|
info.create()
|
791
790
|
|
792
|
-
t.parentNode.
|
791
|
+
t.parentNode.classList.add(t.player.options.type)
|
793
792
|
|
794
793
|
t.player.created = true
|
795
794
|
}
|
package/toolbox/compiler.mjs
CHANGED
@@ -1,15 +1,13 @@
|
|
1
1
|
/*
|
2
2
|
ShokaX ToolBox - Compiler
|
3
|
-
compatibility: ShokaX v0.
|
3
|
+
compatibility: ShokaX v0.5.x-dev
|
4
4
|
*/
|
5
|
-
import path from "node:path";
|
6
5
|
import fs from 'fs/promises'
|
7
|
-
import child_process from 'child_process'
|
8
6
|
import { buildSync } from 'esbuild'
|
9
7
|
import { glob } from 'glob'
|
10
8
|
|
11
9
|
const CONFIG = {
|
12
|
-
|
10
|
+
|
13
11
|
}
|
14
12
|
|
15
13
|
console.log('ShokaX ToolBox - Compiler')
|
@@ -18,50 +16,24 @@ console.log('Start compiling...')
|
|
18
16
|
const entryPoints = await glob('./scripts/**/*.ts');
|
19
17
|
const jsons = await glob('./scripts/**/*.json');
|
20
18
|
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
for (const entry of jsons) {
|
40
|
-
await fs.unlink(entry)
|
41
|
-
}
|
42
|
-
console.log('Finished compiling.')
|
43
|
-
})
|
44
|
-
})
|
45
|
-
} else {
|
46
|
-
console.log('RUN THIS SCRIPT IN YOUR SHOKAX THEME ROOT DIRECTORY!')
|
47
|
-
console.log('Using esbuild compiler...')
|
48
|
-
buildSync({
|
49
|
-
entryPoints: entryPoints,
|
50
|
-
outdir: 'scripts',
|
51
|
-
bundle: false,
|
52
|
-
format: 'cjs',
|
53
|
-
target: ['esnext'],
|
54
|
-
platform: 'node',
|
55
|
-
loader: { '.ts': 'ts' },
|
56
|
-
})
|
57
|
-
entryPoints.forEach(async (entry) => {
|
58
|
-
await fs.unlink(entry)
|
59
|
-
})
|
60
|
-
jsons.forEach(async (entry)=>{
|
61
|
-
await fs.unlink(entry)
|
62
|
-
})
|
63
|
-
console.log('Finished compiling.')
|
64
|
-
}
|
19
|
+
console.log('RUN THIS SCRIPT IN YOUR SHOKAX THEME ROOT DIRECTORY!')
|
20
|
+
console.log('Using esbuild compiler...')
|
21
|
+
buildSync({
|
22
|
+
entryPoints: entryPoints,
|
23
|
+
outdir: 'scripts',
|
24
|
+
bundle: false,
|
25
|
+
format: 'cjs',
|
26
|
+
target: ['esnext'],
|
27
|
+
platform: 'node',
|
28
|
+
loader: { '.ts': 'ts' },
|
29
|
+
})
|
30
|
+
entryPoints.forEach(async (entry) => {
|
31
|
+
await fs.unlink(entry)
|
32
|
+
})
|
33
|
+
jsons.forEach(async (entry)=>{
|
34
|
+
await fs.unlink(entry)
|
35
|
+
})
|
36
|
+
console.log('Finished compiling.')
|
65
37
|
|
66
38
|
console.log('Done.')
|
67
39
|
|
@@ -1,28 +0,0 @@
|
|
1
|
-
/**
|
2
|
-
* 获取一个dom选择器对应的元素
|
3
|
-
* @deprecated Will be removed in the v0.5
|
4
|
-
*/
|
5
|
-
const $dom = (selector: string, element: Document = document): HTMLElement => {
|
6
|
-
// 在测试环境中这能优化0.01-0.02ms左右
|
7
|
-
if (selector[0] === '#') {
|
8
|
-
return <HTMLElement> element.getElementById(selector.substring(1))
|
9
|
-
}
|
10
|
-
return <HTMLElement> element.querySelector(selector)
|
11
|
-
}
|
12
|
-
|
13
|
-
/**
|
14
|
-
* 获取具有此选择器的所有dom节点
|
15
|
-
* @deprecated Will be removed in the v0.5
|
16
|
-
*/
|
17
|
-
$dom.all = (selector: string, element: Document = document): NodeListOf<HTMLElement> => {
|
18
|
-
return element.querySelectorAll(selector)
|
19
|
-
}
|
20
|
-
/**
|
21
|
-
* 获取具有此选择器的所有dom节点,并依次执行callback函数
|
22
|
-
* @deprecated Will be removed in the v0.5
|
23
|
-
*/
|
24
|
-
$dom.each = (selector: string, callback: (value: HTMLElement, key: number, parent: NodeListOf<Element>) => void, element?: Document): void => {
|
25
|
-
$dom.all(selector, element).forEach(callback)
|
26
|
-
}
|
27
|
-
|
28
|
-
export { $dom }
|
@@ -1,12 +0,0 @@
|
|
1
|
-
// Html5LocalStorage的一个API
|
2
|
-
export const $storage = {
|
3
|
-
set (key: string, value: string): void {
|
4
|
-
localStorage.setItem(key, value)
|
5
|
-
},
|
6
|
-
get (key: string): string {
|
7
|
-
return localStorage.getItem(key)
|
8
|
-
},
|
9
|
-
del (key: string): void {
|
10
|
-
localStorage.removeItem(key)
|
11
|
-
}
|
12
|
-
}
|