hexo-theme-shokax 0.5.0-dev-5c5076b → 0.5.0-dev-f96faf9
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/README.md +2 -3
- package/_config.yml +18 -13
- package/languages/en.yml +2 -0
- package/languages/ja.yml +2 -0
- package/languages/zh-CN.yml +2 -0
- package/languages/zh-HK.yml +2 -0
- package/languages/zh-TW.yml +2 -0
- package/layout/_mixin/card.pug +1 -1
- package/layout/_partials/layout.pug +10 -5
- package/layout/_partials/post/footer.pug +8 -5
- package/package.json +31 -21
- package/scripts/generaters/config.js +12 -7
- package/scripts/generaters/images.js +9 -8
- package/scripts/generaters/index.js +48 -38
- package/scripts/generaters/script.js +19 -31
- package/scripts/generaters/summary_ai.js +130 -0
- package/scripts/helpers/engine.js +2 -4
- package/scripts/helpers/summary_ai.js +1 -108
- package/scripts/plugin/index.js +32 -69
- package/source/css/_common/outline/sidebar/quick.styl +1 -1
- package/source/css/_common/outline/sidebar/sidebar.styl +2 -0
- package/source/js/_app/components/sidebar.ts +3 -1
- package/source/js/_app/library/anime.ts +30 -19
- package/source/js/_app/library/declare.d.ts +1 -0
- package/source/js/_app/page/fancybox.ts +11 -10
- package/source/js/_app/pjax/refresh.ts +9 -0
- package/source/js/_app/pjax/siteInit.ts +8 -0
- package/scripts/plugin/lib/injects-point.js +0 -41
- package/scripts/plugin/lib/injects.js +0 -105
@@ -0,0 +1,130 @@
|
|
1
|
+
var __create = Object.create;
|
2
|
+
var __defProp = Object.defineProperty;
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
5
|
+
var __getProtoOf = Object.getPrototypeOf;
|
6
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
7
|
+
var __copyProps = (to, from, except, desc) => {
|
8
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
9
|
+
for (let key of __getOwnPropNames(from))
|
10
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
11
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
12
|
+
}
|
13
|
+
return to;
|
14
|
+
};
|
15
|
+
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
16
|
+
// If the importer is in node compatibility mode or this is not an ESM
|
17
|
+
// file that has been converted to a CommonJS file using a Babel-
|
18
|
+
// compatible transform (i.e. "__esModule" has not been set), then set
|
19
|
+
// "default" to the CommonJS "module.exports" for node compatibility.
|
20
|
+
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
21
|
+
mod
|
22
|
+
));
|
23
|
+
var import_node_crypto = require("node:crypto");
|
24
|
+
var import_promises = __toESM(require("node:fs/promises"));
|
25
|
+
async function getSummaryByAPI(content) {
|
26
|
+
const apiKey = hexo.theme.config.summary.apiKey;
|
27
|
+
const apiUrl = hexo.theme.config.summary.apiUrl;
|
28
|
+
const model = hexo.theme.config.summary.model;
|
29
|
+
const temperature = hexo.theme.config.summary.temperature ?? 1.3;
|
30
|
+
const initalPrompt = hexo.theme.config.summary.initalPrompt;
|
31
|
+
const res = await fetch(apiUrl, {
|
32
|
+
method: "POST",
|
33
|
+
headers: {
|
34
|
+
"Content-Type": "application/json",
|
35
|
+
"Authorization": `Bearer ${apiKey}`
|
36
|
+
},
|
37
|
+
body: JSON.stringify({
|
38
|
+
model,
|
39
|
+
messages: [{
|
40
|
+
role: "system",
|
41
|
+
content: `${initalPrompt}`
|
42
|
+
}, {
|
43
|
+
role: "user",
|
44
|
+
content: `${content}`
|
45
|
+
}],
|
46
|
+
temperature
|
47
|
+
})
|
48
|
+
});
|
49
|
+
if (!res.ok) {
|
50
|
+
throw new Error(`Error: ${res.status} ${res.statusText}`);
|
51
|
+
}
|
52
|
+
const data = await res.json();
|
53
|
+
if (data.error) {
|
54
|
+
throw new Error(`Error: ${data.error.message}`);
|
55
|
+
}
|
56
|
+
const summary = data.choices[0].message.content;
|
57
|
+
return summary;
|
58
|
+
}
|
59
|
+
class SummaryDatabase {
|
60
|
+
fileChanged;
|
61
|
+
data;
|
62
|
+
constructor() {
|
63
|
+
this.fileChanged = false;
|
64
|
+
this.data = {
|
65
|
+
version: 2,
|
66
|
+
features: {
|
67
|
+
incremental: false
|
68
|
+
},
|
69
|
+
summaries: {}
|
70
|
+
};
|
71
|
+
}
|
72
|
+
async readDB() {
|
73
|
+
try {
|
74
|
+
await import_promises.default.access("summary.json");
|
75
|
+
this.data = JSON.parse(await import_promises.default.readFile("summary.json", "utf-8"));
|
76
|
+
} catch (error) {
|
77
|
+
}
|
78
|
+
if (this.data.version !== 2) {
|
79
|
+
throw new Error(`Incompatible version of summary database: ${this.data.version}`);
|
80
|
+
}
|
81
|
+
}
|
82
|
+
async writeDB() {
|
83
|
+
if (this.fileChanged) {
|
84
|
+
await import_promises.default.writeFile("summary.json", JSON.stringify(this.data));
|
85
|
+
}
|
86
|
+
}
|
87
|
+
async getPostSummary(path, content) {
|
88
|
+
const pathHash = (0, import_node_crypto.createHash)("sha256").update(path).digest("hex");
|
89
|
+
const contentHash = (0, import_node_crypto.createHash)("sha256").update(content).digest("hex");
|
90
|
+
if (this.data.summaries[pathHash]?.sha256 === contentHash) {
|
91
|
+
return this.data.summaries[pathHash].summary;
|
92
|
+
} else {
|
93
|
+
const summaryContent = await getSummaryByAPI(content);
|
94
|
+
this.data.summaries[pathHash] = {
|
95
|
+
summary: summaryContent,
|
96
|
+
sha256: contentHash
|
97
|
+
};
|
98
|
+
this.fileChanged = true;
|
99
|
+
return summaryContent;
|
100
|
+
}
|
101
|
+
}
|
102
|
+
}
|
103
|
+
hexo.extend.generator.register("summary_ai", async function(locals) {
|
104
|
+
const posts = locals.posts;
|
105
|
+
if (!hexo.theme.config.summary.enable) {
|
106
|
+
return;
|
107
|
+
}
|
108
|
+
const db = new SummaryDatabase();
|
109
|
+
await db.readDB();
|
110
|
+
const postArray = posts.toArray();
|
111
|
+
const pLimit = require("@common.js/p-limit").default;
|
112
|
+
const concurrencyLimit = pLimit(hexo.theme.config.summary?.concurrency || 5);
|
113
|
+
const processingPromises = postArray.map((post) => concurrencyLimit(async () => {
|
114
|
+
const content = post.content;
|
115
|
+
const path = post.path;
|
116
|
+
const published = post.published;
|
117
|
+
if (content && path && published && content.length > 0) {
|
118
|
+
try {
|
119
|
+
const summary = await db.getPostSummary(path, content);
|
120
|
+
post.summary = summary;
|
121
|
+
} catch (error) {
|
122
|
+
hexo.log.error(`[ShokaX Summary AI] \u5904\u7406\u6587\u7AE0 ${path} \u65F6\u51FA\u9519:`, error.message);
|
123
|
+
post.summary = `${error.message}`;
|
124
|
+
}
|
125
|
+
}
|
126
|
+
}));
|
127
|
+
await Promise.all(processingPromises);
|
128
|
+
await db.writeDB();
|
129
|
+
hexo.log.info(`[ShokaX Summary AI] \u6240\u6709\u6587\u7AE0\u6458\u8981\u5904\u7406\u5B8C\u6210\uFF0C\u5DF2\u4FDD\u5B58\u5230\u6570\u636E\u5E93`);
|
130
|
+
});
|
@@ -23,7 +23,6 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
|
|
23
23
|
));
|
24
24
|
var import_hexo_util = require("hexo-util");
|
25
25
|
var import_node_fs = __toESM(require("node:fs"));
|
26
|
-
const randomServer = parseInt(String(Math.random() * 4), 10) + 1;
|
27
26
|
const randomBG = function(count = 1, image_server = null, image_list = []) {
|
28
27
|
let i;
|
29
28
|
if (image_server) {
|
@@ -37,13 +36,12 @@ const randomBG = function(count = 1, image_server = null, image_list = []) {
|
|
37
36
|
return image_server + "?" + Math.floor(Math.random() * 999999);
|
38
37
|
}
|
39
38
|
const parseImage = function(img, size) {
|
40
|
-
if (img.startsWith("//") || img.startsWith("
|
39
|
+
if (img.startsWith("//") || img.startsWith("https")) {
|
41
40
|
return img;
|
42
41
|
} else if (hexo.theme.config.experiments?.usingRelative) {
|
43
42
|
return img;
|
44
43
|
} else {
|
45
|
-
|
46
|
-
return `https://tva${randomServer}.sinaimg.cn/` + size + "/" + img;
|
44
|
+
throw new Error("Image URL is not valid: " + img);
|
47
45
|
}
|
48
46
|
};
|
49
47
|
if (count && count > 1) {
|
@@ -1,112 +1,5 @@
|
|
1
|
-
var __create = Object.create;
|
2
|
-
var __defProp = Object.defineProperty;
|
3
|
-
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
4
|
-
var __getOwnPropNames = Object.getOwnPropertyNames;
|
5
|
-
var __getProtoOf = Object.getPrototypeOf;
|
6
|
-
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
7
|
-
var __copyProps = (to, from, except, desc) => {
|
8
|
-
if (from && typeof from === "object" || typeof from === "function") {
|
9
|
-
for (let key of __getOwnPropNames(from))
|
10
|
-
if (!__hasOwnProp.call(to, key) && key !== except)
|
11
|
-
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
12
|
-
}
|
13
|
-
return to;
|
14
|
-
};
|
15
|
-
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
16
|
-
// If the importer is in node compatibility mode or this is not an ESM
|
17
|
-
// file that has been converted to a CommonJS file using a Babel-
|
18
|
-
// compatible transform (i.e. "__esModule" has not been set), then set
|
19
|
-
// "default" to the CommonJS "module.exports" for node compatibility.
|
20
|
-
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
21
|
-
mod
|
22
|
-
));
|
23
|
-
var import_node_fs = __toESM(require("node:fs"));
|
24
|
-
function getContent(post) {
|
25
|
-
return post?.raw ?? post?._content ?? post.content;
|
26
|
-
}
|
27
|
-
let db;
|
28
|
-
function postMessage(path, content, dbPath, startMessage) {
|
29
|
-
if (import_node_fs.default.existsSync("summary.json")) {
|
30
|
-
db = JSON.parse(import_node_fs.default.readFileSync("summary.json", { encoding: "utf-8" }));
|
31
|
-
} else {
|
32
|
-
db = {};
|
33
|
-
}
|
34
|
-
const config = hexo.theme.config.summary;
|
35
|
-
if (config.enable) {
|
36
|
-
if (typeof db?.[path] !== "undefined" && typeof db?.[path]?.[dbPath] !== "undefined") {
|
37
|
-
return db[path][dbPath];
|
38
|
-
} else {
|
39
|
-
if (typeof db?.[path] === "undefined") {
|
40
|
-
db[path] = {};
|
41
|
-
} else {
|
42
|
-
db[path][dbPath] = "";
|
43
|
-
}
|
44
|
-
}
|
45
|
-
if (config.mode === "openai") {
|
46
|
-
const request = () => {
|
47
|
-
fetch(`${config.openai.remote}/v1/chat/completions`, {
|
48
|
-
method: "POST",
|
49
|
-
headers: requestHeaders,
|
50
|
-
body: JSON.stringify(requestBody)
|
51
|
-
}).then((response) => {
|
52
|
-
if (!response.ok) {
|
53
|
-
throw Error("ERROR: Failed to get summary from Openai API");
|
54
|
-
}
|
55
|
-
response.json().then((data) => {
|
56
|
-
const summary = data.choices[0].message.content;
|
57
|
-
try {
|
58
|
-
db[path][dbPath] = summary;
|
59
|
-
} catch (e) {
|
60
|
-
db ??= {};
|
61
|
-
db[path] ??= {};
|
62
|
-
db[path][dbPath] ??= "";
|
63
|
-
db[path][dbPath] = summary;
|
64
|
-
}
|
65
|
-
import_node_fs.default.writeFileSync("summary.json", JSON.stringify(db));
|
66
|
-
if (import_node_fs.default.existsSync("requested.lock")) {
|
67
|
-
import_node_fs.default.unlinkSync("requested.lock");
|
68
|
-
}
|
69
|
-
return summary;
|
70
|
-
});
|
71
|
-
});
|
72
|
-
};
|
73
|
-
const checkTime = (waitTime) => {
|
74
|
-
if (import_node_fs.default.existsSync("request.lock")) {
|
75
|
-
if (import_node_fs.default.existsSync("requested.lock")) {
|
76
|
-
setTimeout(checkTime, 1e3 * waitTime);
|
77
|
-
return;
|
78
|
-
}
|
79
|
-
import_node_fs.default.writeFileSync("requested.lock", "");
|
80
|
-
setTimeout(request, 1e3 * 2.5 * waitTime);
|
81
|
-
import_node_fs.default.unlinkSync("request.lock");
|
82
|
-
} else {
|
83
|
-
import_node_fs.default.writeFileSync("request.lock", "");
|
84
|
-
request();
|
85
|
-
}
|
86
|
-
};
|
87
|
-
const requestHeaders = {
|
88
|
-
"Content-Type": "application/json",
|
89
|
-
Authorization: `Bearer ${config.openai.apikey}`
|
90
|
-
};
|
91
|
-
const requestBody = {
|
92
|
-
model: "gpt-3.5-turbo",
|
93
|
-
messages: [{ role: "user", content: `${startMessage} ${content}` }],
|
94
|
-
temperature: 0.7
|
95
|
-
};
|
96
|
-
if (config.pricing === "trial") {
|
97
|
-
hexo.log.info("Requesting OpenAI API... (3 RPM mode)");
|
98
|
-
hexo.log.info("It may take 20 minutes or more (depending on the number of articles, each one takes 25 seconds)");
|
99
|
-
checkTime(10);
|
100
|
-
} else {
|
101
|
-
hexo.log.info("Requesting OpenAI API... (60 RPM mode)");
|
102
|
-
checkTime(0.5);
|
103
|
-
}
|
104
|
-
} else {
|
105
|
-
}
|
106
|
-
}
|
107
|
-
}
|
108
1
|
hexo.extend.helper.register("get_summary", (post) => {
|
109
|
-
return
|
2
|
+
return post.summary;
|
110
3
|
});
|
111
4
|
hexo.extend.helper.register("get_introduce", () => {
|
112
5
|
return hexo.theme.config.summary.introduce;
|
package/scripts/plugin/index.js
CHANGED
@@ -1,75 +1,38 @@
|
|
1
|
-
var __create = Object.create;
|
2
|
-
var __defProp = Object.defineProperty;
|
3
|
-
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
4
|
-
var __getOwnPropNames = Object.getOwnPropertyNames;
|
5
|
-
var __getProtoOf = Object.getPrototypeOf;
|
6
|
-
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
7
|
-
var __copyProps = (to, from, except, desc) => {
|
8
|
-
if (from && typeof from === "object" || typeof from === "function") {
|
9
|
-
for (let key of __getOwnPropNames(from))
|
10
|
-
if (!__hasOwnProp.call(to, key) && key !== except)
|
11
|
-
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
12
|
-
}
|
13
|
-
return to;
|
14
|
-
};
|
15
|
-
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
|
16
|
-
// If the importer is in node compatibility mode or this is not an ESM
|
17
|
-
// file that has been converted to a CommonJS file using a Babel-
|
18
|
-
// compatible transform (i.e. "__esModule" has not been set), then set
|
19
|
-
// "default" to the CommonJS "module.exports" for node compatibility.
|
20
|
-
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
|
21
|
-
mod
|
22
|
-
));
|
23
|
-
var import_injects = __toESM(require("./lib/injects"));
|
24
1
|
var import_package = require("../../package.json");
|
25
|
-
var
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
hexo.on("generateBefore", () => {
|
32
|
-
(0, import_injects.default)(hexo);
|
33
|
-
fs.rmSync("./shokaxTemp", { force: true, recursive: true });
|
34
|
-
if (fs.existsSync("cf-patch.js")) {
|
35
|
-
fs.unlinkSync("cf-patch.js");
|
36
|
-
}
|
37
|
-
if (fs.existsSync("request.lock")) {
|
38
|
-
fs.unlinkSync("request.lock");
|
39
|
-
}
|
40
|
-
if (fs.existsSync("requested.lock")) {
|
41
|
-
fs.unlinkSync("requested.lock");
|
2
|
+
var import_promises = require("node:fs/promises");
|
3
|
+
hexo.on("generateBefore", async () => {
|
4
|
+
await (0, import_promises.rm)("./shokaxTemp", { force: true, recursive: true });
|
5
|
+
try {
|
6
|
+
await (0, import_promises.unlink)("cf-patch.js");
|
7
|
+
} catch (e) {
|
42
8
|
}
|
43
9
|
});
|
44
|
-
hexo.on("generateAfter", () => {
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
try {
|
50
|
-
const latest = resp["version"];
|
51
|
-
const current = import_package.version.split(".");
|
52
|
-
let isOutdated = false;
|
53
|
-
for (let i = 0; i < Math.max(latest.length, current.length); i++) {
|
54
|
-
if (!current[i] || latest[i] > current[i]) {
|
55
|
-
isOutdated = true;
|
56
|
-
break;
|
57
|
-
}
|
58
|
-
if (latest[i] < current[i]) {
|
59
|
-
break;
|
60
|
-
}
|
61
|
-
}
|
62
|
-
if (isOutdated) {
|
63
|
-
hexo.log.warn(`Your theme ShokaX is outdated. Current version: v${current.join(".")}, latest version: v${latest.join(".")}`);
|
64
|
-
hexo.log.warn("Visit https://github.com/theme-shoka-x/hexo-theme-shokaX/releases for more information.");
|
65
|
-
}
|
66
|
-
} catch (e) {
|
67
|
-
hexo.log.warn("Failed to detect version info. Error message:");
|
68
|
-
hexo.log.warn(e);
|
10
|
+
hexo.on("generateAfter", async () => {
|
11
|
+
try {
|
12
|
+
const res = await fetch("https://registry.npmmirror.com/hexo-theme-shokax/latest", {
|
13
|
+
headers: {
|
14
|
+
"User-Agent": "ShokaX Client (hexo-theme-shokax)"
|
69
15
|
}
|
70
|
-
}).catch((e) => {
|
71
|
-
hexo.log.warn("Failed to detect version info. Error message:");
|
72
|
-
hexo.log.warn(e);
|
73
16
|
});
|
74
|
-
|
17
|
+
const resp = await res.json();
|
18
|
+
const latest = resp.version;
|
19
|
+
const current = import_package.version.split(".");
|
20
|
+
let isOutdated = false;
|
21
|
+
for (let i = 0; i < Math.max(latest.length, current.length); i++) {
|
22
|
+
if (!current[i] || latest[i] > current[i]) {
|
23
|
+
isOutdated = true;
|
24
|
+
break;
|
25
|
+
}
|
26
|
+
if (latest[i] < current[i]) {
|
27
|
+
break;
|
28
|
+
}
|
29
|
+
}
|
30
|
+
if (isOutdated) {
|
31
|
+
hexo.log.warn(`Your theme ShokaX is outdated. Current version: v${current.join(".")}, latest version: v${latest.join(".")}`);
|
32
|
+
hexo.log.warn("Visit https://github.com/theme-shoka-x/hexo-theme-shokaX/releases for more information.");
|
33
|
+
}
|
34
|
+
} catch (e) {
|
35
|
+
hexo.log.warn("Failed to detect version info. Error message:");
|
36
|
+
hexo.log.warn(e);
|
37
|
+
}
|
75
38
|
});
|
@@ -145,7 +145,9 @@ export const sidebarTOC = () => {
|
|
145
145
|
|
146
146
|
sections = sections.map((element, index) => {
|
147
147
|
const link = element.querySelector('a.toc-link')
|
148
|
-
const
|
148
|
+
const linkHref = link.getAttribute('href')
|
149
|
+
if (!linkHref) return null
|
150
|
+
const anchor = document.getElementById(decodeURI(linkHref.replace('#', '')))
|
149
151
|
if (!anchor) return null
|
150
152
|
const alink = anchor.querySelector('a.anchor')
|
151
153
|
|
@@ -89,22 +89,33 @@ export const transition = (target: HTMLElement, type: number|string|Function, co
|
|
89
89
|
}, animation)).play()
|
90
90
|
}
|
91
91
|
|
92
|
-
export const pageScroll = (target: HTMLElement|number, offset?: number, complete?: Function) => {
|
93
|
-
//
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
}
|
110
|
-
|
92
|
+
export const pageScroll = (target: HTMLElement | number, offset?: number, complete?: Function) => {
|
93
|
+
// 确定滚动容器
|
94
|
+
const scrollContainer = (typeof offset === 'number' && typeof target !== 'number')
|
95
|
+
? target.parentNode as HTMLElement
|
96
|
+
: document.scrollingElement || document.documentElement;
|
97
|
+
|
98
|
+
// 计算目标滚动位置
|
99
|
+
let scrollTop: number;
|
100
|
+
if (typeof offset !== 'undefined') {
|
101
|
+
scrollTop = offset;
|
102
|
+
} else if (typeof target === 'number') {
|
103
|
+
scrollTop = target;
|
104
|
+
} else if (target) {
|
105
|
+
const rect = target.getBoundingClientRect();
|
106
|
+
scrollTop = rect.top + window.scrollY - siteNavHeight;
|
107
|
+
} else {
|
108
|
+
scrollTop = 0;
|
109
|
+
}
|
110
|
+
|
111
|
+
// 执行平滑滚动
|
112
|
+
scrollContainer.scrollTo({
|
113
|
+
top: scrollTop,
|
114
|
+
behavior: 'smooth'
|
115
|
+
});
|
116
|
+
|
117
|
+
// 处理完成回调(模拟动画持续时间)
|
118
|
+
if (complete) {
|
119
|
+
setTimeout(() => complete(), 500); // 与原动画持续时间保持一致
|
120
|
+
}
|
121
|
+
};
|
@@ -1,10 +1,11 @@
|
|
1
1
|
import { insertAfter } from '../library/proto'
|
2
|
+
import DOMPurify from 'dompurify';
|
2
3
|
|
3
4
|
// TODO 使用PhotoSwipe替换Fancybox
|
4
5
|
export const postFancybox = (p:string) => {
|
5
6
|
if (document.querySelector(p + ' .md img')) {
|
6
|
-
|
7
|
-
|
7
|
+
// vendorCss('fancybox')
|
8
|
+
// vendorCss('justifiedGallery')
|
8
9
|
document.querySelectorAll(p + ' p.gallery').forEach((element) => {
|
9
10
|
const box = document.createElement('div')
|
10
11
|
box.className = 'gallery'
|
@@ -17,8 +18,8 @@ export const postFancybox = (p:string) => {
|
|
17
18
|
})
|
18
19
|
|
19
20
|
document.querySelectorAll(p + ' .md img:not(.emoji):not(.vemoji)').forEach((element) => {
|
20
|
-
const $image =
|
21
|
-
const imageLink = $image.attr('data-src') || $image.attr('src') // 替换
|
21
|
+
const $image = $(element)
|
22
|
+
const imageLink = DOMPurify.sanitize($image.attr('data-src') || $image.attr('src')) // 替换
|
22
23
|
const $imageWrapLink = $image.wrap('<a class="fancybox" href="' + imageLink + '" itemscope itemtype="https://schema.org/ImageObject" itemprop="url"></a>').parent('a')
|
23
24
|
let info; let captionClass = 'image-info'
|
24
25
|
if (!$image.is('a img')) {
|
@@ -34,25 +35,25 @@ export const postFancybox = (p:string) => {
|
|
34
35
|
const para = document.createElement('span')
|
35
36
|
const txt = document.createTextNode(info)
|
36
37
|
para.appendChild(txt)
|
37
|
-
para.
|
38
|
+
para.addClass(captionClass)
|
38
39
|
insertAfter(element, para)
|
39
40
|
}
|
40
41
|
})
|
41
42
|
|
42
43
|
document.querySelectorAll(p + ' div.gallery').forEach((el, i) => {
|
43
44
|
// @ts-ignore
|
44
|
-
|
45
|
-
rowHeight:
|
45
|
+
$(el).justifiedGallery({
|
46
|
+
rowHeight: $(el).data('height') || 120,
|
46
47
|
rel: 'gallery-' + i
|
47
48
|
}).on('jg.complete', function () {
|
48
|
-
|
49
|
+
$(this).find('a').each((k, ele) => {
|
49
50
|
ele.setAttribute('data-fancybox', 'gallery-' + i)
|
50
51
|
})
|
51
52
|
})
|
52
53
|
})
|
53
54
|
|
54
|
-
|
55
|
-
|
55
|
+
$.fancybox.defaults.hash = false
|
56
|
+
$(p + ' .fancybox').fancybox({
|
56
57
|
loop: true,
|
57
58
|
// @ts-ignore
|
58
59
|
helpers: {
|
@@ -1,6 +1,7 @@
|
|
1
1
|
import { cardActive } from '../page/common'
|
2
2
|
import { resizeHandle } from '../globals/handles'
|
3
3
|
import {
|
4
|
+
CONFIG,
|
4
5
|
setLocalHash, setLocalUrl, setOriginTitle,
|
5
6
|
} from '../globals/globalVars'
|
6
7
|
import { positionInit } from '../globals/tools'
|
@@ -10,6 +11,14 @@ import { tabFormat } from '../page/tab'
|
|
10
11
|
import { lazyLoad } from 'unlazy'
|
11
12
|
|
12
13
|
export const siteRefresh = async (reload) => {
|
14
|
+
if (__shokax_antiFakeWebsite__) {
|
15
|
+
if (window.location.origin !== CONFIG.hostname && window.location.origin !== "http://localhost:4000") {
|
16
|
+
window.location.href = CONFIG.hostname
|
17
|
+
/*! 我知道你正在试图去除这段代码,虽然我无法阻止你,但我劝你好自为之 */
|
18
|
+
alert('检测到非法仿冒网站,已自动跳转回正确首页;\nWe have detected a fake website, and you have been redirected to the correct homepage.')
|
19
|
+
}
|
20
|
+
}
|
21
|
+
|
13
22
|
setLocalHash(0)
|
14
23
|
setLocalUrl(window.location.href)
|
15
24
|
|
@@ -70,6 +70,14 @@ const siteInit = async () => {
|
|
70
70
|
|
71
71
|
cloudflareInit()
|
72
72
|
|
73
|
+
if (__shokax_antiFakeWebsite__) {
|
74
|
+
if (window.location.origin !== CONFIG.hostname && window.location.origin !== "http://localhost:4000") {
|
75
|
+
window.location.href = CONFIG.hostname
|
76
|
+
/*! 我知道你正在试图去除这段代码,虽然我无法阻止你,但我劝你好自为之 */
|
77
|
+
alert('检测到非法仿冒网站,已自动跳转回正确首页;\nWe have detected a fake website, and you have been redirected to the correct homepage.')
|
78
|
+
}
|
79
|
+
}
|
80
|
+
|
73
81
|
window.addEventListener('DOMContentLoaded', siteInit, {
|
74
82
|
passive: true
|
75
83
|
})
|
@@ -1,41 +0,0 @@
|
|
1
|
-
"use strict";
|
2
|
-
var __defProp = Object.defineProperty;
|
3
|
-
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
4
|
-
var __getOwnPropNames = Object.getOwnPropertyNames;
|
5
|
-
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
6
|
-
var __export = (target, all) => {
|
7
|
-
for (var name in all)
|
8
|
-
__defProp(target, name, { get: all[name], enumerable: true });
|
9
|
-
};
|
10
|
-
var __copyProps = (to, from, except, desc) => {
|
11
|
-
if (from && typeof from === "object" || typeof from === "function") {
|
12
|
-
for (let key of __getOwnPropNames(from))
|
13
|
-
if (!__hasOwnProp.call(to, key) && key !== except)
|
14
|
-
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
15
|
-
}
|
16
|
-
return to;
|
17
|
-
};
|
18
|
-
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
19
|
-
var injects_point_exports = {};
|
20
|
-
__export(injects_point_exports, {
|
21
|
-
default: () => injects_point_default
|
22
|
-
});
|
23
|
-
module.exports = __toCommonJS(injects_point_exports);
|
24
|
-
var injects_point_default = {
|
25
|
-
views: [
|
26
|
-
"head",
|
27
|
-
"sidebar",
|
28
|
-
"rightNav",
|
29
|
-
"postMeta",
|
30
|
-
"postBodyEnd",
|
31
|
-
"footer",
|
32
|
-
"bodyEnd",
|
33
|
-
"comment",
|
34
|
-
"status"
|
35
|
-
],
|
36
|
-
styles: [
|
37
|
-
"variable",
|
38
|
-
"mixin",
|
39
|
-
"style"
|
40
|
-
]
|
41
|
-
};
|