hexo-theme-solitude 1.2.1 → 1.2.3
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/_config.yml +18 -2
- package/layout/includes/head/config.pug +1 -1
- package/layout/includes/inject/body.pug +2 -3
- package/layout/includes/inject/head.pug +3 -1
- package/layout/includes/page/equipment.pug +1 -1
- package/layout/includes/page/moments.pug +1 -1
- package/layout/includes/page/says.pug +1 -1
- package/layout/includes/page/tlink.pug +1 -1
- package/layout/includes/widgets/aside/asideTag.pug +1 -1
- package/layout/includes/widgets/home/categoryBar.pug +1 -1
- package/layout/includes/widgets/home/postList.pug +20 -21
- package/layout/includes/widgets/third-party/search/algolia-search.pug +2 -4
- package/layout/includes/widgets/third-party/search/local-search.pug +2 -4
- package/layout/index.pug +2 -1
- package/package.json +1 -1
- package/scripts/filter/default.js +27 -21
- package/source/css/_global/index.styl +1 -45
- package/source/css/_global/var.styl +10 -1
- package/source/css/_mode/index.styl +49 -5
- package/source/css/_page/about.styl +0 -109
- package/source/css/_page/equipment.styl +0 -7
- package/source/css/_page/index.styl +110 -1
- package/source/css/_page/moment.styl +0 -7
- package/source/css/_page/says.styl +0 -6
- package/source/css/_search/algolia-search.styl +56 -108
- package/source/css/_search/local-search.styl +131 -112
- package/source/js/extend/{console/comment.js → comment/twikoo.js} +0 -1
- package/source/js/extend/search/algolia-search.js +146 -122
- package/source/js/extend/search/local-search.js +137 -162
- package/source/js/utils.js +30 -1
@@ -1,140 +1,164 @@
|
|
1
|
-
window.addEventListener(
|
1
|
+
window.addEventListener("load", () => {
|
2
|
+
const $searchMask = document.getElementById("search-mask");
|
3
|
+
const $searchDialog = document.querySelector("#algolia-search .search-dialog");
|
4
|
+
|
2
5
|
const openSearch = () => {
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
document.addEventListener(
|
9
|
-
if (event.code ===
|
10
|
-
closeSearch()
|
11
|
-
document.removeEventListener(
|
6
|
+
utils.animateIn($searchMask, "to_show 0.5s");
|
7
|
+
$searchDialog.style.display = "block";
|
8
|
+
setTimeout(() => {
|
9
|
+
document.querySelector("#algolia-search .ais-SearchBox-input").focus();
|
10
|
+
}, 100);
|
11
|
+
document.addEventListener("keydown", function f(event) {
|
12
|
+
if (event.code === "Escape") {
|
13
|
+
closeSearch();
|
14
|
+
document.removeEventListener("keydown", f);
|
12
15
|
}
|
13
|
-
})
|
14
|
-
|
16
|
+
});
|
17
|
+
fixSafariHeight();
|
18
|
+
window.addEventListener("resize", fixSafariHeight);
|
19
|
+
};
|
15
20
|
|
16
21
|
const closeSearch = () => {
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
$searchDialog.style.cssText = "display: none; animation: ''"
|
22
|
-
}, 500)
|
23
|
-
utils.fadeOut(document.getElementById('search-mask'), 0.5)
|
24
|
-
}
|
22
|
+
utils.animateOut($searchDialog, "search_close .5s");
|
23
|
+
utils.animateOut($searchMask, "to_hide 0.5s");
|
24
|
+
window.removeEventListener("resize", fixSafariHeight);
|
25
|
+
};
|
25
26
|
|
26
|
-
const
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
rm.hideRightMenu();
|
32
|
-
openSearch();
|
33
|
-
let t = document.querySelector('.ais-search-box--input');
|
34
|
-
let evt = new Event('input', {bubbles: true, cancelable: true});
|
35
|
-
t.value = selectTextNow;
|
36
|
-
t.dispatchEvent(evt);
|
37
|
-
});
|
38
|
-
}
|
27
|
+
const fixSafariHeight = () => {
|
28
|
+
if (window.innerWidth < 768) {
|
29
|
+
$searchDialog.style.setProperty("--search-height", window.innerHeight + "px");
|
30
|
+
}
|
31
|
+
};
|
39
32
|
|
40
|
-
searchClickFn()
|
33
|
+
const searchClickFn = () => {
|
34
|
+
utils.addEventListenerPjax(document.querySelector("#search-button > .search"), "click", openSearch);
|
35
|
+
};
|
41
36
|
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
}
|
37
|
+
const searchFnOnce = () => {
|
38
|
+
$searchMask.addEventListener("click", closeSearch);
|
39
|
+
document.querySelector("#algolia-search .search-close-button").addEventListener("click", closeSearch);
|
40
|
+
};
|
46
41
|
|
47
|
-
const algolia = GLOBAL_CONFIG.algolia
|
48
|
-
const isAlgoliaValid = algolia.appId && algolia.apiKey && algolia.indexName
|
42
|
+
const algolia = GLOBAL_CONFIG.algolia;
|
43
|
+
const isAlgoliaValid = algolia.appId && algolia.apiKey && algolia.indexName;
|
49
44
|
if (!isAlgoliaValid) {
|
50
|
-
return console.error(
|
45
|
+
return console.error("Algolia setting is invalid!");
|
51
46
|
}
|
52
47
|
|
53
|
-
const searchClient = algoliasearch(
|
54
|
-
algolia.appId,
|
55
|
-
algolia.apiKey
|
56
|
-
);
|
57
|
-
|
58
48
|
const search = instantsearch({
|
59
49
|
indexName: algolia.indexName,
|
60
|
-
searchClient,
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
search.addWidget(
|
67
|
-
instantsearch.widgets.searchBox({
|
68
|
-
container: '#algolia-search-input',
|
69
|
-
showReset: false,
|
70
|
-
placeholder: GLOBAL_CONFIG.lang.search.placeholder,
|
71
|
-
showSubmit: false,
|
72
|
-
showLoadingIndicator: true,
|
73
|
-
templates: {
|
74
|
-
loadingIndicator: '<i class="scoicon sco-loading-line search-icon"></i>'
|
75
|
-
},
|
76
|
-
onStateChange({uiState, setUiState}) {
|
77
|
-
const searchInput = document.querySelector('#algolia-search-input input')
|
78
|
-
if (searchInput.value) {
|
79
|
-
setUiState(uiState);
|
80
|
-
}
|
50
|
+
searchClient: algoliasearch(algolia.appId, algolia.apiKey),
|
51
|
+
searchFunction(helper) {
|
52
|
+
if (helper.state.query) {
|
53
|
+
let innerLoading = '<i class="scoicon sco-loading-line sco-spin"></i>';
|
54
|
+
document.getElementById("algolia-hits").innerHTML = innerLoading;
|
55
|
+
helper.search();
|
81
56
|
}
|
82
|
-
}
|
83
|
-
)
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
57
|
+
},
|
58
|
+
});
|
59
|
+
|
60
|
+
const configure = instantsearch.widgets.configure({
|
61
|
+
hitsPerPage: algolia.hits.per_page ?? 5,
|
62
|
+
});
|
63
|
+
|
64
|
+
const searchBox = instantsearch.widgets.searchBox({
|
65
|
+
container: "#algolia-search-input",
|
66
|
+
showReset: false,
|
67
|
+
showSubmit: false,
|
68
|
+
placeholder: GLOBAL_CONFIG.lang.search.placeholder,
|
69
|
+
showLoadingIndicator: true,
|
70
|
+
searchOnEnterKeyPressOnly: true,
|
71
|
+
searchAsYouType: false,
|
72
|
+
});
|
73
|
+
|
74
|
+
const hits = instantsearch.widgets.hits({
|
75
|
+
container: "#algolia-hits",
|
76
|
+
templates: {
|
77
|
+
item(data) {
|
78
|
+
const link = data.permalink ? data.permalink : GLOBAL_CONFIG.root + data.path;
|
79
|
+
const result = data._highlightResult;
|
80
|
+
const loadingLogo = document.querySelector("#algolia-hits .sco-spin");
|
81
|
+
if (loadingLogo) {
|
82
|
+
loadingLogo.style.display = "none";
|
100
83
|
}
|
84
|
+
setTimeout(() => {
|
85
|
+
document.querySelector("#algolia-search .ais-SearchBox-input").focus();
|
86
|
+
}, 200);
|
87
|
+
return `
|
88
|
+
<a href="${link}" class="algolia-hit-item-link">
|
89
|
+
<span class="algolia-hits-item-title">${result.title.value || "no-title"}</span>
|
90
|
+
</a>`;
|
101
91
|
},
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
)
|
107
|
-
|
108
|
-
search.addWidget(
|
109
|
-
instantsearch.widgets.stats({
|
110
|
-
container: '#algolia-stats',
|
111
|
-
templates: {
|
112
|
-
text(data) {
|
113
|
-
const stats = GLOBAL_CONFIG.lang.search.hit.replace(/\$\{hits}/, data.nbHits).replace(/\$\{time}/, data.processingTimeMS);
|
114
|
-
return `${stats}`;
|
92
|
+
empty: function (data) {
|
93
|
+
const loadingLogo = document.querySelector("#algolia-hits .sco-spin");
|
94
|
+
if (loadingLogo) {
|
95
|
+
loadingLogo.style.display = "none";
|
115
96
|
}
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
97
|
+
setTimeout(() => {
|
98
|
+
document.querySelector("#algolia-search .ais-SearchBox-input").focus();
|
99
|
+
}, 200);
|
100
|
+
return (
|
101
|
+
'<div id="algolia-hits-empty">' +
|
102
|
+
GLOBAL_CONFIG.lang.search.empty.replace(/\$\{query}/, data.query) +
|
103
|
+
"</div>"
|
104
|
+
);
|
105
|
+
},
|
106
|
+
},
|
107
|
+
cssClasses: {
|
108
|
+
item: "algolia-hit-item",
|
109
|
+
},
|
110
|
+
});
|
111
|
+
|
112
|
+
const pagination = instantsearch.widgets.pagination({
|
113
|
+
container: "#algolia-pagination",
|
114
|
+
totalPages: algolia.hits.per_page ?? 5,
|
115
|
+
scrollTo: false,
|
116
|
+
showFirstLast: false,
|
117
|
+
templates: {
|
118
|
+
first: '<i class="scoicon sco-show-left-line"></i>',
|
119
|
+
last: '<i class="scoicon sco-show-right-line"></i>',
|
120
|
+
previous: '<i class="scoicon sco-arrow-left-bold"></i>',
|
121
|
+
next: '<i class="scoicon sco-arrow-right-bold"></i>',
|
122
|
+
},
|
123
|
+
cssClasses: {
|
124
|
+
root: "pagination",
|
125
|
+
item: "pagination-item",
|
126
|
+
link: "page-number",
|
127
|
+
active: "current",
|
128
|
+
disabled: "disabled-item",
|
129
|
+
},
|
130
|
+
});
|
131
|
+
|
132
|
+
const stats = instantsearch.widgets.stats({
|
133
|
+
container: "#algolia-tips > #algolia-stats",
|
134
|
+
templates: {
|
135
|
+
text: function (data) {
|
136
|
+
const stats = GLOBAL_CONFIG.lang.search.hit
|
137
|
+
.replace(/\$\{hits}/, data.nbHits)
|
138
|
+
.replace(/\$\{time}/, data.processingTimeMS);
|
139
|
+
return `<hr>${stats}`;
|
132
140
|
},
|
133
|
-
}
|
134
|
-
)
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
+
},
|
142
|
+
});
|
143
|
+
|
144
|
+
const powerBy = instantsearch.widgets.poweredBy({
|
145
|
+
container: "#algolia-tips > #algolia-poweredBy",
|
146
|
+
});
|
147
|
+
|
148
|
+
search.addWidgets([configure, searchBox,stats, hits,powerBy, pagination]); // add the widgets to the instantsearch instance
|
149
|
+
|
150
|
+
search.start();
|
151
|
+
|
152
|
+
searchClickFn();
|
153
|
+
searchFnOnce();
|
154
|
+
|
155
|
+
window.addEventListener("pjax:complete", () => {
|
156
|
+
!utils.isHidden($searchMask) && closeSearch();
|
157
|
+
searchClickFn();
|
158
|
+
});
|
159
|
+
|
160
|
+
window.pjax &&
|
161
|
+
search.on("render", () => {
|
162
|
+
window.pjax.refresh(document.getElementById("algolia-hits"));
|
163
|
+
});
|
164
|
+
});
|
@@ -1,171 +1,146 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
$
|
4
|
-
$
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
}
|
20
|
-
|
1
|
+
window.onload = () => {
|
2
|
+
let idx, store = [];
|
3
|
+
const $searchMask = document.getElementById("search-mask");
|
4
|
+
const $searchDialog = document.querySelector("#local-search .search-dialog");
|
5
|
+
const openSearch = () => {
|
6
|
+
utils.animateIn($searchMask, "to_show 0.5s");
|
7
|
+
$searchDialog.style.display = "block";
|
8
|
+
setTimeout(() => {
|
9
|
+
document.querySelector("#local-search .search-box-input").focus();
|
10
|
+
}, 100);
|
11
|
+
document.addEventListener("keydown", function f(event) {
|
12
|
+
if (event.code === "Escape") {
|
13
|
+
closeSearch();
|
14
|
+
document.removeEventListener("keydown", f);
|
15
|
+
}
|
16
|
+
});
|
17
|
+
fixSafariHeight();
|
18
|
+
window.addEventListener("resize", fixSafariHeight);
|
19
|
+
};
|
20
|
+
const fixSafariHeight = () => {
|
21
|
+
if (window.innerWidth < 768) {
|
22
|
+
$searchDialog.style.setProperty("--search-height", window.innerHeight + "px");
|
23
|
+
}
|
24
|
+
};
|
25
|
+
const closeSearch = () => {
|
26
|
+
utils.animateOut($searchDialog, "search_close .5s");
|
27
|
+
utils.animateOut($searchMask, "to_hide 0.5s");
|
28
|
+
window.removeEventListener("resize", fixSafariHeight);
|
29
|
+
};
|
30
|
+
utils.addEventListenerPjax(document.querySelector("#search-button > .search"), "click", openSearch);
|
31
|
+
utils.addEventListenerPjax(document.querySelector("#local-search .search-close-button"), "click", closeSearch);
|
32
|
+
function initLunr() {
|
33
|
+
fetch("/search.xml")
|
34
|
+
.then(response => response.text())
|
35
|
+
.then(data => {
|
36
|
+
let parser = new DOMParser();
|
37
|
+
let xmlDoc = parser.parseFromString(data, "text/xml");
|
38
|
+
let entries = xmlDoc.getElementsByTagName("entry");
|
39
|
+
for (let i = 0; i < entries.length; i++) {
|
40
|
+
let entry = entries[i];
|
41
|
+
let title = entry.getElementsByTagName("title")[0].textContent;
|
42
|
+
let link = entry.getElementsByTagName("url")[0].textContent;
|
43
|
+
let content = entry.getElementsByTagName("content")[0].textContent;
|
44
|
+
store.push({
|
45
|
+
'title': title,
|
46
|
+
'link': link,
|
47
|
+
'content': content
|
48
|
+
});
|
49
|
+
}
|
21
50
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
51
|
+
idx = lunr(function () {
|
52
|
+
this.ref('link');
|
53
|
+
this.field('title', {boost: 10});
|
54
|
+
this.field('content');
|
26
55
|
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
title: item.querySelector('title').textContent,
|
34
|
-
content: item.querySelector('content') && item.querySelector('content').textContent,
|
35
|
-
url: item.querySelector('url').textContent
|
36
|
-
}
|
37
|
-
})
|
38
|
-
if (response.ok) {
|
39
|
-
const $loadDataItem = document.getElementById('loading-database')
|
40
|
-
$loadDataItem.nextElementSibling.style.display = 'block'
|
41
|
-
$loadDataItem.remove()
|
56
|
+
store.forEach(function (doc) {
|
57
|
+
this.add(doc);
|
58
|
+
}, this);
|
59
|
+
});
|
60
|
+
})
|
61
|
+
.catch(err => console.error("Error loading search data:", err));
|
42
62
|
}
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
if (!GLOBAL_CONFIG.localsearch.preload && dataObj === null) dataObj = this.fetchData(GLOBAL_CONFIG.localsearch.path)
|
48
|
-
$input.addEventListener('input', function type() {
|
49
|
-
const keywords = this.value.trim().toLowerCase().split(/[\s]+/)
|
50
|
-
if (keywords[0] !== '') $loadingStatus.innerHTML = '<i class="scoicon sco-loading-line"></i><span>加载中</span>'
|
51
|
-
else {
|
52
|
-
$resultContent.innerHTML = ''
|
53
|
-
return
|
54
|
-
}
|
63
|
+
let query = ''
|
64
|
+
let currentPage = 0;
|
65
|
+
const resultsPerPage = 10;
|
66
|
+
let results = [];
|
55
67
|
|
56
|
-
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
let indexContent = -1
|
67
|
-
let firstOccur = -1
|
68
|
-
// only match articles with not empty titles and contents
|
69
|
-
if (dataTitle !== '' || dataContent !== '') {
|
70
|
-
keywords.forEach((keyword, i) => {
|
71
|
-
indexTitle = dataTitle.indexOf(keyword)
|
72
|
-
indexContent = dataContent.indexOf(keyword)
|
73
|
-
if (indexTitle < 0 && indexContent < 0) {
|
74
|
-
isMatch = false
|
75
|
-
} else {
|
76
|
-
if (indexContent < 0) {
|
77
|
-
indexContent = 0
|
68
|
+
function initUI() {
|
69
|
+
const $results = document.getElementById("search-results");
|
70
|
+
const $search = document.getElementById("search-input");
|
71
|
+
$search.addEventListener('keydown', function (e) {
|
72
|
+
if (e.keyCode === 13) {
|
73
|
+
$results.innerHTML = '';
|
74
|
+
query = this.value;
|
75
|
+
results = search(query);
|
76
|
+
renderResults(results, currentPage);
|
77
|
+
renderPagination(results.length);
|
78
78
|
}
|
79
|
-
if (i === 0) {
|
80
|
-
firstOccur = indexContent
|
81
|
-
}
|
82
|
-
}
|
83
|
-
})
|
84
|
-
} else {
|
85
|
-
isMatch = false
|
86
|
-
}
|
87
|
-
|
88
|
-
// show search results
|
89
|
-
if (isMatch) {
|
90
|
-
if (firstOccur >= 0) {
|
91
|
-
// cut out 130 characters
|
92
|
-
let start = firstOccur - 30
|
93
|
-
let end = firstOccur + 100
|
94
|
-
let pre = ''
|
95
|
-
let post = ''
|
96
|
-
|
97
|
-
if (start < 0) {
|
98
|
-
start = 0
|
99
|
-
}
|
100
|
-
|
101
|
-
if (start === 0) {
|
102
|
-
end = 100
|
103
|
-
} else {
|
104
|
-
pre = '...'
|
105
|
-
}
|
106
|
-
|
107
|
-
if (end > dataContent.length) {
|
108
|
-
end = dataContent.length
|
109
|
-
} else {
|
110
|
-
post = '...'
|
111
|
-
}
|
112
|
-
|
113
|
-
let matchContent = dataContent.substring(start, end)
|
114
|
-
// highlight all keywords
|
115
|
-
keywords.forEach(keyword => {
|
116
|
-
const regex = new RegExp(`(?!<[^>]*?)(${keyword})(?![^<]*?>)`, 'gi')
|
117
|
-
matchContent = matchContent.replaceAll(regex, '<span class="search-keyword">$1</span>')
|
118
|
-
dataTitle = dataTitle.replaceAll(regex, '<span class="search-keyword">$1</span>')
|
119
|
-
})
|
120
|
-
|
121
|
-
str += '<div class="search__hit-item"><a href="' + dataUrl + '"><span class="search-result-title">' + dataTitle + '</span>'
|
122
|
-
count += 1
|
123
|
-
if (dataContent !== '') {
|
124
|
-
str += '<div class="search-result">' + pre + matchContent + post + '</div>'
|
125
|
-
}
|
126
79
|
}
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
80
|
+
)
|
81
|
+
;
|
82
|
+
}
|
83
|
+
function search(query) {
|
84
|
+
return idx.search(query).map(result => {
|
85
|
+
return store.filter(page => {
|
86
|
+
return page.link === result.ref;
|
87
|
+
})[0];
|
88
|
+
});
|
89
|
+
}
|
90
|
+
function renderResults(results, page) {
|
91
|
+
const $search_results = document.getElementById("search-results");
|
92
|
+
$search_results.innerHTML = '';
|
93
|
+
const $tips = document.getElementById("search-tips")
|
94
|
+
$tips.innerHTML = '';
|
95
|
+
const start = page * resultsPerPage;
|
96
|
+
const end = start + resultsPerPage;
|
97
|
+
if (!results.length) {
|
98
|
+
const $empty = document.createElement("span");
|
99
|
+
$empty.className = "search-result-empty";
|
100
|
+
$empty.textContent = GLOBAL_CONFIG.lang.search.empty.replace(/\$\{query}/, query);
|
101
|
+
$search_results.appendChild($empty);
|
102
|
+
return;
|
134
103
|
}
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
104
|
+
results.slice(start, end).forEach(function (result) {
|
105
|
+
const $result = document.createElement("li");
|
106
|
+
$result.className = "search-result-item";
|
107
|
+
const $link = document.createElement("a");
|
108
|
+
$link.className = "search-result-title";
|
109
|
+
$link.href = result.link;
|
110
|
+
$link.textContent = result.title;
|
111
|
+
$result.appendChild($link);
|
112
|
+
$search_results.appendChild($result);
|
113
|
+
});
|
114
|
+
const count = document.createElement("span");
|
115
|
+
count.className = "search-result-count";
|
116
|
+
count.innerHTML = `共 <b>${results.length}</b> 条结果`;
|
117
|
+
$tips.appendChild(count);
|
118
|
+
}
|
119
|
+
function renderPagination(totalResults) {
|
120
|
+
const totalPages = Math.ceil(totalResults / resultsPerPage);
|
121
|
+
const paginationContainer = document.getElementById("search-pagination");
|
122
|
+
paginationContainer.innerHTML = '';
|
123
|
+
const paginationList = document.createElement("ul");
|
124
|
+
paginationList.className = "pagination-list";
|
142
125
|
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
126
|
+
for (let i = 0; i < totalPages; i++) {
|
127
|
+
const button = document.createElement("li");
|
128
|
+
button.className = "pagination-item";
|
129
|
+
button.textContent = i + 1;
|
130
|
+
if (i === currentPage) {
|
131
|
+
button.classList.add('select');
|
132
|
+
}
|
133
|
+
button.addEventListener('click', function () {
|
134
|
+
currentPage = i;
|
135
|
+
renderResults(results, i);
|
136
|
+
});
|
137
|
+
paginationList.appendChild(button);
|
138
|
+
}
|
139
|
+
paginationContainer.appendChild(paginationList);
|
140
|
+
}
|
141
|
+
initLunr();
|
142
|
+
initUI();
|
143
|
+
window.addEventListener('DOMContentLoaded', (event) => {
|
144
|
+
initUI();
|
152
145
|
});
|
153
|
-
|
154
|
-
t.dispatchEvent(evt);
|
155
|
-
})
|
156
|
-
}
|
157
|
-
|
158
|
-
const searchClickFnOnce = () => {
|
159
|
-
document.querySelector('#local-search .search-close-button').addEventListener('click', search.closeSearch)
|
160
|
-
$searchMask.addEventListener('click', search.closeSearch)
|
161
|
-
if (GLOBAL_CONFIG.localsearch.preload) dataObj = search.fetchData(GLOBAL_CONFIG.localsearch.path)
|
162
|
-
}
|
163
|
-
|
164
|
-
window.addEventListener('load', () => {
|
165
|
-
searchClickFn()
|
166
|
-
searchClickFnOnce()
|
167
|
-
})
|
168
|
-
|
169
|
-
window.addEventListener('pjax:complete', () => {
|
170
|
-
searchClickFn()
|
171
|
-
})
|
146
|
+
}
|
package/source/js/utils.js
CHANGED
@@ -143,5 +143,34 @@ const utils = {
|
|
143
143
|
})
|
144
144
|
},
|
145
145
|
isMobile: () => /Android|webOS|iPhone|iPad|iPod|BlackBerry|IEMobile|Opera Mini/i.test(navigator.userAgent),
|
146
|
-
isHidden: e => 0 === e.offsetHeight && 0 === e.offsetWidth
|
146
|
+
isHidden: e => 0 === e.offsetHeight && 0 === e.offsetWidth,
|
147
|
+
addEventListenerPjax: function (element, eventType, callback, useCapture = false) {
|
148
|
+
element.addEventListener(eventType, callback, useCapture);
|
149
|
+
utils.addGlobalFn("pjax", function () {
|
150
|
+
element.removeEventListener(eventType, callback, useCapture);
|
151
|
+
});
|
152
|
+
},
|
153
|
+
addGlobalFn: (key, fn, name = false, parent = window) => {
|
154
|
+
const globalFn = parent.globalFn || {}
|
155
|
+
const keyObj = globalFn[key] || {}
|
156
|
+
|
157
|
+
if (name && keyObj[name]) return
|
158
|
+
|
159
|
+
name = name || Object.keys(keyObj).length
|
160
|
+
keyObj[name] = fn
|
161
|
+
globalFn[key] = keyObj
|
162
|
+
parent.globalFn = globalFn
|
163
|
+
},
|
164
|
+
animateIn: (ele, text) => {
|
165
|
+
ele.style.display = 'block'
|
166
|
+
ele.style.animation = text
|
167
|
+
},
|
168
|
+
animateOut: (ele, text) => {
|
169
|
+
ele.addEventListener('animationend', function f() {
|
170
|
+
ele.style.display = ''
|
171
|
+
ele.style.animation = ''
|
172
|
+
ele.removeEventListener('animationend', f)
|
173
|
+
})
|
174
|
+
ele.style.animation = text
|
175
|
+
}
|
147
176
|
}
|