清理:删除废弃的chapters HTML文件夹
This commit is contained in:
parent
dddcafb1fb
commit
e4b249ed2a
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@ -1,56 +0,0 @@
|
||||
{
|
||||
"chapters": [
|
||||
{
|
||||
"id": 186,
|
||||
"title": "前往深渊浮岛",
|
||||
"subtitle": "黑暗的召唤"
|
||||
},
|
||||
{
|
||||
"id": 187,
|
||||
"title": "黑暗之源",
|
||||
"subtitle": "深渊的诅咒"
|
||||
},
|
||||
{
|
||||
"id": 188,
|
||||
"title": "暗影陷阱",
|
||||
"subtitle": "黑暗中的阴谋"
|
||||
},
|
||||
{
|
||||
"id": 189,
|
||||
"title": "暗影将军登场",
|
||||
"subtitle": "深渊的最强守护者"
|
||||
},
|
||||
{
|
||||
"id": 190,
|
||||
"title": "苦战",
|
||||
"subtitle": "绝望的深渊"
|
||||
},
|
||||
{
|
||||
"id": 191,
|
||||
"title": "创世之力觉醒",
|
||||
"subtitle": "神之力的真正形态"
|
||||
},
|
||||
{
|
||||
"id": 192,
|
||||
"title": "击败暗影将军",
|
||||
"subtitle": "深渊的终结"
|
||||
},
|
||||
{
|
||||
"id": 193,
|
||||
"title": "净化黑暗之源",
|
||||
"subtitle": "深渊浮岛的重生"
|
||||
},
|
||||
{
|
||||
"id": 194,
|
||||
"title": "第二块碎片",
|
||||
"subtitle": "创世之力的成长"
|
||||
},
|
||||
{
|
||||
"id": 195,
|
||||
"title": "新的危机",
|
||||
"subtitle": "暗影领主的阴谋"
|
||||
}
|
||||
],
|
||||
"total": 10,
|
||||
"updated": "2026-03-30T07:22:34.732Z"
|
||||
}
|
||||
@ -1,243 +0,0 @@
|
||||
const fs = require('fs');
|
||||
|
||||
const additionalContent = {
|
||||
186: `
|
||||
|
||||
林克和艾琳娜走进神殿入口,周围的黑暗变得更加浓重。墙壁上的符文已经完全被暗影侵蚀,散发出诡异的光芒。
|
||||
|
||||
"小心。"艾琳娜低声说,"这里的空间结构可能被暗影扭曲了。"
|
||||
|
||||
林克点头,握紧光剑。他能感受到周围有无数双眼睛在注视着他们。
|
||||
|
||||
果然,从阴影中涌出更多的暗影生物。这些比外面的更强,体型更大,气息更恐怖。
|
||||
|
||||
"流心·狂!"林克蓄力增强攻击。
|
||||
|
||||
他冲入暗影生物群,剑光如暴风般旋转。每一剑都带走一个敌人,但敌人源源不断。
|
||||
|
||||
"幻影剑舞!"林克爆发最强攻击,清理出一片空间。
|
||||
|
||||
艾琳娜释放光明魔法支援,两人配合默契,逐渐深入神殿。
|
||||
|
||||
终于,他们来到了神殿的核心区域。那里有一个巨大的黑色祭坛,祭坛上漂浮着一颗暗紫色的水晶球——黑暗之源的核心。
|
||||
|
||||
但祭坛前,站着一个身影。那是...
|
||||
|
||||
林克和艾琳娜对视一眼,都看到了对方眼中的震惊。
|
||||
|
||||
新的挑战,即将开始。`,
|
||||
|
||||
187: `
|
||||
|
||||
林克和艾琳娜走进神殿深处,周围的空间变得更加压抑。空气中弥漫着腐烂的气息,地面上的黑色液体发出诡异的声响。
|
||||
|
||||
"这里就是黑暗之源的核心区域。"艾琳娜说,声音有些颤抖。
|
||||
|
||||
"我父母曾经在这里工作,维护黑暗之源的平衡。"
|
||||
|
||||
林克握紧她的手:"我们会让这里恢复正常的。"
|
||||
|
||||
两人继续前行,终于来到了核心祭坛前。祭坛上漂浮着一颗巨大的暗紫色水晶球,那就是黑暗之源的核心。
|
||||
|
||||
但让林克惊讶的是,祭坛周围站满了暗影生物。它们仿佛在守护着什么。
|
||||
|
||||
"看来暗影早就知道我们会来。"林克说。
|
||||
|
||||
"准备好战斗了吗?"
|
||||
|
||||
艾琳娜点头,手中凝聚光明魔法。
|
||||
|
||||
林克举起光剑,金色的创世之力在剑身上流转。
|
||||
|
||||
"那就开始吧!"
|
||||
|
||||
两人冲向暗影生物群,新的战斗开始了。`,
|
||||
|
||||
188: `
|
||||
|
||||
六个黑暗守卫被击败后,林克和艾琳娜终于可以喘口气。
|
||||
|
||||
但林克知道,真正的挑战才刚刚开始。
|
||||
|
||||
暗影将军卡尔站在祭坛前,俯视着他们。他的气息深邃而恐怖,比之前遇到的任何敌人都强。
|
||||
|
||||
"林克,你确实有实力。"卡尔说,"但你面对的是被暗影加强了三百年的神族战士。"
|
||||
|
||||
"你的创世之力还不够。"
|
||||
|
||||
林克握紧光剑,感受到对方的强大。卡尔的每一句话都带着威压,让他几乎窒息。
|
||||
|
||||
但林克没有退缩。他想起卡赞的话——剑意是魂。
|
||||
|
||||
"卡尔,你曾经是深渊浮岛的守护者。"林克说,"你为什么要为暗影卖命?"
|
||||
|
||||
卡尔的表情变得复杂,但很快恢复了冷漠。
|
||||
|
||||
"守护者?那是三百年前的我。现在的我,是暗影的将军。"
|
||||
|
||||
"不要废话了,林克。让我看看你的实力。"
|
||||
|
||||
他举起暗紫色的巨剑,向林克冲来。`,
|
||||
|
||||
189: `
|
||||
|
||||
卡尔停止了攻击,他的身体开始崩解。暗影之力从他体内涌出,逐渐消散。
|
||||
|
||||
"林克...谢谢你..."卡尔虚弱地说。
|
||||
|
||||
"你让我找回了自己...但我已经...活不了多久了..."
|
||||
|
||||
林克蹲下,握住卡尔的手。
|
||||
|
||||
"你已经做得很好。"
|
||||
|
||||
"你守护了深渊浮岛三百年。现在,让我来完成你的使命。"
|
||||
|
||||
卡尔露出一个释然的笑容:"拜托你了...保护好艾琳娜...她是我看着长大的...就像我的妹妹一样..."
|
||||
|
||||
他的眼睛慢慢闭上,身体化为点点光芒消散。
|
||||
|
||||
一个真正的战士,终于得到了解脱。`,
|
||||
|
||||
190: `
|
||||
|
||||
林克爆发出最后的创世之力,金色的光芒从体内涌出。
|
||||
|
||||
"极·神剑术·万剑归宗!"
|
||||
|
||||
无数金色的剑气从林克身周爆发,形成一道巨大的剑龙。剑龙向暗影化身冲去,带着毁天灭地的力量。
|
||||
|
||||
暗影化身试图阻挡,但剑龙的力量太强。它的黑色护盾在剑龙的冲击下逐渐破裂。
|
||||
|
||||
"不...这不可能!"暗影化身惊呼。
|
||||
|
||||
剑龙击中它的胸口,摧毁了核心。
|
||||
|
||||
暗影化身发出一声惨叫,身体开始崩解。黑色的雾气从它体内涌出,逐渐消散。
|
||||
|
||||
林克喘着粗气,身体几乎力竭。但他成功了——击败了暗影化身。
|
||||
|
||||
艾琳娜冲过来,扶住林克。
|
||||
|
||||
"林克,你没事吧?"
|
||||
|
||||
林克摇头:"我没事...我们成功了。"
|
||||
|
||||
两人相视而笑,紧紧拥抱在一起。`,
|
||||
|
||||
191: `
|
||||
|
||||
创世之力真正觉醒后,林克感受到前所未有的力量。
|
||||
|
||||
金色的光芒从体内涌出,驱散了周围所有的黑暗。他的眼睛变成了纯金色,身体周围形成了一个耀眼的光晕。
|
||||
|
||||
这就是真正的创世之力——与意志结合的神圣力量。
|
||||
|
||||
卡尔感受到这股力量,脸色大变。
|
||||
|
||||
"这是...真正的创世之力!"
|
||||
|
||||
"你怎么可能觉醒这种力量!"
|
||||
|
||||
林克没有回答,他感受着体内澎湃的力量。创世之力不再只是简单的能量,而是与他的意志融为一体。
|
||||
|
||||
他能够感受到整个神界的能量流动,感受到暗影的本质,感受到光与暗的平衡。
|
||||
|
||||
这是守护的力量,也是净化的力量。
|
||||
|
||||
林克举起光剑,金色的创世之力在剑身上流转。
|
||||
|
||||
"卡尔,我来帮你解脱。"`,
|
||||
|
||||
192: `
|
||||
|
||||
暗影化身消散后,林克和艾琳娜终于可以净化黑暗之源。
|
||||
|
||||
林克走到祭坛前,将光剑刺入暗紫色的水晶球。
|
||||
|
||||
"创世净化!"
|
||||
|
||||
金色的光芒从剑身涌出,包围了整个水晶球。暗紫色的光芒与金色的光芒交织,爆发出剧烈的能量波。
|
||||
|
||||
整个神殿都在震动,地面龟裂,石块坠落。
|
||||
|
||||
艾琳娜用光明魔法保护自己,紧张地看着净化过程。
|
||||
|
||||
林克的额头上渗出汗水,创世之力消耗得很快。但他感受到了希望——暗影之力正在逐渐消退。
|
||||
|
||||
终于,暗紫色的光芒完全消失。水晶球变成了纯净的黑色,那是黑暗之源原本的颜色。
|
||||
|
||||
净化成功了!`,
|
||||
|
||||
193: `
|
||||
|
||||
黑暗之源净化后,整个深渊浮岛开始恢复。
|
||||
|
||||
黑色的雾气逐渐消散,星光重新出现在天空中。地面上的裂缝开始愈合,黑色的液体逐渐消失。被侵蚀的建筑开始恢复原状,街道重新变得整洁。
|
||||
|
||||
艾琳娜看着这一切,眼中流下泪水。
|
||||
|
||||
"深渊浮岛...回来了..."
|
||||
|
||||
林克握住她的手:"是的,回来了。你父母守护的浮岛,终于得到了解放。"
|
||||
|
||||
艾琳娜转头看向林克,眼中充满了感激和爱意。
|
||||
|
||||
"谢谢你,林克。你完成了我的愿望,也完成了卡尔的遗愿。"
|
||||
|
||||
两人走到神殿外,看着恢复的深渊浮岛。星光洒落,照亮了整个浮岛。
|
||||
|
||||
曾经黑暗的深渊,如今变成了美丽的星夜。
|
||||
|
||||
这是新的开始。`,
|
||||
|
||||
194: `
|
||||
|
||||
林克和艾琳娜返回云端之城,向议会汇报战果。
|
||||
|
||||
宙斯看着林克:"你做得很好。深渊浮岛恢复了,黑暗之源也净化了。第二块神之钥碎片也到手了。"
|
||||
|
||||
林克拿出金色的碎片:"是的,第二块碎片已经与我融合。我的创世之力从20%提升到了28%。"
|
||||
|
||||
雅典娜点头:"创世之力的提升会随着收集的碎片数量而加速。前几块碎片提升较少,后几块碎片提升会更多。当你收集到第七块碎片时,你的创世之力将达到100%。"
|
||||
|
||||
林克握紧拳头:"我会继续前进。还有五块碎片等着我去收集。"
|
||||
|
||||
卡赞走上前:"林克,接下来你要前往天穹浮岛。那是第三块碎片的所在地。但那里的情况比深渊浮岛更加危险。那里有暗影领主镇守,实力比暗影将军更强。"
|
||||
|
||||
林克眼神坚定:"我会准备好的。"`,
|
||||
|
||||
195: `
|
||||
|
||||
天穹浮岛上,林克与暗影领主正面对峙。
|
||||
|
||||
暗影领主的气息深邃而恐怖,比卡尔还要强数倍。他的黑色巨剑散发着毁灭的气息,每一步都让地面震动。
|
||||
|
||||
"林克,你就是那个持有创世之力的剑神?"暗影领主问。
|
||||
|
||||
"我听说过你的事迹。你在阿拉德大陆击败了无数强敌,在魔界与赫尔德对抗,在泰波尔斯击败了伊西斯。你的实力确实不俗。"
|
||||
|
||||
林克握紧光剑:"我就是林克。我来取第三块神之钥碎片。"
|
||||
|
||||
暗影领主冷笑:"你以为你可以轻易地取走碎片?太天真了。"
|
||||
|
||||
他举起巨剑:"让我看看,创世之力到底有多强。"
|
||||
|
||||
两人同时冲向对方,剑与剑的碰撞爆发出了毁天灭地的能量波。
|
||||
|
||||
金色的剑光与黑色的剑气在空中碰撞,整个天穹浮岛都在震动。
|
||||
|
||||
新的战斗,开始了!`
|
||||
};
|
||||
|
||||
for (const [id, content] of Object.entries(additionalContent)) {
|
||||
const path = `./chapter-${id}.json`;
|
||||
try {
|
||||
const data = JSON.parse(fs.readFileSync(path, 'utf8'));
|
||||
data.content = data.content + content;
|
||||
fs.writeFileSync(path, JSON.stringify(data, null, 2));
|
||||
console.log(`Chapter ${id}: ${data.content.length} chars`);
|
||||
} catch(e) {
|
||||
console.log(`Chapter ${id}: Error - ${e.message}`);
|
||||
}
|
||||
}
|
||||
@ -1,582 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<title>洛兰的风 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 10px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 15px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
right: 10px;
|
||||
bottom: 80px;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 36px;
|
||||
height: 36px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 1</div>
|
||||
<h1 class="chapter-title">洛兰的风</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>艾尔文防线的清晨,是从铁匠铺的锤声开始的。</p>
|
||||
<p>"叮——叮——叮——"</p>
|
||||
<p>林克睁开眼,陌生的天花板映入眼帘。木质的房梁,斑驳的墙壁,还有一股淡淡的薰衣草香味。</p>
|
||||
<p>他试图坐起身,左肩却传来一阵剧痛。</p>
|
||||
<p>"别动,你的伤口还没愈合。"</p>
|
||||
<p>清甜的声音从门口传来。林克转头,看到一个少女端着水盆走进来。她有着一头柔顺的棕色长发,眼睛像是春日的湖水,清澈而温暖。</p>
|
||||
<p>"你是……"</p>
|
||||
<p>"我叫赛丽亚。"少女将毛巾浸湿,轻轻敷在他的额头上,"昨天你在洛兰森林里晕倒了,是一位路过的剑士把你送到这里的。"</p>
|
||||
<p>林克努力回忆。</p>
|
||||
<p>他从虚祖出发,一路向西,穿越了大半个阿拉德大陆。最后来到这个叫艾尔文防线的地方,听说是冒险者的聚集地。然后……他在一个叫洛兰的地方迷路了,遇到了一群绿皮怪物——哥布林。</p>
|
||||
<p>那些家伙比他想象中更难对付。数量众多,阴险狡诈,还会设陷阱。他打倒了五六只,但左肩被一只哥布林的短刀划开了一道口子。</p>
|
||||
<p>失血过多,最后他晕倒了。</p>
|
||||
<p>"那位剑士呢?"林克问。</p>
|
||||
<p>"他放下你就走了,只说让你伤好后去一趟铁匠铺。"赛丽亚收起毛巾,露出一个温柔的笑容,"不过他说了一句话,让我很好奇。"</p>
|
||||
<p>"什么话?"</p>
|
||||
<p>"他说……"赛丽亚学着那人的低沉嗓音,"'这小子,和当年的我很像。'"</p>
|
||||
<p>林克愣住了。</p>
|
||||
<p>和当年的他很像?那位剑士是谁?</p>
|
||||
<p>---</p>
|
||||
<p>三天后,林克的伤好得差不多了。</p>
|
||||
<p>赛丽亚的旅馆虽然简陋,但收拾得很干净。这三天里,他每天在赛丽亚的照料下养伤,听她说着艾尔文防线的事。</p>
|
||||
<p>这里是贝尔玛尔公国和德洛斯帝国交界的前线,常年有冒险者来往。最近格兰之森的怪物变得躁动不安,不少新手冒险者都在这里丢了性命。</p>
|
||||
<p>"你也是从外面来的冒险者吗?"赛丽亚一边擦拭柜台,一边问道。</p>
|
||||
<p>"算是吧。"林克看着自己的左手,那上面缠着厚厚的绷带。</p>
|
||||
<p>他的左手,和别人不一样。</p>
|
||||
<p>从记事起,他的左手就是血红色的,皮肤下仿佛有什么东西在蠕动。村里的人说这是诅咒,是不祥之兆。他从小就被视为怪物,被驱逐,被孤立。</p>
|
||||
<p>直到三年前,一位云游的剑士路过他的村庄。</p>
|
||||
<p>"这是鬼手。"那位剑士说,"被卡赞诅咒的手臂,拥有鬼神之力的同时,也会被诅咒侵蚀。"</p>
|
||||
<p>"我会变成怪物吗?"</p>
|
||||
<p>"那取决于你。"剑士说,"力量本身没有善恶,关键在于使用它的心。如果你愿意,我可以教你剑术。用剑,来掌控这份力量。"</p>
|
||||
<p>那位剑士,叫阿甘左。</p>
|
||||
<p>三年了,林克一直在寻找阿甘左的踪迹。听说他最后出现在艾尔文防线附近,所以他才一路追寻到这里。</p>
|
||||
<p>"林克?"赛丽亚的声音将他拉回现实。</p>
|
||||
<p>"啊,抱歉。"他收回思绪,"你说铁匠铺?"</p>
|
||||
<p>"嗯,那位剑士让你伤好后去一趟。"赛丽亚指着门外,"出门左转,走到底就是林纳斯大叔的铁匠铺。"</p>
|
||||
<p>---</p>
|
||||
<p>铁匠铺里热气腾腾。</p>
|
||||
<p>一个中年男人正在炉台前打铁,肌肉虬结的手臂挥舞着铁锤,每一次落下都溅起耀眼的火星。</p>
|
||||
<p>"你就是林克?"男人头也不抬地问。</p>
|
||||
<p>"是。"</p>
|
||||
<p>"阿甘左交代过了。"林纳斯放下铁锤,擦了擦额头的汗水,转过身来。他脸上有一道疤,从左眉延伸到颧骨,看起来经历了不少风浪。</p>
|
||||
<p>"那家伙让我给你准备一把武器。"林纳斯走到货架前,抽出一把太刀,"试试这个。"</p>
|
||||
<p>刀身修长,刀刃锋利,握在手中有一种踏实的重量感。</p>
|
||||
<p>"好刀。"林克由衷赞叹。</p>
|
||||
<p>"算你有眼光。"林纳斯笑了笑,"这刀叫'霜刃',是我年轻时用的家伙。现在给你了,别辱没了它。"</p>
|
||||
<p>林克郑重地接过刀:"多谢。"</p>
|
||||
<p>"先别急着谢。"林纳斯的表情严肃起来,"阿甘左让我给你带句话——'想要掌控鬼手,光靠意志是不够的。去洛兰吧,只有战斗,才能让你真正理解这份力量。'"</p>
|
||||
<p>林克握紧刀柄。</p>
|
||||
<p>三年了,他终于又听到了这个名字。</p>
|
||||
<p>"他还在艾尔文防线吗?"林克急切地问。</p>
|
||||
<p>林纳斯摇摇头:"三天前就走了,说是要去调查格兰之森的异动。"他顿了顿,"不过他说了,如果你能通过洛兰的试炼,你们会再见面的。"</p>
|
||||
<p>---</p>
|
||||
<p>回到旅馆,林克收拾好东西,准备再次前往洛兰。</p>
|
||||
<p>"又要去吗?"赛丽亚有些担心,"你身上的伤刚好……"</p>
|
||||
<p>"没事。"林克将霜刃系在腰间,"这是必经之路。"</p>
|
||||
<p>赛丽亚沉默了一会儿,从柜台下面拿出一个小布袋:"这是一些干粮和药水,你带着。"</p>
|
||||
<p>林克愣了一下。</p>
|
||||
<p>"我……"</p>
|
||||
<p>"艾尔文防线很少有冒险者会回来跟我道别。"赛丽亚轻声说,"大多数人都是一去不复返。你……要小心。"</p>
|
||||
<p>林克看着她清澈的眼睛,心中涌起一股暖意。</p>
|
||||
<p>"我会回来的。"他说,"等我通过试炼,回来请你吃饭。"</p>
|
||||
<p>赛丽亚笑了,像是春日里绽放的花朵。</p>
|
||||
<p>"一言为定。"</p>
|
||||
<p>---</p>
|
||||
<p>洛兰森林比林克记忆中更加阴森。</p>
|
||||
<p>阳光被浓密的树冠遮挡,只有零星的光斑落在地面上。空气中弥漫着腐朽和潮湿的味道,偶尔能听到远处传来的奇怪声响。</p>
|
||||
<p>林克握紧霜刃,小心翼翼地前进。</p>
|
||||
<p>"嘎——"</p>
|
||||
<p>突然,一只绿皮怪物从灌木丛中窜出,挥舞着短刀向他砍来!</p>
|
||||
<p>哥布林!</p>
|
||||
<p>林克侧身躲过,反手一刀斩出。霜刃划破空气,在哥布林的胸口留下一道深深的伤口。</p>
|
||||
<p>"叽叽叽——!"</p>
|
||||
<p>受伤的哥布林发出刺耳的尖叫,更多的绿皮怪物从四面八方涌来。</p>
|
||||
<p>五只、六只、七只……</p>
|
||||
<p>林克的心跳加速。他能感觉到,左手在颤抖,绷带下的鬼手开始发烫。</p>
|
||||
<p>不,现在还不能用那股力量……</p>
|
||||
<p>他咬紧牙关,挥舞霜刃迎战。一只、两只、三只……哥布林的数量太多,他渐渐开始力不从心。</p>
|
||||
<p>"叽叽!"</p>
|
||||
<p>一只哥布林从侧面偷袭,短刀直刺他的腰间!</p>
|
||||
<p>林克勉强闪躲,但动作慢了一步,刀锋在他的肋下划开一道口子。</p>
|
||||
<p>鲜血涌出,疼痛让他的动作更加迟缓。</p>
|
||||
<p>更多的哥布林围了上来,眼中闪烁着残忍的光芒。</p>
|
||||
<p>难道……就要死在这里了吗?</p>
|
||||
<p>就在此时,一股灼热的力量从他的左手涌出,瞬间蔓延至全身。</p>
|
||||
<p>血红色的光芒从绷带下透出,林克感觉自己的意识正在被什么东西吞噬……</p>
|
||||
<p>不,不能失控……</p>
|
||||
<p>他用尽最后的意志力,将那股力量压了下去。</p>
|
||||
<p>但哥布林们已经发起了最后的进攻。</p>
|
||||
<p>"住手。"</p>
|
||||
<p>低沉的声音从森林深处传来。</p>
|
||||
<p>一道身影如鬼魅般闪现,银色的剑光划破空气。那只冲向林克的哥布林瞬间被斩成两半!</p>
|
||||
<p>其他哥布林见状,吓得四散逃窜。</p>
|
||||
<p>林克艰难地抬起头,看到了那个人的脸。</p>
|
||||
<p>黑色的长发,冷峻的面容,还有那双仿佛看透一切的眼睛。</p>
|
||||
<p>"阿……甘左……?"</p>
|
||||
<p>来人收起长剑,低头看着他。</p>
|
||||
<p>"三年不见,你还是这么狼狈。"</p>
|
||||
<p>林克想说什么,但失血过多让他眼前一黑,晕了过去。</p>
|
||||
<p>昏迷前,他听到阿甘左轻声说道:</p>
|
||||
<p>"鬼手的力量,不是压制,而是驾驭。小子,你要学的东西,还很多。"</p>
|
||||
<p>---</p>
|
||||
<p>(第一章完)</p>
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="#" class="nav-btn disabled">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<a href="chapter-2.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter current">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter">第34章:暗精灵墓地·剩余三将军</a>
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(1)) {
|
||||
readChapters.push(1);
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,903 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>暗黑雷鸣废墟 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 10</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>暗黑雷鸣废墟,位于格兰之森最阴森的角落。</p>
|
||||
<p>这里曾是古代战场,无数战士在此殒命。死亡的气息终年不散,久而久之,死者化作僵尸,在废墟中游荡。</p>
|
||||
<p>"这里就是……暗黑雷鸣废墟?"赛丽亚紧紧抓住林克的衣角,声音有些发颤。</p>
|
||||
<p>林克点点头,目光凝重地看着前方。</p>
|
||||
<p>与之前的地图不同,这里没有阳光,天空永远笼罩着一层灰蒙蒙的雾气。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克……"赛丽亚突然停下脚步,"你有没有感觉到?"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"你的鬼手……它好像……被压制了?"</p>
|
||||
<p>林克低头看去,果然发现左手臂上的绷带不再发烫。平日里那股躁动的诅咒之力,此刻竟然安静得像是沉睡了一样。</p>
|
||||
<p>"是这里的死亡气息……"林克若有所思,"GSD说过,这里的死亡气息会压制鬼手的力量。"</p>
|
||||
<p>这就是试炼的含义——在没有鬼神之力的情况下,仅凭剑术战胜敌人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当他们来到废墟的核心区域时,眼前的景象让他们倒吸一口凉气。</p>
|
||||
<p>那是一座巨大的祭坛,祭坛上刻满了古老的符文,中央摆放着一个巨大的石棺。</p>
|
||||
<p>而在祭坛的最高处,站着一个身穿黑色铠甲的身影。</p>
|
||||
<p>那是一个身高超过两米的怪物,全身被黑色的铠甲覆盖,头盔下露出一张腐烂的面孔。它的眼睛是血红色的,手中握着一把巨大的双手剑。</p>
|
||||
<p>"僵尸王……"林克低声说。</p>
|
||||
<p>"新鲜的……血肉……"僵尸王缓缓转过头,血红色的眼睛看向两人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>僵尸王的速度远比普通僵尸快得多。它挥舞着双手剑,带起一阵黑色的旋风,向林克斩来!</p>
|
||||
<p>"好快!"</p>
|
||||
<p>林克举刀格挡,但巨大的力量震得他手臂发麻。僵尸王的力量,甚至比牛头王萨乌塔还要恐怖!</p>
|
||||
<p>林克不断闪避,但僵尸的数量太多,他很快就被包围了。</p>
|
||||
<p>"这样下去不行……"林克咬紧牙关。</p>
|
||||
<p>他下意识地想要调动鬼手的力量,但体内空空如也。</p>
|
||||
<p>"没有鬼神之力……我难道就赢不了吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,林克想起了GSD说过的话。</p>
|
||||
<p>"剑魂追求的,是极致的剑术。不是鬼神之力,不是诅咒,而是剑本身。"</p>
|
||||
<p>"你要相信手中的剑,相信你自己的剑术。"</p>
|
||||
<p>林克闭上眼睛,深吸一口气。</p>
|
||||
<p>他举起霜刃,剑身上亮起耀眼的白光。</p>
|
||||
<p>"斩——!"</p>
|
||||
<p>林克挥剑斩出,一道白色的剑气撕裂了空间,直奔僵尸王!</p>
|
||||
<p>"不——!!!"</p>
|
||||
<p>僵尸王举起双手剑格挡,但剑气直接穿透了它的防御,将它斩成两半!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束了。</p>
|
||||
<p>就在这时,祭坛上的石棺突然发出一阵光芒。</p>
|
||||
<p>石棺缓缓打开,里面放着一把散发着柔和光芒的长剑。</p>
|
||||
<p>那是一把光剑。</p>
|
||||
<p>剑身由纯粹的光能量构成,没有实体,但却散发着令人心悸的锋芒。</p>
|
||||
<p>"试炼的奖励。"GSD的声音突然响起。</p>
|
||||
<p>"GSD?!"</p>
|
||||
<p>"既然你通过了试炼,它就归你了。"</p>
|
||||
<p>林克站起身,走到石棺前,郑重地拿起了那把光剑。</p>
|
||||
<p>当他的手握住剑柄时,光剑发出一阵欢快的嗡鸣,仿佛在迎接新的主人。</p>
|
||||
<p>"从今以后,你就叫'晨曦'吧。"林克轻声说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第十章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-9.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-11.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter ">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter ">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter ">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter ">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter ">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter ">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter ">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter ">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter ">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter current">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter ">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter ">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter ">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter ">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter ">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter ">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter ">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter ">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter ">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter ">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter ">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter ">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter ">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter ">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter ">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter ">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter ">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter ">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter ">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter ">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter ">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter ">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter ">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter ">第34章:暗精灵墓地·剩余三将军</a>
|
||||
<a href="chapter-35.html" class="sidebar-chapter ">第35章:邪龙斯皮兹</a>
|
||||
<a href="chapter-36.html" class="sidebar-chapter ">第36章:莎兰的探望</a>
|
||||
<a href="chapter-37.html" class="sidebar-chapter ">第37章:暗影迷宫·影子剑士</a>
|
||||
<a href="chapter-38.html" class="sidebar-chapter ">第38章:熔岩穴·泰坦之怒</a>
|
||||
<a href="chapter-39.html" class="sidebar-chapter ">第39章:暗黑城入口·无头骑士</a>
|
||||
<a href="chapter-40.html" class="sidebar-chapter ">第40章:万年雪山·冰心少年</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(10)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,937 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>王之书库 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 100</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,核心实验室。</p>
|
||||
<p>古老能量核心在永恒之火的驱动下稳定运转,散发出柔和而强大的光芒。卢克坐在核心旁边,感受着体内久违的平静,脸上露出了久违的笑容。</p>
|
||||
<p>「多少年了...」他轻声感叹,「我终于可以安心地睡一觉了...」</p>
|
||||
<p>「卢克爷爷!」贝奇扑进他的怀里,眼中满是泪水,「太好了...太好了...」</p>
|
||||
<p>林克站在一旁,看着这温馨的一幕,心中也感到欣慰。但他知道,事情还没有结束。</p>
|
||||
<p>「卢克爷爷。」他上前一步,「我想去王之书库看看。」</p>
|
||||
<p>卢克抬起头,浑浊的眼睛中闪过一丝复杂的神色。</p>
|
||||
<p>「王之书库...」他缓缓说道,「那里存放着海伯伦星的所有知识和记忆。你想找什么?」</p>
|
||||
<p>「关于赫尔德的线索。」林克说道,「她是这一切的幕后黑手。如果要彻底解决问题,必须了解她的计划。」</p>
|
||||
<p>卢克沉默了片刻,然后点点头:「你说得对。贝奇,你带他去吧。」</p>
|
||||
<p>「是!」贝奇站起来,牵起林克的手,「跟我来!」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>王之书库位于寂静城的最深处,是一栋巨大的圆形建筑。</p>
|
||||
<p>当林克和贝奇走进书库时,眼前的景象让他们惊叹不已。</p>
|
||||
<p>无数书架从地面延伸到穹顶,每一层都摆满了书籍、卷轴和水晶记忆体。柔和的光芒从天花板洒下,给整个空间增添了一种神圣而庄严的氛围。</p>
|
||||
<p>「这里就是...王之书库...」林克环顾四周,「比想象中还要壮观...」</p>
|
||||
<p>「这是海伯伦星文明的结晶。」贝奇骄傲地说道,「在这里,你可以找到任何想要的知识。」</p>
|
||||
<p>她带着林克来到中央的控制台前,开始检索关于赫尔德的信息。</p>
|
||||
<p>「赫尔德...魔界第二使徒...『哭泣之眼』...」贝奇念着检索结果,「找到了!有一些关于她的记录!」</p>
|
||||
<p>林克凑近屏幕,仔细阅读着上面的内容。</p>
|
||||
<p>「赫尔德来自一个名为『泰拉』的星球。那个星球因为过度开发而毁灭,她是唯一的幸存者...」</p>
|
||||
<p>「为了重建泰拉,她开始研究使徒的力量,并制定了一个可怕的计划——『创新世纪』...」</p>
|
||||
<p>林克继续往下看,脸色越来越凝重。</p>
|
||||
<p>「创新世纪计划...通过转移使徒到阿拉德大陆,引发大灾难,然后利用使徒死亡时释放的能量重建泰拉...」</p>
|
||||
<p>「这...这就是她的目的?」贝奇惊恐地捂住嘴,「她想要牺牲所有使徒,来重建她的家乡?」</p>
|
||||
<p>「不仅如此。」林克指着屏幕上的另一段文字,「看这里——『预言』。她散布了关于使徒毁灭世界的预言,让冒险家们去猎杀使徒...而冒险家们根本不知道,自己只是她的棋子...」</p>
|
||||
<p>贝奇的脸色变得苍白:「那...那卢克爷爷也是她的目标之一?」</p>
|
||||
<p>「是的。」林克点头,「所有使徒都是她的目标。包括安徒恩、罗特斯...还有卢克。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,书库的深处突然传来一阵轻微的响动。</p>
|
||||
<p>「谁?!」林克警觉地拔出细雪之舞。</p>
|
||||
<p>「别紧张,是我。」一个温和的声音响起。</p>
|
||||
<p>从书架后面走出一个身影。那是一个白发苍苍的老者,身穿学者的长袍,脸上带着慈祥的微笑。</p>
|
||||
<p>「你是...?」林克问道。</p>
|
||||
<p>「我是卡西利亚斯。」老者说道,「王之书库的守护者,也是...卢克的旧友。」</p>
|
||||
<p>「卡西利亚斯?」林克惊讶地看着他,「第四使徒『征服者』卡西利亚斯?」</p>
|
||||
<p>「呵呵,没想到还有人认识我。」卡西利亚斯微笑道,「我已经隐居多年,不再过问使徒之间的事了。」</p>
|
||||
<p>他走到林克面前,仔细打量着他:「你就是那个帮助卢克的小子?不错,有胆识,也有实力。」</p>
|
||||
<p>「您认识赫尔德吗?」林克问道。</p>
|
||||
<p>卡西利亚斯的脸色变得严肃:「当然认识。那个女人...是这一切悲剧的源头。」</p>
|
||||
<p>他走到窗前,望着窗外的虚空:「很多年前,我也曾相信她的预言,相信使徒会毁灭世界。但后来我发现了真相...她的预言都是编造的,目的就是让使徒互相残杀。」</p>
|
||||
<p>「为什么?」贝奇问道,「她为什么要这样做?」</p>
|
||||
<p>「因为她想要力量。」卡西利亚斯说道,「使徒死亡时释放的能量,是宇宙中最强大的力量之一。她想要收集这些能量,重建她的泰拉。」</p>
|
||||
<p>他转过身,看着林克:「年轻人,你帮助卢克是正确的。但你要小心...赫尔德已经注意到你了。她不会允许有人破坏她的计划。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>从王之书库出来,林克的心情很沉重。</p>
|
||||
<p>赫尔德的阴谋比他想象的还要可怕。她不仅想要牺牲所有使徒,还利用无辜的冒险家作为她的工具。</p>
|
||||
<p>「林克...」贝奇握着他的手,「我们该怎么办?」</p>
|
||||
<p>「首先,要保护卢克爷爷。」林克说道,「然后...我们要揭露赫尔德的真面目,让所有人知道她的阴谋。」</p>
|
||||
<p>「但是...谁会相信我们呢?」贝奇担忧地问道,「赫尔德的预言已经流传了这么多年,所有人都相信她...」</p>
|
||||
<p>「总会有人相信的。」林克坚定地说道,「只要我们坚持真相,总会有人站在我们这边。」</p>
|
||||
<p>他看着贝奇,眼中满是温柔:「而且,不管发生什么,我都会保护你,保护卢克爷爷,保护所有我在乎的人。」</p>
|
||||
<p>贝奇感动地看着他,然后主动踮起脚尖,吻上了他的唇。</p>
|
||||
<p>「林克...」她轻声说道,「不管发生什么,我也会一直陪着您...」</p>
|
||||
<p>两人在王之书库的门口相拥,在柔和的光芒中,他们的影子交织在一起。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到核心实验室,林克将赫尔德的阴谋告诉了卢克。</p>
|
||||
<p>老人听完后,沉默了很长时间。</p>
|
||||
<p>「我早就知道了...」他最终说道,「在被转移到魔界的那一刻,我就知道了她的计划。但我太虚弱了,无法反抗...」</p>
|
||||
<p>他抬起头,看着林克,眼中闪烁着希望的光芒:「但现在不同了。有了你的帮助,我们有机会改变这一切。」</p>
|
||||
<p>「是的。」林克点头,「我们不会让赫尔德得逞。」</p>
|
||||
<p>卢克露出了微笑,那是林克见过的最温暖的笑容。</p>
|
||||
<p>「谢谢你,年轻人。海伯伦星的王,再一次感谢你的帮助。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第九十八章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-99.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-101.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-70.html" class="sidebar-chapter ">第70章:天界之门·根特外围的战火</a>
|
||||
<a href="chapter-71.html" class="sidebar-chapter ">第71章:根特北门·泽丁的誓言</a>
|
||||
<a href="chapter-72.html" class="sidebar-chapter ">第72章:根特南门·马琳的效忠</a>
|
||||
<a href="chapter-73.html" class="sidebar-chapter ">第73章:根特防御战·钢铁与血肉的碰撞</a>
|
||||
<a href="chapter-74.html" class="sidebar-chapter ">第74章:夜间袭击战·银勺杂技团的覆灭</a>
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter current">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(100)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,985 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>不灭回廊 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 101</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,核心实验室。</p>
|
||||
<p>古老能量核心稳定运转,卢克的身体状况逐渐好转。但林克知道,他们还没有脱离危险——赫尔德的阴谋仍在继续,而通往王座的道路还横亘着最后一道关卡。</p>
|
||||
<p>「不灭回廊...」卢克缓缓说道,「那是通往王座的必经之路,也是寂静城最危险的区域。」</p>
|
||||
<p>「危险?」林克问道。</p>
|
||||
<p>「那里布满了海伯伦星最古老的机关,还有...」卢克顿了顿,「不灭者。」</p>
|
||||
<p>「不灭者?」</p>
|
||||
<p>「我用永恒之火创造的守护者。」卢克说道,「它们可以无限重生,除非破坏核心,否则永远无法击败。」</p>
|
||||
<p>林克点点头:「我去。」</p>
|
||||
<p>「我陪你。」艾泽拉走上前,银白色的长发在光芒中飘动,「我对不灭回廊最熟悉,可以为你带路。」</p>
|
||||
<p>林克看着她,发现她的眼中带着一丝复杂的情感。</p>
|
||||
<p>「好。」他伸出手,「一起。」</p>
|
||||
<p>艾泽拉微微一愣,然后握住了他的手。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>不灭回廊。</p>
|
||||
<p>这里与寂静城其他区域完全不同。走廊两侧的墙壁上刻满了古老的符文,散发着幽蓝色的光芒。空气中弥漫着一种神秘而压抑的气息,仿佛时间在这里静止。</p>
|
||||
<p>「这些符文...」林克观察着墙壁,「是海伯伦星的文字?」</p>
|
||||
<p>「是的。」艾泽拉点头,「这是古代海伯伦星的封印术,用来禁锢不灭者。如果触发了错误的符文,不灭者就会被释放。」</p>
|
||||
<p>她带着林克小心翼翼地前进,每一步都精确地踩在特定的位置。</p>
|
||||
<p>「你对这里很熟悉。」林克说道。</p>
|
||||
<p>「我在这里守护了三十年。」艾泽拉轻声说道,「从卢克爷爷建造寂静城的那一天起,我就一直在这里。」</p>
|
||||
<p>她转过头,紫色的眼睛看着林克:「这三十年里,我一直在等待...等待一个能够真正帮助卢克爷爷的人出现。」</p>
|
||||
<p>「现在这个人出现了。」林克微笑道。</p>
|
||||
<p>「是的。」艾泽拉的脸微微泛红,「你出现了。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,走廊前方突然传来一阵低沉的咆哮声!</p>
|
||||
<p>「小心!不灭者!」艾泽拉惊呼。</p>
|
||||
<p>从墙壁的暗格中,数道身影缓缓走出。那是一些由蓝色火焰构成的人形生物,眼中跳动着白色的光芒。它们的身体仿佛由纯粹的能量构成,散发着令人窒息的威压。</p>
|
||||
<p>「这就是...不灭者?」林克握紧细雪之舞。</p>
|
||||
<p>「它们的核心在胸口!」艾泽拉喊道,「但是核心被火焰保护,普通的攻击根本无法接近!」</p>
|
||||
<p>不灭者们同时发动了攻击!蓝色的火焰如同潮水般涌来,所过之处连金属都被融化!</p>
|
||||
<p>「极·鬼剑术!」</p>
|
||||
<p>林克挥剑格挡,但剑气在接触到蓝色火焰的瞬间就被蒸发!</p>
|
||||
<p>「好强的火焰!」林克大惊,连忙后退。</p>
|
||||
<p>「让我来!」艾泽拉举起法杖,紫色的能量在杖尖凝聚,「封印术——禁锢!」</p>
|
||||
<p>紫色的光芒笼罩了不灭者们,它们的动作瞬间变得迟缓!</p>
|
||||
<p>「现在!攻击它们的核心!」艾泽拉喊道。</p>
|
||||
<p>林克身形一闪,突进到一台不灭者身前。细雪之舞带着寒光,直刺它胸口的核心!</p>
|
||||
<p>「咔嚓——!」</p>
|
||||
<p>核心破碎,不灭者的身体瞬间崩解!</p>
|
||||
<p>「有效!」</p>
|
||||
<p>但就在这时,崩解的火焰重新凝聚,不灭者再次站了起来!</p>
|
||||
<p>「什么?!」林克瞪大了眼睛。</p>
|
||||
<p>「它们可以无限重生!」艾泽拉焦急地说道,「除非同时破坏所有核心,否则它们会不断复活!」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗陷入了僵局。</p>
|
||||
<p>不灭者们源源不断地攻击,林克和艾泽拉只能勉强招架。艾泽拉的封印术消耗巨大,她的额头开始渗出细密的汗珠。</p>
|
||||
<p>「艾泽拉,你没事吧?」林克关切地问道。</p>
|
||||
<p>「没事...」她咬着牙,「但是我的能量快耗尽了...」</p>
|
||||
<p>林克看着她苍白的脸色,心中涌起一股强烈的保护欲。</p>
|
||||
<p>「相信我。」他说道,「我会保护你。」</p>
|
||||
<p>艾泽拉看着他坚定的眼神,心中某个柔软的地方被触动了。</p>
|
||||
<p>「林克...」她轻声说道,「其实我...」</p>
|
||||
<p>话还没说完,一只不灭者突破了封印,向艾泽拉扑来!</p>
|
||||
<p>「小心!」林克大喊,身形一闪挡在她身前。</p>
|
||||
<p>蓝色的火焰击中了林克的肩膀,剧烈的疼痛让他闷哼一声。</p>
|
||||
<p>「林克!」艾泽拉惊恐地抱住他。</p>
|
||||
<p>「没事...」林克咬牙,「只是小伤...」</p>
|
||||
<p>他抬起头,眼中闪过一丝决然。</p>
|
||||
<p>「既然无法一个个击败...那就一起消灭!」</p>
|
||||
<p>「极·神剑术——万剑归宗!」</p>
|
||||
<p>无数剑气从林克身上爆发,形成了一道巨大的剑气风暴,将所有不灭者全部笼罩!</p>
|
||||
<p>「就是现在!艾泽拉,封印它们!」</p>
|
||||
<p>艾泽拉明白了他的意图,她举起法杖,将最后的能量全部释放!</p>
|
||||
<p>「终极封印——永恒禁锢!」</p>
|
||||
<p>紫色的光芒与剑气风暴融合,将所有不灭者的核心同时封印!</p>
|
||||
<p>「咔嚓——咔嚓——咔嚓——!」</p>
|
||||
<p>所有核心同时破碎,不灭者们发出不甘的咆哮,然后彻底消散!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束后,两人瘫坐在地上。</p>
|
||||
<p>艾泽拉看着林克肩膀上的伤口,眼中满是心疼。</p>
|
||||
<p>「为什么要替我挡...」她的声音带着哭腔,「你明明可以躲开的...」</p>
|
||||
<p>林克转过头,看着她泪流满面的脸,心中涌起一股温柔。</p>
|
||||
<p>「因为我不能让你受伤。」他轻声说道,「你对我来说...很重要。」</p>
|
||||
<p>艾泽拉愣住了。</p>
|
||||
<p>「很重要...?」</p>
|
||||
<p>「是的。」林克伸出手,轻轻擦去她眼角的泪水,「从第一次见到你开始,我就被你吸引了。你的温柔,你的善良,你对卢克的忠诚...都让我心动。」</p>
|
||||
<p>艾泽拉的脸瞬间红了。</p>
|
||||
<p>「林克...我...」她的声音颤抖着,「我也喜欢你...从你在艾泽拉面前保护卢克爷爷的那一刻起,我就喜欢上你了...」</p>
|
||||
<p>她低下头,声音变小:「但是我以为...你只会喜欢贝奇那样年轻可爱的女孩...像我这样的老太婆...」</p>
|
||||
<p>「谁说你是老太婆?」林克抬起她的下巴,让她看着自己,「在我眼里,你比任何女孩都要美丽。」</p>
|
||||
<p>艾泽拉看着他的眼睛,看到了其中的真诚和深情。</p>
|
||||
<p>「林克...」她轻声唤道,「可以...吻我吗?」</p>
|
||||
<p>林克没有回答,而是直接低下头,吻上了她的唇。</p>
|
||||
<p>那是一个温柔而深情的吻,带着三十年的等待和终于实现的渴望。艾泽拉生涩地回应着,双手攀上林克的肩膀。</p>
|
||||
<p>「林克...」分开时,她喘着气说道,「我想...把自己交给你...在这里...现在...」</p>
|
||||
<p>林克看着她眼中的坚定和渴望,点了点头。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>在不灭回廊的角落,两人相拥在一起。</p>
|
||||
<p>艾泽拉的身体比想象中更加柔软,她的皮肤白皙如雪,在幽蓝的光芒下散发着迷人的光泽。</p>
|
||||
<p>「我有点紧张...」她轻声说道,「这是我第一次...」</p>
|
||||
<p>「我也是第一次和使徒的守护者...」林克微笑着说。</p>
|
||||
<p>艾泽拉轻轻打了他一下:「别取笑我...」</p>
|
||||
<p>林克握住她的手,温柔地引导她。艾泽拉闭上眼睛,感受着林克的触碰,身体渐渐放松下来。</p>
|
||||
<p>「林克...」她轻声呻吟,「好舒服...」</p>
|
||||
<p>林克加快了动作,艾泽拉的身体开始剧烈颤抖。</p>
|
||||
<p>「啊...林克...我要...」</p>
|
||||
<p>「一起...艾泽拉...」</p>
|
||||
<p>两人同时达到了巅峰。艾泽拉紧紧抱着林克,泪水从眼角滑落。</p>
|
||||
<p>「谢谢你...林克...」她轻声说道,「我终于...不再是一个人了...」</p>
|
||||
<p>林克抱紧她,在她耳边轻声说道:「从今以后,你就是我的女人。我会永远保护你。」</p>
|
||||
<p>艾泽拉笑了,那笑容如同三十年来第一次绽放的花朵。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当两人走出不灭回廊时,贝奇和卢克正在出口等待。</p>
|
||||
<p>看到艾泽拉挽着林克的手臂,脸上带着幸福的红晕,贝奇眨了眨眼睛,然后露出了理解的微笑。</p>
|
||||
<p>「艾泽拉姐姐...」她走上前,握住艾泽拉的手,「欢迎加入我们的大家庭。」</p>
|
||||
<p>艾泽拉的脸更红了,但她没有否认,而是轻轻点了点头。</p>
|
||||
<p>卢克看着这一幕,浑浊的眼睛中闪过一丝欣慰。</p>
|
||||
<p>「年轻人...」他缓缓说道,「你不仅拯救了我的生命,还拯救了艾泽拉的心。海伯伦星的王,再次感谢你。」</p>
|
||||
<p>林克看着身边的两个女人,心中充满了温暖。</p>
|
||||
<p>是的,他会保护她们。</p>
|
||||
<p>保护所有爱他的人,保护这个他们共同守护的世界。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第九十九章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-100.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-102.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-71.html" class="sidebar-chapter ">第71章:根特北门·泽丁的誓言</a>
|
||||
<a href="chapter-72.html" class="sidebar-chapter ">第72章:根特南门·马琳的效忠</a>
|
||||
<a href="chapter-73.html" class="sidebar-chapter ">第73章:根特防御战·钢铁与血肉的碰撞</a>
|
||||
<a href="chapter-74.html" class="sidebar-chapter ">第74章:夜间袭击战·银勺杂技团的覆灭</a>
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter current">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(101)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,945 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>机械王座 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 102</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,机械王座。</p>
|
||||
<p>这里是寂静城的最深处,也是海伯伦星王权的象征。巨大的金属穹顶高耸入云,无数齿轮在头顶缓缓转动,发出庄严而沉重的声响。中央是一座由纯金与水晶构成的王座,散发着柔和而威严的光芒。</p>
|
||||
<p>林克站在王座前,身边是贝奇、艾泽拉、米娅和皇女艾丽婕。经过连番战斗,他们终于抵达了这里。</p>
|
||||
<p>「这里就是...机械王座...」米娅惊叹道,「比想象中还要壮观...」</p>
|
||||
<p>「是卢克爷爷的王座。」贝奇轻声说道,眼中满是敬畏,「海伯伦星最后的王权象征。」</p>
|
||||
<p>就在这时,王座后方传来一阵脚步声。</p>
|
||||
<p>「终于来了吗...」一个清冷的声音响起。</p>
|
||||
<p>从阴影中走出一个身影。那是一个身穿黑色长裙的女子,银色的长发如瀑布般垂落,脸上带着一张精致的面具,只露出一双冰冷的眼睛。</p>
|
||||
<p>「你是谁?!」林克握紧细雪之舞,警惕地问道。</p>
|
||||
<p>「我是赫尔德的使者。」女子淡淡地说道,「你们可以叫我『引导者』。」</p>
|
||||
<p>她环顾四周,目光在每个人身上扫过:「没想到啊...卢克居然真的找到了新的能量来源。看来,计划需要改变了。」</p>
|
||||
<p>「赫尔德的计划?」林克冷笑,「那个牺牲所有使徒来重建泰拉的疯狂计划?」</p>
|
||||
<p>引导者微微一愣,然后轻笑出声:「看来你们已经知道了。没错,『创新世纪』计划——收集所有使徒死亡时释放的能量,重建我们的泰拉。」</p>
|
||||
<p>她看向卢克,眼中闪过一丝嘲讽:「卢克,你本来应该在天界被冒险家们杀死,释放你的能量。但现在...你居然活下来了。」</p>
|
||||
<p>「我不会让你们得逞的。」林克挡在卢克身前,「不管是赫尔德,还是你,都别想伤害卢克爷爷。」</p>
|
||||
<p>引导者看着林克,眼中闪过一丝兴趣:「你就是那个帮助卢克的小子?有趣...居然能改变使徒的命运。」</p>
|
||||
<p>她缓缓抬起手,黑色的能量在她掌心凝聚:「但是,改变命运是要付出代价的。今天,你们所有人都将死在这里。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>引导者的力量远超想象,黑色的能量波如同潮水般涌来,所过之处连空间都被扭曲!</p>
|
||||
<p>「散开!」林克大喊。</p>
|
||||
<p>众人连忙躲避,但能量波的范围太大,米娅和皇女被余波击中,倒飞出去!</p>
|
||||
<p>「米娅!皇女!」林克大惊。</p>
|
||||
<p>「不用担心她们。」引导者微笑道,「我的目标只有你,还有卢克。」</p>
|
||||
<p>她身形一闪,瞬间出现在林克面前,黑色的能量化作利爪,直刺林克胸口!</p>
|
||||
<p>「极·鬼剑术!」</p>
|
||||
<p>林克挥剑格挡,但引导者的力量太强,他被震得连退数步,手臂发麻。</p>
|
||||
<p>「好强...比巴恩还要强!」林克咬牙。</p>
|
||||
<p>「巴恩?那个帝国的小丑?」引导者嗤笑,「他连我的一根手指都比不上。」</p>
|
||||
<p>她再次发动攻击,黑色的能量化作无数触手,从四面八方涌向林克!</p>
|
||||
<p>「林克!」贝奇和艾泽拉同时惊呼。</p>
|
||||
<p>「别过来!」林克大喊,「你们保护卢克爷爷!这家伙交给我!」</p>
|
||||
<p>他深吸一口气,眼中闪过一丝决然。</p>
|
||||
<p>「极·神剑术——万剑归宗!」</p>
|
||||
<p>无数剑气从林克身上爆发,形成了一道巨大的剑气风暴,与黑色的能量触手碰撞!</p>
|
||||
<p>「轰——!」</p>
|
||||
<p>巨大的爆炸声响起,整个机械王座都在震动!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>「有点意思...」引导者看着林克,眼中闪过一丝赞赏,「居然能挡下我的攻击。看来,你有资格见识真正的力量。」</p>
|
||||
<p>她摘下面具,露出一张绝美的脸庞。但那双眼睛却冰冷得令人心悸。</p>
|
||||
<p>「我是赫尔德的分身之一。」她说道,「承载着『哭泣之眼』的一部分力量。你能死在我手上,是你的荣幸。」</p>
|
||||
<p>她举起双手,整个机械王座开始剧烈震动!</p>
|
||||
<p>「不好!她在抽取寂静城的能量!」艾泽拉惊呼。</p>
|
||||
<p>「不能让她得逞!」林克大喊。</p>
|
||||
<p>他看向贝奇和艾泽拉:「帮我争取时间!我要用那一招!」</p>
|
||||
<p>贝奇和艾泽拉对视一眼,同时点头。</p>
|
||||
<p>「交给我们!」</p>
|
||||
<p>贝奇举起双手,机械王座中的机械装置开始运转,向引导者发射能量光束!</p>
|
||||
<p>艾泽拉举起法杖,紫色的封印术笼罩向引导者:「封印术——永恒禁锢!」</p>
|
||||
<p>「雕虫小技!」引导者冷哼,黑色的能量爆发,将两人的攻击全部震散!</p>
|
||||
<p>但就是这短暂的一瞬,给了林克机会!</p>
|
||||
<p>「极·神剑术——终焉之剑!」</p>
|
||||
<p>这是剑神的最强奥义,林克将所有的剑气凝聚成一把巨大的光剑,直刺引导者!</p>
|
||||
<p>「什么?!」引导者大惊,连忙防御。</p>
|
||||
<p>但光剑的力量太过强大,直接穿透了她的防御,刺入她的胸口!</p>
|
||||
<p>「啊——!」</p>
|
||||
<p>引导者发出一声凄厉的惨叫,黑色的能量从她体内爆发,然后迅速消散。</p>
|
||||
<p>「不可能...我怎么会...败给一个人类...」她不甘地看着林克,然后化作黑色的烟雾,彻底消散。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束,机械王座恢复了平静。</p>
|
||||
<p>林克跪倒在地,大口喘着气。刚才那一剑消耗了他所有的力量。</p>
|
||||
<p>「林克!」贝奇和艾泽拉同时扑进他怀里,眼中满是泪水。</p>
|
||||
<p>「你没事吧...」</p>
|
||||
<p>「没事...」林克微笑着说,「只是有点累...」</p>
|
||||
<p>卢克在王座上看着这一幕,浑浊的眼睛中流下了泪水。</p>
|
||||
<p>「谢谢你...年轻人...」他缓缓说道,「你不仅拯救了我的生命,还拯救了寂静城,拯救了所有我爱的人...」</p>
|
||||
<p>林克抬起头,看着这位海伯伦星的王,心中涌起一股温暖。</p>
|
||||
<p>「这是我应该做的。」他说道,「因为你们...都是我在乎的人。」</p>
|
||||
<p>贝奇、艾泽拉、米娅、皇女,所有人都围在他身边,眼中满是爱意和感激。</p>
|
||||
<p>在这一刻,林克感到前所未有的满足。</p>
|
||||
<p>是的,这就是他想要的——守护所爱之人,守护这个美好的世界。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-101.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-103.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-72.html" class="sidebar-chapter ">第72章:根特南门·马琳的效忠</a>
|
||||
<a href="chapter-73.html" class="sidebar-chapter ">第73章:根特防御战·钢铁与血肉的碰撞</a>
|
||||
<a href="chapter-74.html" class="sidebar-chapter ">第74章:夜间袭击战·银勺杂技团的覆灭</a>
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter current">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(102)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,950 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·寂静城的早晨 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 103</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,核心实验室。</p>
|
||||
<p>清晨的第一缕阳光透过水晶穹顶洒入,在地板上投下斑驳的光影。古老能量核心散发着柔和的蓝金色光芒,如同一颗温暖的心脏,静静地跳动着。</p>
|
||||
<p>林克睁开眼睛,发现自己躺在一张柔软的大床上。这是卢克特意为他准备的房间,位于寂静城的核心区域,可以俯瞰整个克洛诺斯岛。</p>
|
||||
<p>他转过头,看到身边还躺着两个身影。</p>
|
||||
<p>贝奇蜷缩在他的左侧,银白色的短发贴在脸颊上,嘴角带着一丝满足的微笑。她的一只手搭在林克的胸口,仿佛在确认他的存在。</p>
|
||||
<p>艾泽拉躺在他的右侧,紫色的长发散落在枕头上,呼吸平稳而轻柔。她的身体微微倾向林克,即使在睡梦中也下意识地靠近他。</p>
|
||||
<p>林克看着身边的两个女人,心中涌起一股温暖。</p>
|
||||
<p>这就是他的后宫,他爱的人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>「早安...」贝奇缓缓睁开眼睛,看到林克正在注视着她,脸瞬间红了。</p>
|
||||
<p>「早安。」林克微笑着吻了吻她的额头。</p>
|
||||
<p>「林克...」艾泽拉也醒了过来,看到眼前的情景,脸上露出羞涩的笑容,「早上好...」</p>
|
||||
<p>「早上好,艾泽拉。」林克伸手将她搂入怀中。</p>
|
||||
<p>三人相拥了一会儿,直到门外传来敲门声。</p>
|
||||
<p>「林克大人,早餐准备好了。」是米娅的声音。</p>
|
||||
<p>「我们马上来。」林克应道。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>寂静城的餐厅是一间宽敞明亮的房间,墙壁上镶嵌着发光的水晶,照亮了整个空间。中央是一张巨大的圆形餐桌,足以容纳十几人同时用餐。</p>
|
||||
<p>当林克带着贝奇和艾泽拉走进餐厅时,发现其他人已经到齐了。</p>
|
||||
<p>米娅和皇女艾丽婕坐在一侧,正在低声交谈。看到林克进来,两人同时抬起头,脸上露出笑容。</p>
|
||||
<p>「林克大人,早安。」米娅起身行礼。</p>
|
||||
<p>「早安,林克。」皇女也微笑着打招呼。</p>
|
||||
<p>「不用这么正式。」林克摆摆手,「在这里,我们都是家人。」</p>
|
||||
<p>他拉着贝奇和艾泽拉坐下,然后看向餐桌上的食物。</p>
|
||||
<p>那是海伯伦星的传统早餐——金色的能量面包、晶莹剔透的水果、还有散发着香气的热饮。虽然看起来简单,但每一口都蕴含着丰富的能量。</p>
|
||||
<p>「这是卢克爷爷让人准备的。」贝奇解释道,「他说,吃海伯伦星的食物,可以补充体力。」</p>
|
||||
<p>「那我就不客气了。」林克拿起一块面包,咬了一口。</p>
|
||||
<p>面包入口即化,一股温暖的能量流入体内,让人感到精神焕发。</p>
|
||||
<p>「好吃!」他赞叹道。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐在轻松愉快的氛围中进行。</p>
|
||||
<p>贝奇不停地给林克夹菜,仿佛要把所有好吃的都堆到他碗里。艾泽拉则优雅地吃着,偶尔用温柔的目光看着林克。</p>
|
||||
<p>米娅和皇女聊着天界的近况,虽然天界已经恢复了和平,但重建工作仍在继续。</p>
|
||||
<p>「林克大人,您什么时候回天界看看?」米娅问道,「皇女陛下和天界的人民都很想念您。」</p>
|
||||
<p>「等这边的事情稳定下来吧。」林克说道,「卢克爷爷的身体还需要观察一段时间。」</p>
|
||||
<p>「我可以理解。」皇女点点头,「您总是这样,把别人的事情放在第一位。」</p>
|
||||
<p>「因为你们对我来说很重要。」林克微笑着说。</p>
|
||||
<p>皇女的脸微微泛红,低下头继续吃早餐。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐后,林克带着众人在寂静城中散步。</p>
|
||||
<p>古老能量核心稳定运转,整个城堡都充满了生机。墙壁上的水晶散发着柔和的光芒,齿轮在头顶缓缓转动,发出舒缓的声响。</p>
|
||||
<p>「这里好美...」米娅感叹道,「比刚来的时候温暖多了。」</p>
|
||||
<p>「那是因为能量核心被激活了。」艾泽拉解释道,「以前这里充满了压抑的气息,现在...终于有了家的感觉。」</p>
|
||||
<p>她看向林克,眼中满是感激:「这都是因为你,林克。」</p>
|
||||
<p>「是我们大家一起努力的结果。」林克握住她的手。</p>
|
||||
<p>贝奇跑到前面,转过身对着大家挥手:「快来!我带你们去看一个地方!」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>贝奇带他们来到了寂静城的观景台。</p>
|
||||
<p>从这里可以俯瞰整个克洛诺斯岛,紫色的虚空能量在四周流动,远处的天界散发着柔和的光芒。</p>
|
||||
<p>「好美...」皇女惊叹道。</p>
|
||||
<p>「这里是我最喜欢的地方。」贝奇靠在林克怀里,「以前,我经常一个人来这里,看着外面的世界,想象着有一天能出去看看...」</p>
|
||||
<p>「现在你可以出去了。」林克说道,「等一切安定下来,我带你去看阿拉德大陆、天界、还有魔界的其他地方。」</p>
|
||||
<p>「真的吗?」贝奇眼睛亮了起来。</p>
|
||||
<p>「真的。」林克点头,「不仅是你,还有艾泽拉、米娅、皇女...我们一起去。」</p>
|
||||
<p>「太好了!」贝奇兴奋地跳了起来。</p>
|
||||
<p>艾泽拉微笑着看着这一幕,眼中闪过一丝憧憬。</p>
|
||||
<p>「我也...很想看看外面的世界。」她轻声说道,「三十年来,我一直守护着寂静城,从未离开过...」</p>
|
||||
<p>「以后我们一起。」林克将她搂入怀中,「我带你去看遍这个世界。」</p>
|
||||
<p>艾泽拉将脸埋在他胸口,轻轻点了点头。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>中午时分,众人回到了核心实验室。</p>
|
||||
<p>卢克坐在能量核心旁边,看到林克他们进来,脸上露出了慈祥的笑容。</p>
|
||||
<p>「年轻人,玩得开心吗?」</p>
|
||||
<p>「很开心,卢克爷爷。」林克说道,「谢谢您为我们准备的一切。」</p>
|
||||
<p>「应该是我谢谢你。」卢克说道,「你不仅拯救了我的生命,还给了贝奇和艾泽拉幸福...海伯伦星的王,欠你太多。」</p>
|
||||
<p>「您别这么说。」林克坐到卢克身边,「您是我的家人,我做这些都是应该的。」</p>
|
||||
<p>卢克看着他,浑浊的眼睛中闪过一丝欣慰。</p>
|
||||
<p>「年轻人,我有一个请求。」</p>
|
||||
<p>「您说。」</p>
|
||||
<p>「贝奇和艾泽拉...就拜托你了。」卢克握住林克的手,「她们是我最珍贵的宝物,我希望你能永远保护她们。」</p>
|
||||
<p>林克郑重地点头:「我答应您,卢克爷爷。我会用我的生命保护她们。」</p>
|
||||
<p>贝奇和艾泽拉听到这话,眼中都泛起了泪光。</p>
|
||||
<p>「卢克爷爷...」她们同时扑进卢克的怀里。</p>
|
||||
<p>林克看着这温馨的一幕,心中暗暗发誓。</p>
|
||||
<p>是的,他会保护她们。</p>
|
||||
<p>保护这个他深爱的家庭,保护这个他们共同守护的世界。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-102.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-104.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-73.html" class="sidebar-chapter ">第73章:根特防御战·钢铁与血肉的碰撞</a>
|
||||
<a href="chapter-74.html" class="sidebar-chapter ">第74章:夜间袭击战·银勺杂技团的覆灭</a>
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter current">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(103)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,930 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·贝奇与艾泽拉 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 104</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,午后。</p>
|
||||
<p>林克和卢克在研究古老能量核心的维护问题,米娅和皇女回天界处理政务。寂静城中,只剩下贝奇和艾泽拉两个女人。</p>
|
||||
<p>「艾泽拉姐姐...」贝奇拉着艾泽拉的手,眼中满是期待,「我们去花园玩吧!」</p>
|
||||
<p>「花园?」艾泽拉微微一愣,「寂静城有花园吗?」</p>
|
||||
<p>「有啊!」贝奇兴奋地点头,「在城堡的顶层,卢克爷爷以前种了很多花!虽然很多年没人打理了,但是...我想和你一起去看看!」</p>
|
||||
<p>艾泽拉看着眼前这个活泼的少女,心中涌起一股温柔。</p>
|
||||
<p>「好。」她微笑着说,「我们一起去。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>寂静城顶层花园。</p>
|
||||
<p>这里确实曾经是一座美丽的花园,但多年的荒废让大部分植物都枯萎了。只有一些顽强的花朵还在角落里绽放,散发着淡淡的香气。</p>
|
||||
<p>「好可惜...」贝奇看着枯萎的花丛,眼中闪过一丝悲伤,「以前这里好美的...」</p>
|
||||
<p>「没关系。」艾泽拉蹲下身,轻轻抚摸着一朵还在绽放的小花,「我们可以重新种。」</p>
|
||||
<p>「真的吗?」贝奇眼睛亮了起来。</p>
|
||||
<p>「当然。」艾泽拉站起身,「我守护寂静城三十年,对这里的每一寸土地都很熟悉。我知道哪里有种子,哪里有工具。」</p>
|
||||
<p>她拉着贝奇的手:「我们一起,让这座花园重新绽放。」</p>
|
||||
<p>「嗯!」贝奇用力点头。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两个女人开始在花园中忙碌起来。</p>
|
||||
<p>艾泽拉用魔法清理枯萎的植物,贝奇则用她的创造能力培育新的花苗。两人配合默契,虽然性格迥异,但在这一刻却仿佛心意相通。</p>
|
||||
<p>「艾泽拉姐姐...」贝奇一边种花,一边问道,「你为什么会喜欢上林克呢?」</p>
|
||||
<p>艾泽拉的手微微一顿,脸上泛起红晕。</p>
|
||||
<p>「怎么突然问这个...」</p>
|
||||
<p>「我想知道!」贝奇凑过来,眼中满是好奇,「是因为他很帅吗?还是因为他很强?」</p>
|
||||
<p>艾泽拉沉默了片刻,然后轻声说道:「是因为...他的善良。」</p>
|
||||
<p>「善良?」</p>
|
||||
<p>「嗯。」艾泽拉点头,「我见过很多强大的冒险家,但他们大多只关心自己的力量和利益。但林克不同...他帮助卢克爷爷,不是为了得到什么,而是真心想要帮助我们。」</p>
|
||||
<p>她看着手中的花苗,眼中满是温柔:「那一刻,我就知道...这个男人值得我托付一生。」</p>
|
||||
<p>贝奇听着,脸上露出理解的笑容。</p>
|
||||
<p>「我也是!」她说道,「林克先生打开容器的那一刻,我感受到了从未有过的温暖。他把我当作真正的人,而不是一个造物...」</p>
|
||||
<p>两个女人对视一眼,同时笑了起来。</p>
|
||||
<p>「我们真是姐妹呢。」贝奇说道,「喜欢上同一个人。」</p>
|
||||
<p>「是啊。」艾泽拉微笑着说,「以后...我们要一起守护他。」</p>
|
||||
<p>「嗯!一起!」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚时分,花园已经焕然一新。</p>
|
||||
<p>枯萎的植物被清理干净,新的花苗在土壤中扎根。虽然还没有开花,但已经能看到生命的迹象。</p>
|
||||
<p>「好累...」贝奇瘫坐在长椅上,「但是好开心!」</p>
|
||||
<p>艾泽拉坐在她身边,递给她一杯水:「喝点水吧。」</p>
|
||||
<p>「谢谢姐姐!」贝奇接过水杯,大口喝了起来。</p>
|
||||
<p>夕阳的光芒洒在两人身上,给她们镀上了一层金色的光晕。</p>
|
||||
<p>「贝奇。」艾泽拉突然说道,「以后...我可以把你当作真正的妹妹吗?」</p>
|
||||
<p>贝奇愣了一下,然后眼中涌出泪水。</p>
|
||||
<p>「当然可以!」她扑进艾泽拉怀里,「我一直想要一个姐姐!一个真正的姐姐!」</p>
|
||||
<p>艾泽拉轻轻拍着她的背,眼中也泛起了泪光。</p>
|
||||
<p>「我也是。」她轻声说道,「三十年来,我一直一个人...现在,我终于有了家人。」</p>
|
||||
<p>两人相拥而泣,在夕阳下,她们的影子交织在一起,仿佛真正的姐妹。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克找到她们时,看到的就是这样一幅画面。</p>
|
||||
<p>两个女人坐在长椅上,手牵着手,脸上带着满足的笑容。花园虽然还没有开花,但已经充满了生机。</p>
|
||||
<p>「你们在这里啊。」林克走过来,「花园...是你们整理的?」</p>
|
||||
<p>「嗯!」贝奇跳起来,扑进林克怀里,「我和艾泽拉姐姐一起整理的!以后这里会变成最美的花园!」</p>
|
||||
<p>「是吗?」林克微笑着看向艾泽拉。</p>
|
||||
<p>艾泽拉站起身,走到林克身边,轻轻挽住他的手臂:「贝奇说,想和你一起看花。」</p>
|
||||
<p>「那等花开了,我们一起看。」林克说道。</p>
|
||||
<p>「嗯!」贝奇和艾泽拉同时点头,脸上洋溢着幸福的笑容。</p>
|
||||
<p>三人站在花园中,望着天边的夕阳,心中充满了对未来的期待。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外一百零二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-103.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-105.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-74.html" class="sidebar-chapter ">第74章:夜间袭击战·银勺杂技团的覆灭</a>
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter current">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(104)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,914 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·卢克的嘱托 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 105</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,黄昏。</p>
|
||||
<p>林克被卢克叫到核心实验室。老人坐在能量核心旁边,浑浊的眼睛望着跳动的光芒,脸上带着复杂的神色。</p>
|
||||
<p>「卢克爷爷,您找我?」林克走到他身边坐下。</p>
|
||||
<p>「年轻人...」卢克缓缓转过头,看着他,「我有话想对你说。」</p>
|
||||
<p>「您说。」</p>
|
||||
<p>卢克沉默了片刻,似乎在组织语言。</p>
|
||||
<p>「贝奇...是我用核心能量创造的生命。」他缓缓说道,「她虽然不是人类,但在我心中,她就是我的女儿。」</p>
|
||||
<p>「我明白。」林克点头。</p>
|
||||
<p>「这三十年...」卢克的声音有些颤抖,「她一直被关在容器里,从未见过外面的世界。我本想等她的身体成熟后再放她出来,但是...我的身体状况越来越差,恐怕等不到那一天了。」</p>
|
||||
<p>他抬起头,浑浊的眼睛中满是悲伤:「如果不是你出现,贝奇可能会永远被关在那个容器里,直到能量耗尽...」</p>
|
||||
<p>「卢克爷爷...」</p>
|
||||
<p>「谢谢你,年轻人。」卢克握住林克的手,「谢谢你救了贝奇,给了她自由。」</p>
|
||||
<p>林克感受着老人干枯的手掌,心中涌起一股酸涩。</p>
|
||||
<p>「这是我应该做的。」他说道,「贝奇是一个善良的女孩,她值得被善待。」</p>
|
||||
<p>「是啊...」卢克露出了微笑,「她善良、纯真,就像她母亲...」</p>
|
||||
<p>他顿了顿,眼中闪过一丝怀念:「海伯伦星的王后,我的妻子...她在星球毁灭时牺牲了。我用最后的力量逃出来,带走了贝奇的胚胎...」</p>
|
||||
<p>林克静静地听着,没有打断。</p>
|
||||
<p>「我本想重建海伯伦星,让贝奇在一个美好的世界长大。」卢克继续说道,「但是...我失败了。我耗尽了所有力量,只能建造这座寂静城,勉强维持生命...」</p>
|
||||
<p>他的声音变得低沉:「我把贝奇关在容器里,不是因为不爱她,而是因为我害怕...害怕自己死后,她一个人无法生存...」</p>
|
||||
<p>「卢克爷爷...」林克心中涌起一股强烈的情感。</p>
|
||||
<p>这个老人,为了女儿,独自承受了三十年的孤独和痛苦...</p>
|
||||
<p>「但是现在,我不害怕了。」卢克抬起头,眼中闪烁着光芒,「因为我遇到了你。」</p>
|
||||
<p>他紧紧握住林克的手:「年轻人,我把贝奇托付给你。请你...代替我照顾她,保护她,给她幸福...」</p>
|
||||
<p>「我答应您。」林克郑重地说道,「我会用我的生命保护贝奇,给她幸福。」</p>
|
||||
<p>卢克露出了欣慰的笑容,那笑容中带着释然,也带着感激。</p>
|
||||
<p>「谢谢你...」他轻声说道,「海伯伦星的王,终于可以安心地休息了...」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>从核心实验室出来,林克看到贝奇站在门口,眼中满是泪水。</p>
|
||||
<p>「贝奇...」</p>
|
||||
<p>「我听到了...」贝奇扑进他怀里,声音哽咽,「卢克爷爷的话...我都听到了...」</p>
|
||||
<p>林克轻轻拍着她的背,没有说话。</p>
|
||||
<p>「林克...」贝奇抬起头,紫色的眼睛中满是泪水,「你会一直陪着我吗?」</p>
|
||||
<p>「会。」林克坚定地说道,「我会一直陪着你,直到永远。」</p>
|
||||
<p>贝奇将脸埋在他胸口,泪水打湿了他的衣襟。</p>
|
||||
<p>「谢谢你...林克...」她轻声说道,「谢谢你愿意接受我...接受这样的我...」</p>
|
||||
<p>林克捧起她的脸,轻轻擦去她的泪水。</p>
|
||||
<p>「傻瓜。」他微笑着说,「我爱的是你,不管你是人类还是人造人,我都爱你。」</p>
|
||||
<p>贝奇愣住了,然后脸上绽放出灿烂的笑容。</p>
|
||||
<p>「我也爱你,林克。」她踮起脚尖,吻上了他的唇,「永远爱你...」</p>
|
||||
<p>在夕阳的光芒中,两人相拥而吻,仿佛时间都静止了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外一百零三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-104.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-106.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-75.html" class="sidebar-chapter ">第75章:补给线阻断战·UM-0终结者</a>
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter current">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(105)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,909 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>时空之门的召唤 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 106</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,王之书库。</p>
|
||||
<p>林克站在巨大的水晶控制台前,眉头紧锁。屏幕上显示着密密麻麻的数据,那是关于时空之门的古老记录。</p>
|
||||
<p>「时空之门...真的存在吗?」贝奇站在他身边,眼中满是好奇。</p>
|
||||
<p>「存在。」卡西利亚斯从阴影中走出,「那是海伯伦星最高科技的结晶,可以穿越时空,回到过去。」</p>
|
||||
<p>「为什么要回去?」艾泽拉问道,「过去的事情...不是已经无法改变了吗?」</p>
|
||||
<p>「不。」林克摇头,「时空之门可以改变过去。虽然会有代价,但...如果我们能改变使徒们的命运,就能阻止赫尔德的阴谋。」</p>
|
||||
<p>他看向众人,眼中闪烁着坚定的光芒:「我要回到过去,拯救那些不该死去的使徒。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>时空之门位于寂静城的最深处,是一扇由纯金与水晶构成的巨大门扉。门上刻满了复杂的符文,散发着神秘而古老的气息。</p>
|
||||
<p>「这就是...时空之门...」米娅惊叹道,「比想象中还要壮观...」</p>
|
||||
<p>「使用它需要消耗巨大的能量。」卡西利亚斯说道,「而且,每次穿越只能停留有限的时间。如果超过时限,就会被永远困在过去。」</p>
|
||||
<p>「我明白。」林克点头,「我会小心的。」</p>
|
||||
<p>他看向身边的众人:「这次,我想一个人去。」</p>
|
||||
<p>「什么?!」贝奇惊呼,「不行!太危险了!」</p>
|
||||
<p>「贝奇说得对。」艾泽拉也说道,「我们不能让你一个人去冒险。」</p>
|
||||
<p>林克微笑着摇头:「时空之门只能容纳一个人。而且...我需要你们在这里守护寂静城,守护卢克爷爷。」</p>
|
||||
<p>他握住贝奇和艾泽拉的手:「相信我,我会平安回来的。」</p>
|
||||
<p>贝奇咬着嘴唇,眼中满是担忧,但最终还是点了点头。</p>
|
||||
<p>「答应我...一定要回来...」</p>
|
||||
<p>「我答应你。」林克将她拥入怀中,然后看向艾泽拉,「帮我照顾好她们。」</p>
|
||||
<p>「我会的。」艾泽拉点头,眼中闪烁着泪光。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克站在时空之门前,深吸一口气。</p>
|
||||
<p>「目标:巴卡尔的时代。」他在控制台上输入坐标,「时间:暴龙王陨落前三天。」</p>
|
||||
<p>门上的符文开始发光,金色的光芒从门缝中透出,照亮了整个空间。</p>
|
||||
<p>「林克!」贝奇突然喊道。</p>
|
||||
<p>林克转过头,看到贝奇和艾泽拉同时跑向他。</p>
|
||||
<p>「一定要平安回来!」贝奇扑进他怀里,泪水打湿了他的衣襟。</p>
|
||||
<p>「我们等你。」艾泽拉也抱住他,声音颤抖。</p>
|
||||
<p>林克紧紧抱着她们,心中涌起一股温暖。</p>
|
||||
<p>「我会的。」他在她们耳边轻声说道,「等我回来。」</p>
|
||||
<p>他松开她们,转身走向时空之门。</p>
|
||||
<p>金色的光芒将他笼罩,他感到身体在飞速移动,周围的一切都变得模糊。</p>
|
||||
<p>「巴卡尔...等着我。」</p>
|
||||
<p>「这一次,我一定要改变你的命运。」</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零四章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-105.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-107.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-76.html" class="sidebar-chapter ">第76章:追击歼灭战·机械吉赛尔的末路</a>
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter current">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(106)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,863 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>时空回响·赛丽亚的记忆 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 107.5</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克回到了现代。</p>
|
||||
<p>他睁开眼睛,发现自己站在艾尔文防线的入口。熟悉的阳光、熟悉的空气、熟悉的一切...但他心中却充满了复杂的情绪。</p>
|
||||
<p>500年前的那一幕还在他脑海中回荡——那个惊恐的金发少女,那个让他心痛的眼神,那句"我们...还会再见面吗?"</p>
|
||||
<p>"赛丽亚..."林克握紧拳头,"我找到你了。"</p>
|
||||
<p>他迫不及待地朝着赛丽亚的树屋走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>树屋前,赛丽亚正在浇花。她穿着那件熟悉的白色连衣裙,金色的长发在阳光下闪烁着柔和的光芒。</p>
|
||||
<p>"林克?"赛丽亚看到林克,脸上露出惊喜的笑容,"你回来了!时空之门的冒险怎么样?"</p>
|
||||
<p>林克没有回答,他只是静静地看着赛丽亚,眼中满是柔情。</p>
|
||||
<p>"怎么了?"赛丽亚被他看得有些不好意思,"为什么这么看着我?"</p>
|
||||
<p>"赛丽亚。"林克深吸一口气,"我有重要的事情要告诉你。"</p>
|
||||
<p>"什么事?"</p>
|
||||
<p>"关于...500年前的事。"</p>
|
||||
<p>赛丽亚愣住了:"500年前?"</p>
|
||||
<p>"我去了格兰之火。"林克说道,"我看到了...最初的你。"</p>
|
||||
<p>赛丽亚的身体微微一震:"你...你说什么?"</p>
|
||||
<p>"你在森林中醒来,什么都不记得,遇到了西岚,然后...遇到了我。"林克轻声说道,"我救了你,但我不能告诉你真相,因为那时空之门即将关闭。"</p>
|
||||
<p>赛丽亚的眼睛渐渐睁大,她的手开始颤抖:"那个剑士...那个救了我的银发剑士...是你?"</p>
|
||||
<p>"是我。"林克点头,"我记得你离开前回头看了我一眼,那个眼神...我记了500年。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>赛丽亚的眼泪夺眶而出。</p>
|
||||
<p>"原来...原来是你..."她颤抖着说,"我一直记得那个模糊的背影,那个让我心动的瞬间...我以为那只是我的幻觉,原来...原来都是真的..."</p>
|
||||
<p>她扑进林克的怀里,泣不成声:"我等了你...等了500年..."</p>
|
||||
<p>林克紧紧抱住她:"我知道...我现在告诉你,那个救你的人就是我。"</p>
|
||||
<p>"为什么...为什么不早点告诉我?"赛丽亚哭着问。</p>
|
||||
<p>"因为我刚回来。"林克温柔地说,"我第一时间就来找你了。"</p>
|
||||
<p>赛丽亚抬起头,看着林克的眼睛:"那个剑士...真的是你?"</p>
|
||||
<p>"真的。"林克点头,"我记得你穿着朴素的衣裙,金色的长发,还有...你回头看我时的那个眼神。"</p>
|
||||
<p>"那个眼神..."赛丽亚的脸微微发红,"我...我当时觉得你很熟悉,仿佛在哪里见过...但我不知道你是谁..."</p>
|
||||
<p>"现在你知道了。"林克微笑,"我就是那个剑士,也是...一直爱你的人。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>赛丽亚将脸埋在林克胸口,感受着他有力的心跳。</p>
|
||||
<p>"500年前..."她轻声说道,"你救了我,然后离开...我在艾尔文防线等你,等了500年..."</p>
|
||||
<p>"我知道。"林克抚摸着她的长发,"现在我终于找到你了。"</p>
|
||||
<p>"这不是巧合..."赛丽亚抬起头,眼中闪烁着光芒,"这是命中注定...我们的相遇,是命中注定的..."</p>
|
||||
<p>"是的。"林克点头,"500年前我救了你,500年后我找到了你...这不是巧合,是命运。"</p>
|
||||
<p>赛丽亚踮起脚尖,吻上了林克的唇。</p>
|
||||
<p>这个吻温柔而绵长,带着500年的等待和思念,带着命中注定的缘分和爱情。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夕阳西下,两人坐在树屋前的台阶上,相依相偎。</p>
|
||||
<p>"林克。"赛丽亚轻声说道,"谢谢你...谢谢你500年前救了我,谢谢你500年后找到我..."</p>
|
||||
<p>"这是我应该做的。"林克握紧她的手,"不管过去多久,我都会找到你。"</p>
|
||||
<p>"以后..."赛丽亚靠在他肩上,"你还会去时空之门吗?"</p>
|
||||
<p>"会的。"林克说道,"还有更多的真相等着我去揭开,还有...赫尔德的阴谋需要阻止。"</p>
|
||||
<p>"那我等你。"赛丽亚说道,"不管多久,我都会在这里等你。"</p>
|
||||
<p>"赛丽亚..."林克感动地看着她。</p>
|
||||
<p>"因为..."赛丽亚微笑,"我已经等了500年,不在乎再多等一段时间。"</p>
|
||||
<p>两人相视一笑,在夕阳下紧紧相拥。</p>
|
||||
<p>命中注定的缘分,终于在这一刻圆满。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零七点五章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-106.5.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-108.5.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-107.5.html" class="sidebar-chapter current">第107.5章:时空回响·赛丽亚的记忆</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(107.5)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,976 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>格兰之火 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 107</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>格兰之森,500年前。</p>
|
||||
<p>金色的光芒在森林深处闪烁,空间如同水波般扭曲。一道身影从光芒中走出,踏在了这片古老的大地上。</p>
|
||||
<p>林克睁开眼睛,映入眼帘的是一片郁郁葱葱的森林。高大的树木遮天蔽日,阳光透过树叶的缝隙洒下斑驳的光影。空气中弥漫着草木的清香,还有一丝若有若无的烟火气息。</p>
|
||||
<p>"这就是...500年前的格兰之森?"</p>
|
||||
<p>林克环顾四周,这里的景色与他记忆中的格兰之森几乎一模一样,但又有些微妙的不同。树木更加茂盛,空气中没有那种被污染后的浑浊感,一切都显得那么原始、那么纯净。</p>
|
||||
<p>他低头看了看自己的双手,感受着体内流转的剑魂之力。时空之门的穿越似乎对他的力量产生了一些影响——他能感觉到,部分高阶技能变得难以施展,仿佛被某种规则压制在70级以内。</p>
|
||||
<p>"70级以内的技能..."林克喃喃自语,握紧了腰间的光剑"细雪之舞","足够了。"</p>
|
||||
<p>他深吸一口气,朝着森林深处走去。根据卡西利亚斯的说法,格兰之火即将发生,而那场大火将改变整个阿拉德大陆的命运。更重要的是,那场大火与赛丽亚的身世有关——那个他深爱的女人,那个在艾尔文防线等待他归来的女人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克在森林中穿行,很快就发现了异常。</p>
|
||||
<p>前方传来打斗声,还有魔法的光芒闪烁。林克加快脚步,躲在一棵大树后观察。</p>
|
||||
<p>他看到了一个意想不到的场景——</p>
|
||||
<p>一个银发的男子正在与一群怪物战斗。那男子手持太刀,剑法凌厉,每一击都带着强大的剑气。他的动作行云流水,仿佛与周围的环境融为一体,虽然还没有未来那种历经沧桑的沉稳,但已经展现出了非凡的剑术天赋。</p>
|
||||
<p>"西岚?"</p>
|
||||
<p>林克认出了那个男子。四剑圣之一的西岚,未来的时空之门守护者。但现在的西岚看起来年轻许多,眼神中充满了朝气和锐气。</p>
|
||||
<p>更让林克惊讶的是,西岚身边还有一个人——一个金发的少女,正躲在树后瑟瑟发抖。</p>
|
||||
<p>那是一张林克无比熟悉的面孔。</p>
|
||||
<p>赛丽亚。</p>
|
||||
<p>不,不是他认识的那个赛丽亚。这个赛丽亚看起来更加稚嫩,眼神中充满了恐惧和迷茫。她穿着朴素的衣裙,身上没有任何力量的波动,就像一个普通的乡村少女。</p>
|
||||
<p>"这就是...最初的赛丽亚?"林克心中震撼。</p>
|
||||
<p>"该死,这些怪物是从哪里来的?"西岚一边战斗一边咒骂,他的太刀划出一道优美的弧线,将一只猫妖斩成两半,"小姑娘,你没事吧?"</p>
|
||||
<p>"我...我不知道..."赛丽亚颤抖着说,声音中带着哭腔,"我只是...只是在这里醒来...什么都不记得了...我不知道我是谁...也不知道为什么会在这里..."</p>
|
||||
<p>林克心中一震。</p>
|
||||
<p>这就是格兰之火的真相吗?赛丽亚的身世,她失去的记忆,一切都要从这里开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>突然,森林深处传来一声巨响。</p>
|
||||
<p>林克转头看去,只见一道巨大的火柱冲天而起,瞬间点燃了周围的树木。那火焰呈现出诡异的紫色,仿佛蕴含着某种邪恶的力量。火势蔓延得极快,转眼间就已经形成了一片火海,朝着四面八方扩散。</p>
|
||||
<p>"不好!"西岚脸色大变,"是魔法火焰!这种规模的魔法...难道是那个传说中的使徒?"</p>
|
||||
<p>他话还没说完,更多的怪物从火海中涌出。这些怪物浑身燃烧着紫色的火焰,眼中闪烁着疯狂的光芒,形态扭曲而恐怖。它们发出刺耳的嘶吼,朝着西岚和赛丽亚扑来。</p>
|
||||
<p>"该死!"西岚咬牙,额头上渗出汗水,"小姑娘,快跑!往森林外面跑!"</p>
|
||||
<p>但赛丽亚已经吓得动弹不得,她的双腿发软,只能眼睁睁地看着那些燃烧的怪物逼近,眼中满是绝望。</p>
|
||||
<p>林克知道,他不能再躲藏了。</p>
|
||||
<p>"流心·跃!"</p>
|
||||
<p>他的身体如同离弦之箭般射出,光剑"细雪之舞"在空中划出一道冰蓝色的弧线。冰属性的剑气与火焰怪物碰撞,发出刺耳的嘶鸣声,白色的蒸汽瞬间弥漫开来。</p>
|
||||
<p>"什么人?!"西岚惊讶地看向林克,眼中充满警惕。</p>
|
||||
<p>林克没有回答,他的光剑已经连续斩出数剑,每一剑都精准地命中怪物的要害。里鬼剑术在他的手中如同艺术般流畅,剑光闪烁间,数只火焰怪物已经倒地。</p>
|
||||
<p>"路过的剑士。"林克简短地回答,同时挡在了赛丽亚身前,他的背影如同一座山,将所有的危险都隔绝在外,"这些怪物交给我,你带她先走。"</p>
|
||||
<p>西岚深深地看了林克一眼,那眼神中有着探究、警惕,还有一丝感激。但此刻情况紧急,他没有时间多问。</p>
|
||||
<p>"好!多谢了!"</p>
|
||||
<p>西岚拉起赛丽亚的手,朝着森林外跑去。赛丽亚在离开前回头看了林克一眼,那眼神中充满了感激、困惑,还有一丝莫名的熟悉感,仿佛在哪里见过这个神秘的剑士。</p>
|
||||
<p>那一眼,让赛丽亚的心脏漏跳了一拍。</p>
|
||||
<p>那个银发的剑士,他的背影如此熟悉,仿佛在她的梦中出现过无数次。虽然她的记忆一片空白,但内心深处却有一个声音在告诉她——这个人,很重要。</p>
|
||||
<p>"等等..."赛丽亚想要开口,但西岚已经拉着她跑出了很远。</p>
|
||||
<p>她最后回头看了一眼,那个剑士已经被火焰怪物包围,但他的剑光依然在火海中闪烁,如同一颗不屈的星辰。</p>
|
||||
<p>"我们...还会再见面吗?"赛丽亚在心中默默问道。</p>
|
||||
<p>林克没有回头,他的注意力已经全部集中在眼前的敌人身上。但他感觉到了那道目光,那道让他心痛的目光。</p>
|
||||
<p>"对不起,赛丽亚..."他在心中默默说道,"现在我不能告诉你真相。但请相信,500年后,我一定会找到你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>火焰怪物越来越多,仿佛无穷无尽,从四面八方的火海中涌出。林克挥舞着光剑,剑魂的技能在手中绽放——里鬼剑术如同狂风暴雨,流心·刺精准致命,拔刀斩横扫千军。每一击都带走数只怪物的生命,但更多的怪物前仆后继地涌来。</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>林克的身形如同游龙般穿梭在怪物群中,光剑带起一道金色的龙形剑气,将周围的怪物全部击飞。但那些怪物落地后,竟然又摇摇晃晃地站了起来,身上的紫色火焰燃烧得更加旺盛。</p>
|
||||
<p>"不死之身?"林克皱眉,"不对,是有人在控制它们!"</p>
|
||||
<p>他闭上眼睛,感受着周围的能量波动。很快,他就发现了异常——在火海的深处,有一股强大而邪恶的力量正在操控着这一切。那股力量他并不陌生,在寂静城与赫尔德的使者战斗时,他就感受过类似的气息。</p>
|
||||
<p>"赫尔德..."林克低声说道,眼中闪过一丝寒光,"果然是你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克不再与那些小怪纠缠,他的身形如同闪电般朝着火海深处冲去。沿途的怪物试图阻挡他,但都被他的剑气斩成碎片。</p>
|
||||
<p>火海深处,林克终于看到了那个身影。</p>
|
||||
<p>那是一个身穿黑色长袍、戴着面具的神秘人,银色的长发从兜帽中垂落。她站在一座由紫色火焰构成的祭坛上,双手高举,口中念诵着古老的咒语。黑色的长袍在火焰中飘动,如同死神的披风。</p>
|
||||
<p>"黑袍人..."林克握紧光剑,"你就是这一切的幕后黑手!"</p>
|
||||
<p>黑袍人转过头,面具下的眼睛看向林克,发出阴冷的笑声:"哦?居然有人能穿越我的火焰屏障?有趣...你是什么人?"</p>
|
||||
<p>"一个来阻止你的人。"林克冷声说道,"赫尔德的走狗,你的阴谋不会得逞。"</p>
|
||||
<p>黑袍人的身体微微一震,然后轻笑出声:"居然知道赫尔德大人?看来,你不是这个时代的人。是西岚那个小鬼打开的时空之门吗?不...他的力量还不够..."</p>
|
||||
<p>她的目光变得锐利起来:"你是从未来来的?"</p>
|
||||
<p>林克没有回答,他的光剑已经指向了黑袍人:"我不会让你烧毁格兰之森,也不会让你伤害赛丽亚。"</p>
|
||||
<p>"赛丽亚?"黑袍人愣了一下,然后恍然大悟,"哦...你说那个容器啊。她可是我计划的关键,我怎么可能伤害她呢?这场大火,只是为了唤醒她体内的力量而已。"</p>
|
||||
<p>她举起双手,紫色的火焰变得更加狂暴:"不过,既然你来了,那就留下吧。一个来自未来的灵魂,应该能为我的计划提供不少能量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>黑袍人的实力比林克想象的还要强大。她操控着紫色的火焰,每一击都带着毁灭性的力量。林克挥舞着光剑,剑魂的技能全力施展——里鬼剑术、流心、拔刀斩、破军升龙击、猛龙断空斩,所有的技能如同行云流水般连贯而出。</p>
|
||||
<p>但黑袍人仿佛能够预知他的动作,每一次攻击都被她轻松化解。</p>
|
||||
<p>"就这点实力吗?"黑袍人嗤笑,"我还以为来自未来的你会有多强呢。看来,时空之门不仅限制了你的力量,还限制了你的成长啊。"</p>
|
||||
<p>林克咬牙,他知道对方说得没错。在70级的限制下,他无法使用极·神剑术等高级技能,实力大打折扣。</p>
|
||||
<p>但他没有放弃。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>无数剑气从林克身上爆发,形成了一道巨大的剑气风暴,朝着黑袍人席卷而去。这是他在70级以内能够使用的最强技能!</p>
|
||||
<p>"雕虫小技!"黑袍人冷笑,双手结印,一道紫色的火焰屏障出现在身前。</p>
|
||||
<p>剑气风暴与火焰屏障碰撞,发出震耳欲聋的轰鸣声。整个格兰之森都在震动,无数树木被余波摧毁。</p>
|
||||
<p>最终,剑气风暴消散,火焰屏障也出现了裂痕。</p>
|
||||
<p>"不错..."黑袍人看着林克,眼中闪过一丝赞赏,"在70级的限制下,居然能伤到我。你有资格知道我的名字——我是赫尔德大人的使者,『引导者』。"</p>
|
||||
<p>她缓缓抬起手,紫色的火焰在她掌心凝聚成一个巨大的火球:"但是,游戏到此为止了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这千钧一发之际,一道银色的剑光从天而降,将黑袍人逼退!</p>
|
||||
<p>"什么人?!"引导者大惊。</p>
|
||||
<p>一个身影落在林克身边,正是西岚。但此刻的西岚与之前不同,他的身上散发着一种古老而神秘的气息,双眼中仿佛蕴含着时空的奥秘。</p>
|
||||
<p>"西岚?"林克惊讶地看着他。</p>
|
||||
<p>"不...不是西岚..."引导者的声音中带着一丝恐惧,"你是...时空的守护者?!"</p>
|
||||
<p>西岚——或者说,被某种力量附身的西岚——没有回答。他只是淡淡地看了林克一眼,然后举起太刀,朝着引导者斩去。</p>
|
||||
<p>那一刀,仿佛斩断了时空。</p>
|
||||
<p>引导者发出一声凄厉的惨叫,她的身体开始崩溃,紫色的火焰四处飞散。</p>
|
||||
<p>"该死...这次算你们赢了..."她的声音越来越虚弱,"但是,计划不会停止。格兰之火已经点燃,赛丽亚的力量即将觉醒。这一切,都是命中注定的..."</p>
|
||||
<p>她的身体彻底消散,只留下一片紫色的火焰在燃烧。</p>
|
||||
<p>西岚——时空的守护者——看了林克一眼,那眼神中有着探究、惊讶,还有一丝莫名的熟悉感。然后,他的身体一软,倒在了地上,那种古老的气息也随之消散。</p>
|
||||
<p>林克连忙扶住他,发现西岚只是昏迷了过去,并没有生命危险。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>格兰之火在继续燃烧,但火势已经减弱了许多。</p>
|
||||
<p>林克站在火海中,看着昏迷的西岚,心中充满了复杂的情绪。他改变了历史吗?还是这一切本来就是历史的一部分?</p>
|
||||
<p>远处,赛丽亚的身影若隐若现。她站在森林的边缘,看着这片燃烧的大地,眼中流下了泪水。</p>
|
||||
<p>林克知道,从这一刻起,赛丽亚的命运已经改变。她将失去记忆,在艾尔文防线醒来,等待着一个名叫林克的冒险家。</p>
|
||||
<p>而他自己,也必须离开了。时空之门的时限将至,如果他继续留在这里,就会被永远困在过去。</p>
|
||||
<p>"赛丽亚..."林克轻声说道,"等着我...500年后,我们一定会再次相遇..."</p>
|
||||
<p>他转身走向森林深处,那里有一道金色的光芒正在等待着他。</p>
|
||||
<p>时空之门,即将关闭。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零五章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-106.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-108.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-77.html" class="sidebar-chapter ">第77章:海上列车·鲁夫特悬空海港</a>
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter current">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(107)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,975 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>瘟疫之源 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 108</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>三天后,林克再次来到时空之门前。</p>
|
||||
<p>这三天里,他和赛丽亚度过了难得的宁静时光。他们一起看日出日落,一起在艾尔文防线的街道上散步,一起回忆500年前的那场相遇。</p>
|
||||
<p>但林克知道,他不能一直停留在这里。赫尔德的阴谋还在继续,时空之门中还有更多的真相等待揭开。</p>
|
||||
<p>"一定要去吗?"赛丽亚站在时空之门前,眼中满是不舍。</p>
|
||||
<p>"是的。"林克握住她的手,"瘟疫之源、暗黑圣战、昔日悲鸣...还有很多地方等着我去。只有揭开全部真相,才能真正阻止赫尔德。"</p>
|
||||
<p>赛丽亚轻轻点头:"我明白。我会在这里等你回来。"</p>
|
||||
<p>"等我。"林克在她额头上轻轻一吻,"这次,不会再让你等500年了。"</p>
|
||||
<p>赛丽亚笑了,眼泪却在眼眶中打转:"快去吧,别让命运等太久。"</p>
|
||||
<p>林克转身,踏入时空之门。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的光芒闪烁,林克感到身体被时空之力牵引,穿越到了另一个时间点。</p>
|
||||
<p>当他睁开眼睛时,眼前的景象让他心中一沉。</p>
|
||||
<p>这里曾经是一个宁静的村庄——低矮的石屋错落有致,街道两旁种着暗精灵特有的紫罗兰。但此刻,整个村庄笼罩在一层黑色的雾气中,空气中弥漫着腐臭和死亡的气息。</p>
|
||||
<p>街道上,曾经繁华的市集如今一片狼藉。摊位翻倒,货物散落,还有一些...尸体。</p>
|
||||
<p>不,不是尸体。</p>
|
||||
<p>那些东西在动。</p>
|
||||
<p>"这就是...诺伊佩拉?"林克握紧了细雪之舞,冰属性的光剑在这种环境下显得格外清冷。</p>
|
||||
<p>他记得这个地方。在未来的时间线里,诺伊佩拉因为瘟疫而变成了死城,暗精灵王国不得不封锁这片区域。而现在,他正站在瘟疫爆发的原点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"救...救命..."</p>
|
||||
<p>微弱的声音从废墟中传来。林克循声走去,在一座倒塌的石屋下,发现了一个还活着的暗精灵。</p>
|
||||
<p>那是一个身穿民兵制服的暗精灵男子,他的脸色苍白,身上有多处被感染的痕迹,黑色的纹路在皮肤下蔓延。但他的眼神依然清醒,手中紧紧握着一把短剑。</p>
|
||||
<p>"你是谁?"暗精灵警惕地看着林克。</p>
|
||||
<p>"路过的剑士。"林克蹲下身,"这里发生了什么?"</p>
|
||||
<p>暗精灵苦笑一声:"瘟疫...一夜之间,整个村庄都毁了。我叫贺加斯,是这里的民兵队长。"</p>
|
||||
<p>他艰难地坐起身,指向村庄中央:"昨天夜里,一个身穿黑色斗篷的神秘人出现在村子里。他...他在水源里投放了什么东西。然后,天就亮了,瘟疫爆发了。"</p>
|
||||
<p>"黑色斗篷?"林克心中一凛。在格兰之火,他也遇到了那个黑袍人。</p>
|
||||
<p>"那个人...不是普通人。"贺加斯的声音颤抖,"他使用的是某种邪恶的魔法,我从未见过。村民们...有的当场死亡,有的变成了那种怪物..."</p>
|
||||
<p>他指向街道尽头,那里有几个身影在游荡——那是被瘟疫感染的盗尸者,它们的身体扭曲变形,眼中闪烁着疯狂的光芒。</p>
|
||||
<p>"求求你..."贺加斯抓住林克的手,"我知道我活不了多久了,但请你...阻止那个黑斗篷。他还在村子里,他在进行某种仪式...救救我的族人..."</p>
|
||||
<p>林克看着这个濒临死亡的民兵队长,郑重地点头:"我答应你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克站起身,朝着村庄中央走去。</p>
|
||||
<p>沿途,他遭遇了各种瘟疫怪物。有的是被感染的村民变成的盗尸者,它们行动迟缓但数量众多;有的是被瘟疫溶解的怪物,黑色的浆糊状生物,散发着剧毒的气息。</p>
|
||||
<p>"流心·刺!"</p>
|
||||
<p>林克的光剑精准地刺穿一只盗尸者的头颅,冰属性的剑气瞬间冻结了它的身体。但更多的怪物从四面八方涌来。</p>
|
||||
<p>他深吸一口气,光剑在手中旋转。</p>
|
||||
<p>"里鬼剑术!"</p>
|
||||
<p>无数剑气如同暴风般席卷而出,将周围的怪物全部斩成碎片。冰蓝色的剑光在黑色的瘟疫雾气中显得格外耀眼。</p>
|
||||
<p>但林克注意到,这些怪物被击败后,身上会掉落一些闪烁着微光的碎片——那是时间之痕,西岚需要的东西。</p>
|
||||
<p>他一边战斗,一边收集时间之痕。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>村庄中央,林克终于找到了那个黑色斗篷人。</p>
|
||||
<p>那是一个身穿黑色长袍、戴着面具的神秘人,和格兰之火遇到的那个一模一样。她站在一座祭坛上,手中高举着一瓶黑色的液体,正在进行某种邪恶的仪式。祭坛周围,黑色的能量在涌动,瘟疫的气息更加浓郁。</p>
|
||||
<p>"又是你..."林克冷声说道,"格兰之火的账还没算完,你竟然又在这里散播瘟疫!"</p>
|
||||
<p>黑袍人转过身,面具下的眼睛看向林克,发出阴冷的笑声:"哦?又是你?看来上次的教训还不够啊。"</p>
|
||||
<p>林克心中一震——她记得格兰之火的事情!</p>
|
||||
<p>"你到底是什么人?为什么要做这些?"</p>
|
||||
<p>"我?"黑袍人放下手中的瓶子,"我是赫尔德大人的使者,负责为'创新世纪'计划铺路。这场瘟疫,是为了削弱暗精灵王国,让他们在未来无法抵抗使徒的入侵。"</p>
|
||||
<p>她张开双臂,黑色的能量在她周身涌动:"狄瑞吉终将降临,而暗精灵王国将因为这场瘟疫而元气大伤。到时候,整个阿拉德大陆都将陷入混乱..."</p>
|
||||
<p>"我不会让你得逞的!"林克握紧光剑。</p>
|
||||
<p>"就凭你?"黑袍人嗤笑,"一个被时空之门限制在70级的剑士?"</p>
|
||||
<p>她双手结印,黑色的瘟疫能量化作无数触手,朝着林克席卷而来!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>黑袍人的瘟疫魔法诡异而强大,黑色的触手蕴含着剧毒,所过之处连石头都被腐蚀。林克挥舞着细雪之舞,冰属性的剑气与瘟疫能量碰撞,发出刺耳的嘶鸣声。</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>林克的身形如同游龙般冲向黑袍人,光剑带起一道金色的龙形剑气。但黑袍人轻轻一闪,就避开了这一击。</p>
|
||||
<p>"太慢了。"黑袍人冷笑,"在70级的限制下,你的速度根本跟不上我。"</p>
|
||||
<p>她挥手间,更多的瘟疫触手从四面八方涌来,将林克团团围住。</p>
|
||||
<p>林克咬牙,他知道对方说得没错。在70级的限制下,他无法使用极·神剑术等高级技能,实力大打折扣。</p>
|
||||
<p>但他没有放弃。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>无数剑气从林克身上爆发,形成了一道巨大的剑气风暴,将周围的瘟疫触手全部斩断。这是他在70级以内能够使用的最强技能!</p>
|
||||
<p>"有点意思..."黑袍人终于露出了认真的表情,"但还不够!"</p>
|
||||
<p>她双手高举,祭坛上的黑色液体开始沸腾,一股更加强大的瘟疫能量爆发出来!</p>
|
||||
<p>"瘟疫爆发!"</p>
|
||||
<p>黑色的能量如同潮水般涌向林克,所过之处一切都被腐蚀。林克感到前所未有的压力,这种级别的攻击,已经超出了普通70级技能的防御范围!</p>
|
||||
<p>就在这千钧一发之际,林克突然想起了什么。</p>
|
||||
<p>"细雪之舞...冰属性..."</p>
|
||||
<p>他低头看着手中的光剑,眼中闪过一丝明悟。</p>
|
||||
<p>瘟疫的本质是病毒和细菌,而极寒可以冻结一切生命活动!</p>
|
||||
<p>"流心·跃!"</p>
|
||||
<p>林克的身形高高跃起,躲过了瘟疫能量的正面冲击。同时,他将全身的剑魂之力注入细雪之舞,光剑爆发出前所未有的冰蓝色光芒!</p>
|
||||
<p>"极寒...拔刀斩!"</p>
|
||||
<p>这一剑,不是普通的拔刀斩。林克将冰属性的力量发挥到了极致,剑气所过之处,连空气都被冻结!</p>
|
||||
<p>冰蓝色的剑气与黑色的瘟疫能量碰撞,发出震耳欲聋的轰鸣声。最终,极寒的剑气冻结了瘟疫能量,将它们全部粉碎!</p>
|
||||
<p>"什么?!"黑袍人大惊。</p>
|
||||
<p>林克没有给她反应的机会,身形如同闪电般冲到黑袍人面前。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>金色的龙形剑气穿透了黑袍人的防御,将她重重地击飞出去!</p>
|
||||
<p>黑袍人撞在祭坛上,面具碎裂,露出了一张苍白的脸。她的眼中满是不甘和震惊。</p>
|
||||
<p>"不可能...我怎么可能败给一个人类..."</p>
|
||||
<p>林克走到她面前,光剑指向她的咽喉:"你的阴谋结束了。"</p>
|
||||
<p>黑袍人突然狂笑起来:"结束?你以为阻止了我就能改变什么?狄瑞吉终将降临,瘟疫必将蔓延...这是命中注定的..."</p>
|
||||
<p>她的身体开始崩溃,黑色的能量从她体内爆发,然后彻底消散。</p>
|
||||
<p>"赫尔德...大人...计划不会停止..."</p>
|
||||
<p>这是她的最后一句话。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束,祭坛上的黑色液体也随之消散。</p>
|
||||
<p>林克收集了大量时间之痕,这些都是西岚需要的东西。但他心中却没有胜利的喜悦。</p>
|
||||
<p>黑袍人的话在他耳边回响——</p>
|
||||
<p>"狄瑞吉终将降临...这是命中注定的..."</p>
|
||||
<p>赫尔德的阴谋比他想象的更加深远。格兰之火、瘟疫之源,这些都只是开始。</p>
|
||||
<p>林克转身离开,朝着时空之门的方向走去。</p>
|
||||
<p>在他身后,贺加斯靠在废墟上,看着林克的背影,眼中闪过一丝感激。</p>
|
||||
<p>"谢谢你...陌生人..."</p>
|
||||
<p>贺加斯闭上了眼睛,他的使命完成了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>时空之门前,林克回头望了一眼这片被瘟疫毁灭的土地。</p>
|
||||
<p>"诺伊佩拉...我会记住这个地方。"</p>
|
||||
<p>他踏入金色的光芒,前往下一个时间点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零八章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-107.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-109.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-78.html" class="sidebar-chapter ">第78章:列车上的海贼·铁鳞团的覆灭</a>
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter current">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(108)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,964 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>卡勒特之初 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 109</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克感到双脚踩在滚烫的沙地上。</p>
|
||||
<p>他睁开眼睛,映入眼帘的是一片荒凉的沙漠——无边无际的黄沙延伸至天际,烈日高悬,空气中弥漫着燥热的气息。远处,几座破旧的建筑孤零零地矗立着,像是被世界遗忘的角落。</p>
|
||||
<p>"这就是...无法地带?"</p>
|
||||
<p>林克环顾四周,这里与他见过的任何地方都不同。没有阿拉德的绿意盎然,没有天界的钢铁建筑,只有无尽的荒凉和...自由的气息。</p>
|
||||
<p>根据卡西利亚斯的说法,无法地带是天界最混乱的区域,这里没有法律,没有秩序,只有强者和弱者。而卡勒特组织,就是在这里诞生的。</p>
|
||||
<p>"卡勒特之初..."林克喃喃自语,"我要找到卡勒特组织诞生的原点。"</p>
|
||||
<p>他整理了一下装备,朝着远处的建筑群走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>破旧的酒馆前,几个衣衫褴褛的壮汉正在喝酒。他们看到林克走来,纷纷投来警惕的目光。</p>
|
||||
<p>"喂,小子,你是什么人?"为首的壮汉站起来,手中把玩着一把左轮手枪,"没见过你啊。"</p>
|
||||
<p>"路过的冒险家。"林克淡淡地说道,"我想打听一些事。"</p>
|
||||
<p>"打听事?"壮汉嗤笑,"在无法地带,信息可是要收费的。"</p>
|
||||
<p>"多少钱?"</p>
|
||||
<p>"看你的诚意。"壮汉上下打量着林克,"你身上那把剑不错,值不少钱吧?"</p>
|
||||
<p>林克眼中闪过一丝冷意,但他不想在这里惹事。他随手扔出一袋金币:"这些够吗?"</p>
|
||||
<p>壮汉接过钱袋,掂了掂,眼中闪过贪婪:"够了够了。你想打听什么?"</p>
|
||||
<p>"卡勒特组织。"林克说道,"我听说这里有一个武装集团正在崛起。"</p>
|
||||
<p>壮汉的表情变了,他左右看了看,压低声音:"你打听他们做什么?那群疯子可不是好惹的。"</p>
|
||||
<p>"只是好奇。"</p>
|
||||
<p>"好吧。"壮汉收起钱袋,"卡勒特的老大叫兰蒂卢斯,是个从军队逃出来的家伙。他聚集了一群无法无天的暴徒,专门抢劫过往的商队。最近他们好像得到了什么人的支持,武器突然变得先进了很多。"</p>
|
||||
<p>"得到了支持?"林克皱眉,"是什么人?"</p>
|
||||
<p>"不知道。"壮汉摇头,"有人说是一个穿黑袍的神秘人,但没人见过真面目。"</p>
|
||||
<p>林克心中一凛。又是黑袍人...和格兰之火、瘟疫之源一样的手法。</p>
|
||||
<p>"他们现在在哪?"</p>
|
||||
<p>"东边的一个废弃工厂,那是他们的据点。"壮汉指了指方向,"不过我劝你别去,那地方危险得很。"</p>
|
||||
<p>"谢谢。"林克转身离去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>前往工厂的路上,林克遭遇了几次袭击。</p>
|
||||
<p>无法地带的强盗们看到落单的旅行者,就像闻到血腥的鲨鱼。但当他们发现这个"落单的旅行者"有着远超想象的实力后,纷纷变成了尸体。</p>
|
||||
<p>"流心·刺!"</p>
|
||||
<p>林克的光剑精准地刺穿最后一名强盗的喉咙,鲜血染红了黄沙。他收起剑,继续向前走去。</p>
|
||||
<p>就在这时,他感觉到了一股异样的气息。</p>
|
||||
<p>那是一种...熟悉的邪恶气息,和格兰之火、瘟疫之源一模一样。</p>
|
||||
<p>"黑袍人..."林克循着气息走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>废弃工厂外,林克隐藏在阴影中观察。</p>
|
||||
<p>工厂内,一群暴徒正在搬运武器。那些武器明显不是无法地带能制造的——精密的枪械、先进的火炮,甚至还有初代的机动兵器。</p>
|
||||
<p>"这些武器..."林克皱眉,"是黑袍人提供的?"</p>
|
||||
<p>他悄悄潜入工厂,朝着气息最浓郁的方向摸去。</p>
|
||||
<p>工厂深处,一个身穿黑色长袍、戴着面具的身影正站在高台上,对着下方的暴徒们演讲。那身影和格兰之火、瘟疫之源遇到的黑袍人一模一样。</p>
|
||||
<p>"我的兄弟们!"黑袍人的声音沙哑而阴冷,"我们被天界抛弃,被世界遗忘!但今天,我们有了新的力量!有了支持我们的人!"</p>
|
||||
<p>她举起一把崭新的步枪:"这些武器,将让我们成为无法地带的主宰!然后...是整个天界!"</p>
|
||||
<p>下方的暴徒们发出狂热的欢呼。</p>
|
||||
<p>林克心中一凛。果然,又是黑袍人在背后操控!</p>
|
||||
<p>"兰蒂卢斯。"黑袍人看向一个身材高大的男子,"你将成为卡勒特的首领,带领他们征服一切。"</p>
|
||||
<p>"是!"兰蒂卢斯狂热地回应,"我不会让您失望的!"</p>
|
||||
<p>黑袍人满意地点头,然后转身走向工厂深处。</p>
|
||||
<p>林克悄悄跟了上去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>工厂深处的密室中,黑袍人正站在一座祭坛前,手中拿着一块黑色的水晶。</p>
|
||||
<p>"又是祭坛..."林克躲在暗处观察。</p>
|
||||
<p>和格兰之火、瘟疫之源一样,黑袍人似乎在每个地方都建立了这种祭坛,用来进行某种邪恶的仪式。</p>
|
||||
<p>"谁?!"黑袍人突然转头,面具下的眼睛看向林克藏身的方向。</p>
|
||||
<p>林克知道自己被发现了,干脆走了出来。</p>
|
||||
<p>"又是你。"黑袍人发出阴冷的笑声,"格兰之火和瘟疫之源都没能阻止你,看来你比我想象中更难缠。"</p>
|
||||
<p>"你的阴谋到此为止了。"林克握紧光剑,"我不会让你继续操控这一切。"</p>
|
||||
<p>"操控?"黑袍人轻笑,"我只是在帮助他们实现梦想而已。无法地带的人渴望力量,我给了他们力量。这有什么不对?"</p>
|
||||
<p>"你给的只是毁灭。"林克冷声说道,"卡勒特组织会在未来造成无数灾难,天界会因此陷入战乱。而这一切,都是你的阴谋!"</p>
|
||||
<p>"哦?"黑袍人似乎来了兴趣,"你来自未来,你知道会发生什么?"</p>
|
||||
<p>她缓缓走下祭坛,朝着林克走来:"那告诉我,未来...卡勒特成功了吗?"</p>
|
||||
<p>"没有。"林克说道,"他们最终会被击败,而你...也会暴露身份。"</p>
|
||||
<p>"暴露身份?"黑袍人轻笑,"我的身份...你永远不会知道。"</p>
|
||||
<p>她突然挥手,一道黑色的能量朝着林克袭来!</p>
|
||||
<p>"但至少,你今天会死在这里!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>黑袍人的实力比之前更强,她操控着黑色的能量,每一击都带着毁灭性的力量。林克挥舞着细雪之舞,冰属性的剑气与黑色能量碰撞,发出刺耳的嘶鸣声。</p>
|
||||
<p>"里鬼剑术!"</p>
|
||||
<p>剑光闪烁,但黑袍人轻松避开,她的身法诡异而迅捷。</p>
|
||||
<p>"太慢了。"黑袍人冷笑,"在70级的限制下,你根本不是我的对手。"</p>
|
||||
<p>她双手结印,黑色的能量化作无数触手,将林克团团围住。</p>
|
||||
<p>林克咬牙,他知道对方说得没错。在70级的限制下,他的实力大打折扣。</p>
|
||||
<p>但他没有放弃。</p>
|
||||
<p>"流心·跃!"</p>
|
||||
<p>林克的身形高高跃起,躲过了黑色触手的包围。同时,他将剑魂之力注入细雪之舞,光剑爆发出耀眼的冰蓝色光芒!</p>
|
||||
<p>"极寒...猛龙断空斩!"</p>
|
||||
<p>这是他将冰属性与猛龙断空斩结合的新招式!金色的龙形剑气带着极寒的气息,穿透了黑袍人的防御!</p>
|
||||
<p>"什么?!"黑袍人大惊,她没想到林克竟然能创新招式。</p>
|
||||
<p>剑气穿透了她的身体,黑色的长袍被撕裂,露出了一角白皙的肌肤。但黑袍人并没有倒下,她的身体开始散发出更加浓郁的黑色能量。</p>
|
||||
<p>"不错..."黑袍人的声音变得低沉,"你比我想象中更有趣。"</p>
|
||||
<p>她收起攻击,转身走向祭坛:"但这次,我不会和你纠缠。卡勒特的种子已经种下,我的任务完成了。"</p>
|
||||
<p>"站住!"林克想要追击。</p>
|
||||
<p>"下次吧。"黑袍人回头看了他一眼,"下一次,我会亲自送你上路。"</p>
|
||||
<p>她的身体化作黑色的烟雾,消失在空气中。</p>
|
||||
<p>只留下一句话在密室中回荡:"记住,林克...命运虽然难以改变,但你的选择,会让一切变得不同。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>黑袍人离去后,林克摧毁了祭坛,收集了一些时间之痕。</p>
|
||||
<p>但他知道,这只是暂时的胜利。黑袍人的阴谋还在继续,卡勒特组织已经诞生,未来天界的战乱不可避免。</p>
|
||||
<p>"下次..."林克握紧光剑,"下次我一定要揭开你的真面目!"</p>
|
||||
<p>他转身离开工厂,朝着时空之门的方向走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零七章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-108.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-110.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-79.html" class="sidebar-chapter ">第79章:夺回西部线·卡勒特的余孽</a>
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter current">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(109)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,897 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>剑魂转职仪式 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 11</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>暗黑雷鸣废墟的试炼结束后,林克和赛丽亚跟随GSD回到了赫顿玛尔。</p>
|
||||
<p>剑道馆内,GSD站在大厅中央,表情庄严。林克单膝跪在他面前,手中捧着那把刚刚获得的光剑"晨曦"。</p>
|
||||
<p>"林克,你已通过暗黑雷鸣废墟的试炼,证明了你的意志和剑术。"GSD的声音低沉而有力,"今日,我正式授予你剑魂之名。"</p>
|
||||
<p>他伸出手,轻轻点在林克的额头。</p>
|
||||
<p>"剑魂,以剑为魂,追求极致剑术之道。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>GSD转身,从身后的架子上取下五把不同的武器,一一摆在林克面前。</p>
|
||||
<p>"太刀、巨剑、短剑、钝器、光剑——在剑魂手中,万物皆可为剑。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>GSD开始详细讲解每种武器的特性:</p>
|
||||
<p>"太刀,灵活迅捷,适合单挑和快速连击。"</p>
|
||||
<p>"巨剑,力量型武器,破甲能力极强。对付硬甲敌人时,巨剑是最佳选择。"</p>
|
||||
<p>"短剑,带有魔法属性攻击。对付魔法防御低的敌人,短剑能发挥出意想不到的效果。"</p>
|
||||
<p>"钝器,能够产生震荡伤害,有概率眩晕目标。"</p>
|
||||
<p>"光剑,剑魂专属武器,极速连击,附加光属性伤害。它是剑魂的象征,也是你最强大的伙伴。"</p>
|
||||
<p>林克认真记下每一种武器的特性。</p>
|
||||
<p>"真正的剑魂,不会在战斗中局限于一把武器。"GSD强调,"根据敌人的特点,灵活切换最适合的武器,这才是剑魂的精髓。"</p>
|
||||
<p>"你的鬼手给了你强大的力量,但剑魂之道,不在于力量的大小,而在于剑术的境界。"</p>
|
||||
<p>"你要学会驾驭剑,而不是被剑驾驭。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>仪式进行到高潮,GSD将手放在林克的光剑"晨曦"上。</p>
|
||||
<p>"这把剑,从此刻起,正式成为你的伙伴。"</p>
|
||||
<p>"但记住,晨曦的力量远不止于此。"GSD说,"它与天空之城的光之核心有着神秘的联系。如果你想发挥它的真正力量,就必须去天空之城,找到答案。"</p>
|
||||
<p>林克握紧晨曦,感受着剑身上传来的温暖力量。</p>
|
||||
<p>"弟子明白。"</p>
|
||||
<p>"好。"GSD收回手,"从今天起,你就是正式的剑魂了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>仪式结束后,GSD将一套装备交给了林克。</p>
|
||||
<p>"这是剑魂的标准装备——五把武器,涵盖所有类型。"</p>
|
||||
<p>林克接过装备,发现除了原本的霜刃和晨曦,还有三把新武器:</p>
|
||||
<p>• <strong>巨剑"破军"</strong>:沉重但威力巨大,剑身上刻满了战斗的痕迹</p>
|
||||
<p>• <strong>短剑"影牙"</strong>:漆黑如墨,剑刃上缠绕着暗影之力</p>
|
||||
<p>• <strong>钝器"碎骨"</strong>:巨大的铁锤,一锤下去连钢铁都能砸碎</p>
|
||||
<p>"这五把武器,将是你在天空之城的依仗。"GSD说,"好好使用它们。"</p>
|
||||
<p>"谢谢师父!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>转职仪式结束后的两天,林克在剑道馆内刻苦修炼。</p>
|
||||
<p>GSD亲自指导他如何在战斗中快速切换武器,如何根据敌人的特点选择最优解。</p>
|
||||
<p>"差不多了。"GSD点点头,"接下来,你该去天空之城了。"</p>
|
||||
<p>"但在那之前,先去一趟西海岸。"</p>
|
||||
<p>"西海岸?"</p>
|
||||
<p>"那里有位魔道学者,名叫莎兰。"GSD说,"她对天空之城了解很深,会告诉你一些我不知道的事情。"</p>
|
||||
<p>"而且……"GSD顿了顿,"她可能会告诉你关于晨曦的秘密。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-10.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-12.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter ">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter ">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter ">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter ">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter ">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter ">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter ">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter ">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter ">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter ">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter current">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter ">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter ">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter ">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter ">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter ">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter ">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter ">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter ">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter ">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter ">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter ">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter ">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter ">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter ">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter ">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter ">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter ">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter ">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter ">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter ">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter ">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter ">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter ">第34章:暗精灵墓地·剩余三将军</a>
|
||||
<a href="chapter-35.html" class="sidebar-chapter ">第35章:邪龙斯皮兹</a>
|
||||
<a href="chapter-36.html" class="sidebar-chapter ">第36章:莎兰的探望</a>
|
||||
<a href="chapter-37.html" class="sidebar-chapter ">第37章:暗影迷宫·影子剑士</a>
|
||||
<a href="chapter-38.html" class="sidebar-chapter ">第38章:熔岩穴·泰坦之怒</a>
|
||||
<a href="chapter-39.html" class="sidebar-chapter ">第39章:暗黑城入口·无头骑士</a>
|
||||
<a href="chapter-40.html" class="sidebar-chapter ">第40章:万年雪山·冰心少年</a>
|
||||
<a href="chapter-41.html" class="sidebar-chapter ">第41章:敏泰的加入</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(11)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,926 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>无法地带 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 110</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克感到一股燥热的气息扑面而来。</p>
|
||||
<p>他睁开眼睛,发现自己站在一片更加荒凉的沙漠中。这里的温度比卡勒特之初更高,空气中弥漫着硝烟和血腥的味道。远处,枪声和爆炸声此起彼伏,仿佛永不停歇的战争。</p>
|
||||
<p>"这就是...无法地带的核心?"</p>
|
||||
<p>林克环顾四周,这里的混乱程度远超卡勒特之初。到处都是战斗的痕迹——废弃的战车、破碎的武器、还有...尸体。这里没有法律,没有秩序,只有无尽的杀戮和掠夺。</p>
|
||||
<p>他握紧细雪之舞,朝着枪声传来的方向走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一片废弃的矿区中,两伙武装分子正在激战。</p>
|
||||
<p>一方是卡勒特的成员,他们穿着统一的军装,手持先进的武器,训练有素。另一方则是无法地带的本地势力,他们装备简陋,但人数众多,战斗风格凶狠而疯狂。</p>
|
||||
<p>"为了卡勒特!"</p>
|
||||
<p>"为了自由!"</p>
|
||||
<p>双方的喊杀声交织在一起,子弹如雨点般穿梭,不断有人倒下。</p>
|
||||
<p>林克躲在暗处观察,他发现卡勒特的武器比上次更加先进——自动步枪、手雷、甚至还有小型火炮。这些武器绝对不是无法地带能制造的,一定是黑袍人提供的。</p>
|
||||
<p>"黑袍人...你究竟想做什么?"林克低声自语。</p>
|
||||
<p>就在这时,一道黑色的身影出现在战场边缘。那熟悉的黑袍,那诡异的面具,正是林克一直在追寻的人。</p>
|
||||
<p>"终于找到你了!"林克身形一闪,朝着黑袍人冲去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"又是你。"黑袍人似乎早就发现了林克,她转过身,发出阴冷的笑声,"你真是阴魂不散啊。"</p>
|
||||
<p>"你的阴谋该结束了!"林克拔出光剑,"我不会让你继续操控这一切!"</p>
|
||||
<p>"操控?"黑袍人轻笑,"我只是在加速历史的进程而已。无法地带的混乱、卡勒特的崛起、天界的战乱...这些都是命中注定的。"</p>
|
||||
<p>她张开双臂,黑色的能量在她周身涌动:"我只是在扮演我的角色而已。"</p>
|
||||
<p>"你的角色?"林克皱眉,"你到底是什么人?为什么要为赫尔德卖命?"</p>
|
||||
<p>黑袍人的身体微微一僵,然后冷冷地说道:"我的身份...你永远不会知道。"</p>
|
||||
<p>她突然挥手,一道黑色的能量朝着林克袭来!</p>
|
||||
<p>"但至少,你今天会死在这里!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>黑袍人的实力比之前更强,她操控着黑色的能量,每一击都带着毁灭性的力量。林克挥舞着细雪之舞,冰属性的剑气与黑色能量碰撞,发出刺耳的嘶鸣声。</p>
|
||||
<p>"里鬼剑术!"</p>
|
||||
<p>剑光闪烁,但黑袍人轻松避开,她的身法诡异而迅捷,仿佛在预判林克的每一个动作。</p>
|
||||
<p>"太慢了。"黑袍人冷笑,"在70级的限制下,你根本不是我的对手。"</p>
|
||||
<p>她双手结印,黑色的能量化作无数触手,将林克团团围住。</p>
|
||||
<p>林克咬牙,他知道对方说得没错。在70级的限制下,他的实力大打折扣。但他没有放弃,他想起了在卡勒特之初领悟的新招式。</p>
|
||||
<p>"极寒...猛龙断空斩!"</p>
|
||||
<p>金色的龙形剑气带着极寒的气息,穿透了黑色触手的包围!黑袍人似乎没有料到这一招,被剑气擦中了肩膀,黑色的长袍被撕裂了一角。</p>
|
||||
<p>"什么?!"黑袍人大惊。</p>
|
||||
<p>林克抓住机会,身形如同闪电般冲向黑袍人,光剑直刺她的胸口!</p>
|
||||
<p>"该死!"黑袍人连忙闪避,但还是被剑气划破了面具,露出了一角白皙的肌肤。</p>
|
||||
<p>那是一角绝美的面容,但林克来不及细看,黑袍人已经后退数丈,面具重新合拢。</p>
|
||||
<p>"你...你竟然能伤到我?"黑袍人的声音中带着一丝震惊,"看来,我小看你了。"</p>
|
||||
<p>她收起攻击,转身离去:"但这次,我不会和你纠缠。我们的对决...留到下一次。"</p>
|
||||
<p>"站住!"林克想要追击。</p>
|
||||
<p>"下次吧。"黑袍人回头看了他一眼,那眼神中似乎带着一丝复杂的情绪,"下一次,我会让你看到我的真面目。"</p>
|
||||
<p>她的身体化作黑色的烟雾,消失在空气中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>黑袍人离去后,林克收集了战场上的时间之痕。</p>
|
||||
<p>但他心中充满了疑问。刚才那一瞬间,他看到了黑袍人面具下的面容一角——那是一张美丽而苍白的脸,眼中似乎带着...悲伤?</p>
|
||||
<p>"她...到底是什么人?"林克喃喃自语。</p>
|
||||
<p>为什么她要为赫尔德卖命?为什么她的眼中会有悲伤?她说的"命中注定"又是什么意思?</p>
|
||||
<p>太多的疑问,太多的谜团。</p>
|
||||
<p>林克知道,只有继续追查下去,才能揭开这一切的真相。</p>
|
||||
<p>"下一次..."林克握紧光剑,"下一次,我一定要揭开你的面具!"</p>
|
||||
<p>他转身走向时空之门的方向,准备前往下一个时间点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百零八章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-109.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-111.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-80.html" class="sidebar-chapter ">第80章:雾都赫伊斯·无法地带的阴影</a>
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter current">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(110)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,924 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>暗黑圣战 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 111</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克感到一股阴冷而神圣的气息扑面而来。</p>
|
||||
<p>他睁开眼睛,发现自己站在一座宏伟的教堂前。这座教堂通体漆黑,散发着诡异而庄严的气息。教堂周围,无数的圣职者正在与恶魔激战,喊杀声和祈祷声交织在一起。</p>
|
||||
<p>"这就是...暗黑圣战?"</p>
|
||||
<p>林克握紧细雪之舞,冰属性的光剑在这种环境下显得格外清冷。</p>
|
||||
<p>根据西岚的说法,暗黑圣战是阿拉德历史上最惨烈的战争之一。黑色圣殿——一个崇拜混沌之神的邪教组织——发动了大规模的入侵,圣职者们为了守护大陆,展开了殊死搏斗。</p>
|
||||
<p>而林克的任务,就是调查这场战争背后的真相。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>教堂内部,到处都是战斗的痕迹。墙壁上布满了圣光和黑暗魔法碰撞的痕迹,地面上散落着破碎的武器和铠甲。</p>
|
||||
<p>林克小心翼翼地前进,沿途遭遇了各种恶魔——被黑暗侵蚀的信徒、召唤出来的恶魔生物、还有...被控制的圣职者。</p>
|
||||
<p>"流心·刺!"</p>
|
||||
<p>林克的光剑精准地刺穿一只恶魔的心脏,冰属性的剑气瞬间冻结了它的身体。但更多的恶魔从四面八方涌来。</p>
|
||||
<p>"里鬼剑术!"</p>
|
||||
<p>剑光闪烁,恶魔纷纷倒下。林克一路杀到教堂深处,终于发现了异常——</p>
|
||||
<p>一个身穿黑色长袍、戴着面具的身影正站在祭坛前,手中高举着一颗黑色的水晶。</p>
|
||||
<p>"黑袍人..."林克冷声说道,"果然是你。"</p>
|
||||
<p>黑袍人转过身,面具下的眼睛看向林克,发出阴冷的笑声:"哦?又是你?看来你真的很喜欢追着我跑。"</p>
|
||||
<p>"你的阴谋该结束了!"林克握紧光剑,"这次我不会让你逃走!"</p>
|
||||
<p>"阴谋?"黑袍人轻笑,"我只是在帮助这些迷失的灵魂找到归宿而已。"</p>
|
||||
<p>她指向祭坛周围——那里跪着数十名被控制的圣职者,他们的眼中都闪烁着黑色的光芒。</p>
|
||||
<p>"看到了吗?这些都是被世界抛弃的人。我给了他们力量,让他们能够复仇。"</p>
|
||||
<p>"你给了他们黑暗!"林克冷声说道,"让他们变成了恶魔的傀儡!"</p>
|
||||
<p>"那又怎样?"黑袍人张开双臂,"力量就是力量,不分光明与黑暗。"</p>
|
||||
<p>她突然挥手,黑色的能量化作无数触手,朝着林克席卷而来!</p>
|
||||
<p>"来吧,让我看看你的成长!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>黑袍人的实力比之前更强,她操控着黑色的能量,每一击都带着毁灭性的力量。林克挥舞着细雪之舞,冰属性的剑气与黑色能量碰撞,发出刺耳的嘶鸣声。</p>
|
||||
<p>"极寒...猛龙断空斩!"</p>
|
||||
<p>金色的龙形剑气带着极寒的气息,穿透了黑袍人的防御!但黑袍人似乎早有准备,她的身体化作黑色烟雾,避开了这一击。</p>
|
||||
<p>"同样的招式,对我没用。"黑袍人冷笑。</p>
|
||||
<p>"那试试这个!"林克突然改变剑势,"流心·跃!"</p>
|
||||
<p>他的身形高高跃起,从上方直刺黑袍人!</p>
|
||||
<p>"什么?!"黑袍人大惊,连忙闪避,但还是被剑气划破了长袍。</p>
|
||||
<p>"你...!"黑袍人后退数丈,眼中闪过一丝震惊。</p>
|
||||
<p>"你的面具下..."林克盯着她,"究竟藏着什么?"</p>
|
||||
<p>"你不会知道的!"黑袍人转身离去,"这次算你们赢了,但暗黑圣战的结局...已经注定了!"</p>
|
||||
<p>她的身体化作黑色烟雾,消失在空气中。</p>
|
||||
<p>"该死!"林克想要追击,但那些被她控制的圣职者突然暴起,朝着他冲来!</p>
|
||||
<p>"必须先救他们!"</p>
|
||||
<p>林克挥剑斩断控制他们的黑暗能量,圣职者们逐渐恢复了清醒。</p>
|
||||
<p>"谢谢...你..."一名圣职者虚弱地说,"那个黑袍人...她在收集圣职者的灵魂...为了某种邪恶的仪式..."</p>
|
||||
<p>"什么仪式?"</p>
|
||||
<p>"我们...不知道...但她提到了...『创新世纪』..."</p>
|
||||
<p>林克心中一凛。又是『创新世纪』!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>暗黑圣战的危机暂时解除,但林克心中充满了疑问。</p>
|
||||
<p>黑袍人到底在收集什么?她的真正目的是什么?</p>
|
||||
<p>"创新世纪..."林克握紧拳头,"我一定要查清楚!"</p>
|
||||
<p>他走向教堂深处,那里有一道金色的光芒正在等待着他。</p>
|
||||
<p>时空之门,即将带他前往下一个时间点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-110.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-112.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-81.html" class="sidebar-chapter ">第81章:阿登高地·GT-9600</a>
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter current">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(111)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,923 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>昔日悲鸣 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 112</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克感到一股阴冷的气息扑面而来。</p>
|
||||
<p>他睁开眼睛,发现自己站在一个黑暗的洞穴入口。洞穴深处传来凄厉的哀嚎声,仿佛有无数冤魂在哭泣。</p>
|
||||
<p>"这就是...悲鸣洞穴?"</p>
|
||||
<p>林克握紧细雪之舞,冰属性的光剑在黑暗中散发着微弱的蓝光。</p>
|
||||
<p>根据西岚的说法,悲鸣洞穴是阿拉德大陆上最危险的地下城之一。多年前,四剑圣曾在这里与使徒希洛克战斗,最终将其封印。但那场战斗也造成了无数伤亡,洞穴中充满了死者的怨念。</p>
|
||||
<p>而更关键的是,这里隐藏着赫尔德阴谋的重要线索。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>洞穴内部,到处都是战斗的痕迹。墙壁上布满了剑痕和血迹,地面上散落着破碎的武器和铠甲。</p>
|
||||
<p>"这里发生过惨烈的战斗..."林克皱眉。</p>
|
||||
<p>他小心翼翼地前进,突然听到前方传来打斗声。</p>
|
||||
<p>"阿甘左!小心左边!"一个女性的声音响起。</p>
|
||||
<p>"卢克西,你退后!这里交给我!"一个低沉的男声回应。</p>
|
||||
<p>林克加快脚步,转过一个拐角,看到了让他震惊的一幕——</p>
|
||||
<p>四剑圣正在与使徒希洛克激战!</p>
|
||||
<p>阿甘左手持巨剑,每一击都带着开山裂石的力量;西岚的太刀如同幻影,在希洛克周围穿梭;布万加的钝器每一次挥舞都引发地震;而凯恩...凯恩已经倒在了血泊中。</p>
|
||||
<p>但最让林克注意的是那个红发的女鬼剑士——卢克西。她浑身散发着狂暴的气息,正在与希洛克殊死搏斗。</p>
|
||||
<p>"卢克西,不要!"阿甘左大喊,"你会被卡赞吞噬的!"</p>
|
||||
<p>"没关系..."卢克西回头看了阿甘左一眼,眼中满是深情,"只要能保护你...我什么都愿意..."</p>
|
||||
<p>她的身体开始膨胀,卡赞的诅咒彻底爆发!</p>
|
||||
<p>"不——!"阿甘左发出撕心裂肺的喊声。</p>
|
||||
<p>但已经来不及了。卢克西化作一道红色的光芒,与希洛克同归于尽!</p>
|
||||
<p>轰——!!!</p>
|
||||
<p>巨大的爆炸席卷整个洞穴,林克被冲击波震飞,重重地撞在墙壁上。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克醒来时,战斗已经结束。</p>
|
||||
<p>希洛克被封印,但卢克西也牺牲了。阿甘左跪在地上,抱着卢克西渐渐冰冷的身体,眼中满是绝望。</p>
|
||||
<p>"为什么...为什么要离开我..."阿甘左的声音沙哑,"我们说好了...要一起活下去的..."</p>
|
||||
<p>林克静静地看着这一幕,心中充满了悲伤。</p>
|
||||
<p>这就是悲鸣洞穴的真相——四剑圣的荣耀背后,是卢克西的牺牲,是阿甘左永远的痛苦。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,林克感觉到了一股异样的气息。</p>
|
||||
<p>他转头看去,只见一个身穿黑色长袍、戴着面具的身影正站在阴影中,静静地观察着这一切。</p>
|
||||
<p>"黑袍人..."林克冷声说道。</p>
|
||||
<p>黑袍人转过身,面具下的眼睛看向林克,发出阴冷的笑声:"哦?又是你?看来你真的很喜欢追着我跑。"</p>
|
||||
<p>"你在这里做什么?"林克握紧光剑,"这一切...都是你的阴谋?"</p>
|
||||
<p>"阴谋?"黑袍人轻笑,"我只是在...观察而已。观察使徒的死亡,观察人类的绝望,观察...命运的轨迹。"</p>
|
||||
<p>她指向阿甘左和卢克西:"看到了吗?这就是命运。即使知道结局,也无法改变。"</p>
|
||||
<p>"你错了!"林克冷声说道,"命运是可以改变的!"</p>
|
||||
<p>"是吗?"黑袍人微笑,"那就让我看看...你能改变什么。"</p>
|
||||
<p>她突然挥手,一道黑色的能量朝着林克袭来!</p>
|
||||
<p>"来吧,让我看看你的成长!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>但这一次,黑袍人没有恋战。她只是试探了几招,然后就化作黑色烟雾消失了。</p>
|
||||
<p>"下次吧..."她的声音在空气中回荡,"下一次,在凛冬...我会让你看到一切的真相。"</p>
|
||||
<p>林克想要追击,但时空之门的时限已经到来。</p>
|
||||
<p>他最后看了一眼悲鸣洞穴,看了一眼还在哭泣的阿甘左,心中暗暗发誓——</p>
|
||||
<p>"我一定会改变这一切。"</p>
|
||||
<p>他踏入金色的光芒,前往下一个时间点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-111.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-113.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-82.html" class="sidebar-chapter ">第82章:卡勒特指挥部·兰蒂卢斯</a>
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter current">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(112)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,938 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>凛冬 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 113</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克感到一股刺骨的寒意。</p>
|
||||
<p>他睁开眼睛,发现自己站在一片冰雪覆盖的土地上。远处,高耸的城堡在风雪中若隐若现,天空中飞舞着巨大的龙影。</p>
|
||||
<p>"这就是...500年前的天界?"</p>
|
||||
<p>林克环顾四周,这里与他见过的天界完全不同。没有先进的科技,没有繁华的都市,只有原始的冰雪和...龙族的气息。</p>
|
||||
<p>"巴卡尔的时代..."林克握紧细雪之舞,"我来到了暴龙王统治天界的时期。"</p>
|
||||
<p>根据西岚的说法,这是时空之门中最危险的时间点之一。暴龙王巴卡尔,第九使徒,曾经统治天界数百年,禁止魔法,发展科技,最终被天界人联合反抗军击败。</p>
|
||||
<p>而林克的任务,就是从这里找到赫尔德阴谋的真相。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>冰雪中,林克朝着城堡的方向前进。</p>
|
||||
<p>沿途,他遭遇了各种龙族生物——龙人、幼龙、还有...被巴卡尔统治的人类。</p>
|
||||
<p>"站住!"一队龙人守卫拦住了他,"你是什么人?竟敢擅闯巴卡尔大人的领地!"</p>
|
||||
<p>"路过的冒险家。"林克说道,"我想见巴卡尔。"</p>
|
||||
<p>"见巴卡尔大人?"龙人守卫嗤笑,"你以为你是谁?巴卡尔大人是天空的霸主,岂是你这种凡人能见的?"</p>
|
||||
<p>"那就让我打进去。"林克拔出光剑。</p>
|
||||
<p>"狂妄!"龙人守卫怒吼,"兄弟们,上!"</p>
|
||||
<p>数十只龙人朝着林克冲来,但林克的剑气所向披靡,任何敌人都无法阻挡他的脚步!</p>
|
||||
<p>"里鬼剑术!"</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>剑光闪烁,龙人纷纷倒下。林克一路杀到城堡门前,终于引起了城堡内的注意。</p>
|
||||
<p>"有趣..."一个低沉的声音从城堡中传来,"竟然有人类能闯到这里。"</p>
|
||||
<p>轰——!!!</p>
|
||||
<p>城堡的大门缓缓打开,一个巨大的身影走了出来。</p>
|
||||
<p>那是一条巨龙,身高数十米,浑身覆盖着金色的鳞片。他的双眼如同燃烧的火焰,散发着威严和霸气。</p>
|
||||
<p>"暴龙王...巴卡尔..."林克握紧光剑。</p>
|
||||
<p>巴卡尔俯视着林克,眼中闪过一丝兴趣:"人类,你的剑术不错。是谁派你来的?"</p>
|
||||
<p>"没有人派我来。"林克说道,"我来自未来,来寻找真相。"</p>
|
||||
<p>"未来?"巴卡尔愣了一下,然后狂笑起来,"有趣!竟然有人类能穿越时空!"</p>
|
||||
<p>他收起威压,俯视着林克:"说吧,你想知道什么真相?"</p>
|
||||
<p>"赫尔德的阴谋。"林克说道,"她操控了一切,使徒的转移、天界的混乱、还有...你的命运。"</p>
|
||||
<p>巴卡尔的身体微微一震,眼中的火焰跳动了一下:"赫尔德...那个该死的女人..."</p>
|
||||
<p>他沉默片刻,然后说道:"进来吧,人类。既然你来自未来,也许...你能改变什么。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>城堡内部,巴卡尔坐在巨大的王座上,林克站在他面前。</p>
|
||||
<p>"赫尔德..."巴卡尔的声音低沉,"她是第二使徒,也是最狡猾的使徒。她操控着一切,包括我的命运。"</p>
|
||||
<p>"你知道她的计划?"林克问道。</p>
|
||||
<p>"当然知道。"巴卡尔冷笑,"她想要收集使徒死亡时释放的能量,重建泰拉。而我...就是她选中的牺牲品之一。"</p>
|
||||
<p>他看向林克:"我知道我会死,被天界人击败。但我不后悔,因为我禁止魔法,让天界人发展科技,这样他们未来才能对抗赫尔德。"</p>
|
||||
<p>"你...早就知道?"林克震惊。</p>
|
||||
<p>"当然。"巴卡尔微笑,"我是暴龙王,不是傻子。赫尔德以为她在操控我,其实...我也在利用她。"</p>
|
||||
<p>他站起身,走到林克面前:"人类,你来自未来,告诉我...天界人最终战胜赫尔德了吗?"</p>
|
||||
<p>林克沉默片刻:"还没有,但我们正在努力。"</p>
|
||||
<p>"努力..."巴卡尔笑了,"那就够了。"</p>
|
||||
<p>他突然伸出手,一道金色的光芒注入林克体内:"这是我最后的礼物——龙之力。它能让你在面对赫尔德时,多一份胜算。"</p>
|
||||
<p>"巴卡尔..."</p>
|
||||
<p>"去吧,人类。"巴卡尔转身走向王座,"我的时代即将结束,但你的时代...才刚刚开始。"</p>
|
||||
<p>他坐下,闭上了眼睛:"记住,不要被命运束缚。即使知道结局,也要勇敢地去改变。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克离开城堡,心中充满了复杂的情绪。</p>
|
||||
<p>巴卡尔...不是暴君,而是一个为了天界未来而牺牲自己的英雄。他明知会死,却依然选择了这条路。</p>
|
||||
<p>"赫尔德..."林克握紧拳头,"我一定会阻止你。"</p>
|
||||
<p>就在这时,一道黑色的身影出现在风雪中。</p>
|
||||
<p>"终于见面了,林克。"黑袍人的声音从面具下传来,"你比我想象中更出色。"</p>
|
||||
<p>"又是你。"林克握紧光剑,"这次我不会让你逃走!"</p>
|
||||
<p>"呵呵..."黑袍人轻笑,"在凛冬,我不会和你战斗。这里...只是给你一个警告。"</p>
|
||||
<p>"什么警告?"</p>
|
||||
<p>"下一个时间点,迷之觉悟..."黑袍人的声音变得冰冷,"一切的真相,都将在那里揭晓。"</p>
|
||||
<p>她的身体化作黑色烟雾,消失在风雪中。</p>
|
||||
<p>只留下一句话在空气中回荡:"准备好面对真相吧,林克...那可能会让你崩溃。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克站在风雪中,心中充满了疑问。</p>
|
||||
<p>黑袍人到底是谁?她说的真相又是什么?</p>
|
||||
<p>"迷之觉悟..."林克握紧拳头,"不管真相是什么,我都会面对!"</p>
|
||||
<p>他走向时空之门,准备前往最后一个时间点。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-112.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-114.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-83.html" class="sidebar-chapter ">第83章:皇女的告白·天界的新篇章</a>
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter current">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(113)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,929 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>迷之觉悟 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 114</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>金色的光芒散去,林克回到了现代。</p>
|
||||
<p>他睁开眼睛,发现自己站在虚祖的时空之门前。西岚正站在那里,神情凝重。</p>
|
||||
<p>"你终于回来了。"西岚说道,"我等你很久了。"</p>
|
||||
<p>"西岚,我有重要的事情要告诉你。"林克说道,"关于黑袍人的身份..."</p>
|
||||
<p>"我知道。"西岚打断他,"我已经调查清楚了。"</p>
|
||||
<p>他拿出一张羊皮纸,上面写满了古老的文字:"这是我在艾丽丝的住处找到的。她...就是黑袍人。"</p>
|
||||
<p>林克心中一震。虽然他已经猜到了,但听到西岚确认,还是感到震惊。</p>
|
||||
<p>"艾丽丝...是赫尔德的人偶。"西岚的声音低沉,"她被赫尔德制造出来,用来操控阿拉德大陆的命运。格兰之火、瘟疫之源、卡勒特之乱...都是她在背后操控。"</p>
|
||||
<p>"为什么?"林克问道,"她为什么要这么做?"</p>
|
||||
<p>"因为她被控制了。"西岚说道,"赫尔德用某种方法控制了她,让她成为自己的傀儡。"</p>
|
||||
<p>他看向林克:"我们必须阻止她。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝的住处位于虚祖的边缘,一间看似普通的占卜师小屋。</p>
|
||||
<p>但当林克和西岚推开门时,眼前的景象让他们震惊——</p>
|
||||
<p>小屋内部是一个巨大的空间,到处都是魔界的物品。墙上挂满了预言的羊皮纸,地上画着复杂的魔法阵,空气中弥漫着浓郁的魔界气息。</p>
|
||||
<p>"欢迎回来,林克。"一个熟悉的声音响起。</p>
|
||||
<p>艾丽丝从阴影中走出,但此刻的她与平时完全不同。她的眼中没有温柔,只有冰冷和疯狂。</p>
|
||||
<p>"艾丽丝..."林克握紧光剑,"真的是你..."</p>
|
||||
<p>"没错,就是我。"艾丽丝微笑,"赫尔德的使者,时空之门的引导者...也是你的敌人。"</p>
|
||||
<p>"为什么?"林克问道,"你为什么要做这些?"</p>
|
||||
<p>"为什么?"艾丽丝轻笑,"因为我被制造出来就是为了这个目的。我是赫尔德的人偶,我的存在就是为了执行她的意志。"</p>
|
||||
<p>她举起法杖,紫色的光芒在周身涌动:"但是...与你相处的这段时间,我发现了一些有趣的事情。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"你...让我产生了不该有的感情。"艾丽丝的眼中闪过一丝挣扎,"我明明是个人偶,却对你..."</p>
|
||||
<p>她突然摇头,眼中的挣扎消失,取而代之的是冰冷:"但这都不重要了。今天,你们都要死在这里。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发!</p>
|
||||
<p>艾丽丝的实力远超想象,她操控着元素之力,火焰、冰霜、雷电交织成毁灭性的攻击!</p>
|
||||
<p>"极·鬼剑术!"</p>
|
||||
<p>林克挥剑格挡,但艾丽丝的魔法太过强大,他被震得连连后退。</p>
|
||||
<p>"没用的!"艾丽丝狂笑,"在迷之觉悟,你们没有任何胜算!"</p>
|
||||
<p>西岚也加入了战斗,他的太刀如同幻影,在艾丽丝周围穿梭。但艾丽丝仿佛能预知他们的动作,每一次攻击都被她轻松避开。</p>
|
||||
<p>"我的占卜术可以预知未来。"艾丽丝说道,"你们的每一个动作,我都看得一清二楚。"</p>
|
||||
<p>"那又怎样?"林克咬牙,"即使知道未来,我也要改变它!"</p>
|
||||
<p>他突然收起光剑,朝着艾丽丝冲去!</p>
|
||||
<p>"什么?!"艾丽丝大惊,连忙施展魔法防御。</p>
|
||||
<p>但林克没有攻击,而是...抱住了她!</p>
|
||||
<p>"艾丽丝,醒醒!"林克大声说道,"你不是人偶,你是有感情的人!我知道你能感受到,你对我的感情是真实的!"</p>
|
||||
<p>"不...不要..."艾丽丝的身体颤抖,"放开我..."</p>
|
||||
<p>"我不会放开你!"林克紧紧抱住她,"不管你是什么身份,我都不会放弃你!"</p>
|
||||
<p>艾丽丝的眼中流下了泪水:"为什么...为什么要对我这么好...我明明...伤害了你那么多次..."</p>
|
||||
<p>"因为我喜欢你。"林克认真地说,"从第一次见到你,我就被你的温柔和神秘吸引了。艾丽丝...回到我身边吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝的身体开始崩溃,黑色的能量从她体内涌出。</p>
|
||||
<p>"不...赫尔德的控制...在消失..."她虚弱地说,"林克...谢谢你..."</p>
|
||||
<p>她的身体软倒在林克怀里,失去了意识。</p>
|
||||
<p>西岚走过来,看着这一幕,叹了口气:"你做到了...你拯救了她。"</p>
|
||||
<p>"但她需要休息。"林克抱起艾丽丝,"我会照顾她,直到她完全恢复。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>时空之门的冒险结束了,但林克知道,真正的战斗才刚刚开始。</p>
|
||||
<p>赫尔德的阴谋还没有停止,更多的使徒将面临危险。但无论如何,他都会继续前进。</p>
|
||||
<p>因为他不是一个人在战斗。</p>
|
||||
<p>赛丽亚、奥菲利亚、敏泰、莎兰、帕丽丝、泽丁、马琳、皇女艾丽婕、贝奇、艾泽拉...还有艾丽丝。</p>
|
||||
<p>她们都在等着他。</p>
|
||||
<p>"走吧。"林克看向前方,"下一个冒险,在等着我们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十四章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-113.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-115.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-84.html" class="sidebar-chapter ">第84章:幽灵列车·亡者的低语</a>
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter current">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(114)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,938 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·艾丽丝的抉择 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 115</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>迷之觉悟的战斗结束后,艾丽丝陷入了昏迷。</p>
|
||||
<p>林克将她带回虚祖的住所,日夜守护。三天后,她终于醒来。</p>
|
||||
<p>"这是...哪里?"艾丽丝睁开眼睛,看到陌生的天花板。</p>
|
||||
<p>"我的房间。"林克坐在床边,握住她的手,"你昏迷了三天。"</p>
|
||||
<p>艾丽丝看着林克,眼中闪过复杂的神色。记忆如潮水般涌来——她想起了自己的身份,想起了自己做过的一切,想起了...她是如何伤害这个男人的。</p>
|
||||
<p>"对不起..."艾丽丝的眼泪夺眶而出,"我...我伤害了你那么多次...我还差点杀了你..."</p>
|
||||
<p>"那不是你的错。"林克温柔地说,"你是被赫尔德控制的。"</p>
|
||||
<p>"但那确实是我做的..."艾丽丝痛苦地闭上眼睛,"格兰之火、瘟疫之源、卡勒特之乱...那么多人因我而死...我...我不配活在这个世界上..."</p>
|
||||
<p>"艾丽丝..."</p>
|
||||
<p>"让我赎罪。"艾丽丝突然说道,"我要离开这里,去弥补我犯下的过错。"</p>
|
||||
<p>林克心中一紧:"你要去哪里?"</p>
|
||||
<p>"我不知道。"艾丽丝摇头,"但我要去做一些好事,帮助那些被我伤害过的人...直到我赎清罪孽。"</p>
|
||||
<p>"那要多久?"</p>
|
||||
<p>"我不知道...也许几年,也许几十年..."艾丽丝看着林克,眼中满是不舍,"但我会回来的...等我赎清罪孽,我一定会回来找你。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>他知道艾丽丝需要这个,她需要为自己的过错赎罪,才能重新面对这个世界。但他...舍不得她。</p>
|
||||
<p>"能不能...不要走?"林克轻声说道,"我可以陪你一起赎罪..."</p>
|
||||
<p>"不。"艾丽丝摇头,"这是我的罪,必须由我自己来赎。"</p>
|
||||
<p>她坐起身,看着林克:"但在离开之前...我想把自己完全交给你。"</p>
|
||||
<p>"艾丽丝..."</p>
|
||||
<p>"我知道我不配..."艾丽丝的眼中流下泪水,"但我想...在离开之前,成为你的女人。这样...我就有活下去的动力了。"</p>
|
||||
<p>林克看着她,心中涌起一股柔情。</p>
|
||||
<p>"好。"他轻声说道,"我会等你...不管多久。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当晚,月光洒在房间里。</p>
|
||||
<p>艾丽丝躺在林克的怀里,脸上带着羞涩的红晕。她已经褪去了所有的伪装,此刻只是一个普通的女子,一个渴望爱情的女子。</p>
|
||||
<p>"我...我不太懂这些..."艾丽丝羞涩地说,"魔界...没有教过我这些..."</p>
|
||||
<p>"没关系。"林克温柔地说,"让我来教你。"</p>
|
||||
<p>他缓缓进入她的身体。</p>
|
||||
<p>"啊——!"艾丽丝痛呼一声,眼泪流了出来,"痛...好痛..."</p>
|
||||
<p>"忍一忍。"林克停下动作,温柔地吻着她,"第一次都会痛的...等一会儿就好了。"</p>
|
||||
<p>他耐心地等待着,一只手轻抚着她的头发,另一只手与她十指相扣。艾丽丝的呼吸渐渐平稳,身体的紧绷也慢慢放松。</p>
|
||||
<p>"好...好多了..."她轻声说,"可以...动了..."</p>
|
||||
<p>林克开始缓慢地动作,每一次都小心翼翼。艾丽丝起初只是咬着嘴唇忍耐,但渐渐地,一种奇妙的感觉从身体深处涌起。</p>
|
||||
<p>"嗯...啊..."她开始发出细碎的呻吟,"好奇怪...不痛了...好舒服..."</p>
|
||||
<p>"舒服吗?"林克轻笑。</p>
|
||||
<p>"嗯..."艾丽丝点头,"给我...更多..."</p>
|
||||
<p>林克加快了速度,动作也越来越深。艾丽丝的呻吟声越来越大,身体不受控制地扭动着。</p>
|
||||
<p>"林克...林克..."她不停地呼唤着他的名字,"我爱你...我爱你..."</p>
|
||||
<p>"我也爱你。"林克温柔地回应。</p>
|
||||
<p>烛光摇曳,映照着两个纠缠的身影。</p>
|
||||
<p>"要...要去了..."艾丽丝突然抓紧了林克,"林克...我...我..."</p>
|
||||
<p>"一起..."林克低吼一声。</p>
|
||||
<p>"啊——!!!"</p>
|
||||
<p>艾丽丝发出一声高亢的尖叫,身体剧烈地颤抖着,达到了顶峰。林克也在同一时间释放,两人的身体紧紧贴在一起。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>不知过了多久,一切归于平静。</p>
|
||||
<p>艾丽斯躺在林克的怀里,脸上带着满足的红晕。她的紫发散落在枕头上,像是一朵盛开的花。</p>
|
||||
<p>"开心吗?"林克问道。</p>
|
||||
<p>"嗯。"艾丽丝点点头,"我终于...真正成为你的女人了。"</p>
|
||||
<p>她抬起头,认真地看着林克:"林克...我发誓,从今以后,我的身体...我的心...都是你的。"</p>
|
||||
<p>"艾丽丝..."林克感动地吻住她。</p>
|
||||
<p>"等我赎清罪孽..."艾丽丝轻声说道,"我一定会回来...回到你身边。"</p>
|
||||
<p>"我等你。"林克紧紧抱住她,"不管多久,我都会等你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,艾丽丝悄然离去。</p>
|
||||
<p>只留下一封信和一根紫色的发丝。</p>
|
||||
<p>"林克:</p>
|
||||
<p>我走了。不要找我,等我赎清罪孽,自然会回来。</p>
|
||||
<p>谢谢你...愿意接受这样的我。</p>
|
||||
<p>爱你的,</p>
|
||||
<p>艾丽丝"</p>
|
||||
<p>林克握着那根发丝,望向远方。</p>
|
||||
<p>"我等你...艾丽丝..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外一百一十五章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-114.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-116.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-85.html" class="sidebar-chapter ">第85章:伊顿工业区·克雷发电站</a>
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter current">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(115)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,995 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·后宫的日常 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 116</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>清晨的阳光透过窗帘洒进房间,林克迷迷糊糊地睁开眼睛。</p>
|
||||
<p>还没等他完全清醒,一个柔软的身躯就钻进了他的被窝。</p>
|
||||
<p>"林克哥哥,起床啦!"敏泰的声音在耳边响起,带着少女特有的活力。</p>
|
||||
<p>"嗯...几点了?"林克揉了揉眼睛。</p>
|
||||
<p>"太阳都晒屁股了!大家都等着你吃早餐呢!"</p>
|
||||
<p>林克这才注意到,房间里不止敏泰一个人——赛丽亚、帕丽丝、莎兰、奥菲利亚都在门口探头探脑,脸上带着促狭的笑容。</p>
|
||||
<p>"你们..."</p>
|
||||
<p>"今天是后宫大聚会嘛!"帕丽丝大大咧咧地说,"大家都约好了,要让你好好休息,然后..."</p>
|
||||
<p>"然后?"</p>
|
||||
<p>"然后陪你一整天!"五人异口同声。</p>
|
||||
<p>林克哭笑不得,但心中涌起一股温暖。</p>
|
||||
<p>这就是他的家人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>赛丽亚的旅馆餐厅里,十三位少女围坐在一张巨大的圆桌旁。</p>
|
||||
<p>林克坐在主位,左右分别是赛丽亚和敏泰。奥菲利亚、莎兰、帕丽丝、莫纳亨、泽丁、马琳、皇女艾丽婕、米娅、贝奇、艾泽拉依次落座。</p>
|
||||
<p>艾丽丝的位置空着,但桌上摆着一副碗筷,仿佛她也在场。</p>
|
||||
<p>"今天是我们难得的聚会。"赛丽亚微笑着说,"林克,你一直在冒险,也该好好休息一下了。"</p>
|
||||
<p>"没错!"帕丽丝拍着桌子,"再不休息,我们都要被冷落了!"</p>
|
||||
<p>"帕丽丝姐姐,你又夸张了。"米娅捂着嘴笑,"林克大哥明明每次都很照顾我们。"</p>
|
||||
<p>"哼,照顾是照顾,但时间太少了。"帕丽丝嘟着嘴,"我都要忘记被拥抱的感觉了。"</p>
|
||||
<p>"帕丽丝!"众少女同时脸红。</p>
|
||||
<p>林克也有些尴尬,但更多的是幸福。</p>
|
||||
<p>"好了好了,先吃饭。"赛丽亚打圆场,"今天的早餐是我和敏泰一起做的哦。"</p>
|
||||
<p>桌上摆满了各种美食——面包、牛奶、煎蛋、培根、水果沙拉...还有班图族特有的奶酪茶。</p>
|
||||
<p>"大家尝尝这个!"敏泰兴奋地说,"这是我从班图族带来的奶酪,超级好喝!"</p>
|
||||
<p>林克端起杯子,浓郁的奶香扑鼻而来。他喝了一口,温暖的感觉从胃里蔓延到全身。</p>
|
||||
<p>"好喝。"他笑着说。</p>
|
||||
<p>敏泰的脸瞬间红了,开心得差点跳起来。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐后,众人来到旅馆后院的草坪上。</p>
|
||||
<p>阳光正好,微风轻拂,是个适合休息的好日子。</p>
|
||||
<p>"林克,我最近研究了一个新魔法。"莎兰走到林克身边,手中悬浮着一个小小的光球,"想看看吗?"</p>
|
||||
<p>"当然。"</p>
|
||||
<p>莎兰轻轻一挥手,光球升空,然后炸开,化作无数闪烁的星星。那些星星在空中飞舞,组成了一幅美丽的画面——林克和后宫们的合影。</p>
|
||||
<p>"好漂亮!"贝奇惊叹道,"莎兰姐姐好厉害!"</p>
|
||||
<p>莎兰的脸微微泛红:"只是...一点小魔法而已。"</p>
|
||||
<p>"我也想学!"敏泰举手,"莎兰姐姐,教教我吧!"</p>
|
||||
<p>"好呀。"莎兰温柔地笑了,"不过魔法需要天赋和耐心,你要做好心理准备哦。"</p>
|
||||
<p>"没问题!我最有耐心了!"</p>
|
||||
<p>林克看着这一幕,嘴角不自觉地上扬。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>草坪的另一边,帕丽丝正在和泽丁、马琳切磋。</p>
|
||||
<p>"来来来,让我看看你们的实力有没有退步!"帕丽丝活动着手腕,一脸跃跃欲试。</p>
|
||||
<p>"帕丽丝姐姐,你太嚣张了!"泽丁握紧拳头,"我可是皇都军的守备队长!"</p>
|
||||
<p>"那又怎样?本小姐可是诺斯玛尔的街霸!"</p>
|
||||
<p>两人你来我往,打得难解难分。马琳在一旁观战,偶尔出声指点。</p>
|
||||
<p>"泽丁,你的出拳速度不够快!"</p>
|
||||
<p>"帕丽丝姐姐,你的步伐有漏洞!"</p>
|
||||
<p>林克走过去,看着三人切磋。</p>
|
||||
<p>"需要指导吗?"他笑着问。</p>
|
||||
<p>"林克!"帕丽丝眼睛一亮,"来,让我试试你的实力!"</p>
|
||||
<p>"你确定?"林克挑眉,"我可是剑神。"</p>
|
||||
<p>"剑神又怎样?本小姐才不怕!"</p>
|
||||
<p>林克摇摇头,拔出腰间的细雪之舞。</p>
|
||||
<p>"那就...点到为止。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一炷香后,帕丽丝躺在草地上,气喘吁吁。</p>
|
||||
<p>"你...你是不是放水了?"她不甘心地说。</p>
|
||||
<p>"没有。"林克收剑入鞘,"你进步了。"</p>
|
||||
<p>帕丽丝翻了个白眼,但嘴角却带着笑意。</p>
|
||||
<p>泽丁和马琳也走了过来,脸上满是敬佩。</p>
|
||||
<p>"林克大人的实力...真是深不可测。"泽丁感叹。</p>
|
||||
<p>"不愧是剑神。"马琳点头。</p>
|
||||
<p>林克笑了笑,伸出手将帕丽丝拉了起来。</p>
|
||||
<p>"还需要继续努力。"他轻声说。</p>
|
||||
<p>帕丽丝的脸红了,但很快恢复了常态:"哼,下次我一定会赢你!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,皇女艾丽婕拉着林克来到旅馆的二楼。</p>
|
||||
<p>"林克,我有件事想和你商量。"她的表情严肃。</p>
|
||||
<p>"什么事?"</p>
|
||||
<p>"关于...艾丽丝。"艾丽婕说道,"她离开去赎罪,但我们都很担心她。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>艾丽丝...他心中永远的痛。虽然她被赫尔德控制,但她确实伤害了很多人。</p>
|
||||
<p>"我知道她在做什么。"林克轻声说,"她需要这个。"</p>
|
||||
<p>"但我们...能不能帮帮她?"艾丽婕问道,"她是我们的姐妹,我们不希望她一个人承受。"</p>
|
||||
<p>林克看向艾丽婕,眼中闪过一丝温暖。</p>
|
||||
<p>"我也有这个想法。"他说,"等她完成一部分赎罪,我会去找她。"</p>
|
||||
<p>"真的?"艾丽婕的眼睛亮了。</p>
|
||||
<p>"嗯。"林克点头,"她是我的人,我不会让她一个人。"</p>
|
||||
<p>艾丽婕开心地扑进他怀里:"谢谢你,林克!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,夕阳将天空染成了橘红色。</p>
|
||||
<p>林克独自站在旅馆门口,看着远处的风景。</p>
|
||||
<p>十三位少女在他身后,有的在聊天,有的在玩耍,有的在安静地陪伴。</p>
|
||||
<p>这是他的家人,他的牵挂,他的...一切。</p>
|
||||
<p>"林克。"赛丽亚走到他身边,轻轻握住他的手,"在想什么?"</p>
|
||||
<p>"在想...我是多么幸运。"林克轻声说,"能有你们在身边。"</p>
|
||||
<p>赛丽亚笑了,靠在他的肩上:"是我们幸运,能遇到你。"</p>
|
||||
<p>其他少女也纷纷围了过来,十三个人挤在一起,看着夕阳慢慢落下。</p>
|
||||
<p>"林克。"贝奇突然说,"你以后...还会继续冒险吗?"</p>
|
||||
<p>"会。"林克点头,"赫尔德的阴谋还没有结束,还有很多真相需要揭开。"</p>
|
||||
<p>"那我们陪你!"众少女异口同声。</p>
|
||||
<p>林克看着她们,心中涌起一股暖流。</p>
|
||||
<p>"好。"他轻声说,"我们一起。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,旅馆里点起了温暖的灯光。</p>
|
||||
<p>林克坐在客厅的沙发上,十三位少女围坐在他身边。</p>
|
||||
<p>"今天开心吗?"他问。</p>
|
||||
<p>"开心!"众少女齐声回答。</p>
|
||||
<p>赛丽亚靠在他左边,敏泰靠在他右边。奥菲利亚和莎兰坐在地毯上,帕丽丝和莫纳亨坐在另一张沙发上。泽丁和马琳挤在一起,皇女艾丽婕优雅地坐在椅子上。米娅抱着平板电脑,贝奇和艾泽拉坐在窗台上。</p>
|
||||
<p>"林克。"艾泽拉突然开口,"你...后悔吗?"</p>
|
||||
<p>"后悔什么?"</p>
|
||||
<p>"后悔遇到我们...后悔背负这么多。"</p>
|
||||
<p>林克沉默了片刻,然后笑了。</p>
|
||||
<p>"不后悔。"他认真地说,"遇到你们,是我这辈子最幸运的事。"</p>
|
||||
<p>众少女的眼中闪烁着泪光,但嘴角都带着幸福的笑容。</p>
|
||||
<p>"我们也一样。"赛丽亚轻声说,"遇到你...是我们最大的幸运。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,林克躺在床上,却睡不着。</p>
|
||||
<p>他起身走到窗前,看着星空。</p>
|
||||
<p>艾丽丝...你还好吗?</p>
|
||||
<p>他拿出一根紫色的发丝,轻轻放在唇边。</p>
|
||||
<p>"等你回来..."他轻声说,"我会去找你。"</p>
|
||||
<p>窗外,月光如水,洒在这片宁静的土地上。</p>
|
||||
<p>明天,又是新的一天。</p>
|
||||
<p>新的冒险,新的挑战,在等着他。</p>
|
||||
<p>但此刻,他只想享受这份平静。</p>
|
||||
<p>因为...他知道,无论前方有什么,他都不是一个人。</p>
|
||||
<p>他有她们。</p>
|
||||
<p>他的家人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十六章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·后宫日常 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-115.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-117.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-86.html" class="sidebar-chapter ">第86章:普鲁兹发电站·闪电之帕特里斯</a>
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter current">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(116)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,999 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与赛丽亚的约会 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 117</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>第二天清晨,林克早早地起床。</p>
|
||||
<p>今天,他有一个特别的计划。</p>
|
||||
<p>"赛丽亚,今天有空吗?"他走到正在厨房忙碌的少女身边。</p>
|
||||
<p>"嗯?怎么了?"赛丽亚转过身,脸上带着温柔的笑容。</p>
|
||||
<p>"我想...和你单独出去。"林克轻声说,"就我们两个。"</p>
|
||||
<p>赛丽亚愣了一下,然后脸红了:"你是说...约会?"</p>
|
||||
<p>"嗯。"</p>
|
||||
<p>赛丽亚低下头,手指绞着围裙的边缘。过了一会儿,她抬起头,眼中满是期待:"好!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>上午,两人离开了旅馆。</p>
|
||||
<p>赛丽亚穿着一件淡绿色的连衣裙,金色的长发披散在肩上,在阳光下闪闪发光。她挽着林克的手臂,脸上带着幸福的笑容。</p>
|
||||
<p>"我们去哪里?"她好奇地问。</p>
|
||||
<p>"去一个特别的地方。"林克神秘地笑了笑。</p>
|
||||
<p>他们穿过艾尔文防线,来到了一片开满鲜花的草地。这里是他们第一次相遇的地方——林克受伤昏迷后,被赛丽亚救起的地方。</p>
|
||||
<p>"这里是..."赛丽亚惊讶地看着周围的景色。</p>
|
||||
<p>"还记得吗?"林克轻声说,"那天你把我从洛兰森林带回来,照顾了我三天。"</p>
|
||||
<p>"当然记得。"赛丽亚的眼中闪过回忆的光芒,"你那时候满身是血,我还以为...还以为你会死掉..."</p>
|
||||
<p>她的声音有些哽咽。林克伸手,轻轻擦去她眼角的泪水。</p>
|
||||
<p>"但我活下来了。"他温柔地说,"因为你。"</p>
|
||||
<p>赛丽亚抬起头,看着林克的眼睛。阳光下,他的眼中满是深情。</p>
|
||||
<p>"谢谢你,赛丽亚。谢谢你当初救了我,谢谢你一直陪在我身边。"</p>
|
||||
<p>"林克..."赛丽亚扑进他的怀里,"我也谢谢你...谢谢你出现在我的生命中。"</p>
|
||||
<p>两人在草地上坐下,看着远处的风景。</p>
|
||||
<p>"你知道吗?"赛丽亚轻声说,"那天你醒来,问我你的剑在哪里,我就知道...你是个特别的冒险家。"</p>
|
||||
<p>"为什么?"</p>
|
||||
<p>"因为你的眼睛。"赛丽亚看着他的眼睛,"那种渴望变强、渴望冒险的眼神...我从没见过。"</p>
|
||||
<p>林克沉默了片刻,然后说道:"那时候我只想找到阿甘左,让他教我更多。"</p>
|
||||
<p>"现在呢?"</p>
|
||||
<p>"现在..."林克看向她,"我只想保护你,保护所有我在乎的人。"</p>
|
||||
<p>赛丽亚的脸红了,她低下头,声音小小的:"林克...你真好。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>中午,两人在一家小餐馆吃了午餐。</p>
|
||||
<p>赛丽亚吃着林克点的甜点,脸上满是满足的笑容。</p>
|
||||
<p>"好吃吗?"林克问。</p>
|
||||
<p>"嗯!"赛丽亚用力点头,"你也尝尝!"</p>
|
||||
<p>她挖了一勺送到林克嘴边。林克张嘴吃下,然后笑了。</p>
|
||||
<p>"很甜。"</p>
|
||||
<p>"是不是!"赛丽亚开心地说。</p>
|
||||
<p>餐馆的老板娘看着这一幕,脸上露出慈祥的笑容:"你们感情真好。"</p>
|
||||
<p>"谢谢。"林克微笑道。</p>
|
||||
<p>"在一起多久了?"老板娘好奇地问。</p>
|
||||
<p>林克看向赛丽亚,两人对视一眼。</p>
|
||||
<p>"很久了。"赛丽亚轻声说,"从那一天开始,就很久了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,两人来到了洛兰森林。</p>
|
||||
<p>这里是林克第一次战斗的地方,也是他觉醒卡赞诅咒的地方。</p>
|
||||
<p>"还可怕吗?"赛丽亚看着幽深的森林,轻声问。</p>
|
||||
<p>"不害怕了。"林克握紧她的手,"因为有你在。"</p>
|
||||
<p>他们走进森林,来到了那片空地。</p>
|
||||
<p>"这里就是..."赛丽亚看着四周。</p>
|
||||
<p>"我第一次与哥布林战斗的地方。"林克说道,"那时候我很弱,差点死掉。"</p>
|
||||
<p>他看向赛丽亚:"但现在,我已经足够强了。强到可以保护你。"</p>
|
||||
<p>赛丽亚的眼中闪过泪光:"林克..."</p>
|
||||
<p>林克从怀里取出一个小盒子,递给她。</p>
|
||||
<p>"这是什么?"赛丽亚好奇地问。</p>
|
||||
<p>"打开看看。"</p>
|
||||
<p>赛丽亚打开盒子,里面是一条精致的项链。项链的吊坠是一颗蓝色水晶,在阳光下闪烁着柔和的光芒。</p>
|
||||
<p>"这是..."</p>
|
||||
<p>"我请莎兰帮忙做的。"林克说道,"水晶里封存着一道我的剑气,可以保护你。"</p>
|
||||
<p>他拿起项链,轻轻戴在赛丽亚的脖子上:"即使我不在你身边,它也会保护你。"</p>
|
||||
<p>赛丽亚摸着吊坠,眼泪终于滑落:"谢谢你...林克...谢谢你..."</p>
|
||||
<p>林克伸手擦去她的泪水,然后低下头,轻轻吻住了她的唇。</p>
|
||||
<p>这是一个温柔的吻,带着500年的思念和深深的爱。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人坐在洛兰森林的边缘,看着夕阳落下。</p>
|
||||
<p>"林克。"赛丽亚靠在他的肩上,"你还会继续冒险吗?"</p>
|
||||
<p>"会。"林克点头,"赫尔德的阴谋还没有结束。"</p>
|
||||
<p>"那你...会带着我吗?"</p>
|
||||
<p>"当然。"林克握紧她的手,"你说过,无论去哪里,你都会陪着我。"</p>
|
||||
<p>赛丽亚笑了:"嗯。我说过。"</p>
|
||||
<p>她抬起头,看着林克的眼睛:"林克,我有一个请求。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"以后...不管多忙,都要抽出时间陪我们。"她的声音小小的,"不只是我,还有奥菲利亚、敏泰、莎兰、帕丽丝...所有姐妹。"</p>
|
||||
<p>林克沉默了片刻,然后认真地点头:"我答应你。"</p>
|
||||
<p>"真的?"</p>
|
||||
<p>"真的。"林克轻声说,"你们是我最重要的人,我不会忽略你们。"</p>
|
||||
<p>赛丽亚开心地抱住他:"谢谢你!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,星空璀璨。</p>
|
||||
<p>两人躺在草地上,看着满天的星星。</p>
|
||||
<p>"林克,你知道吗?"赛丽亚轻声说,"我有时候会想...500年前的那个剑士,真的是你吗?"</p>
|
||||
<p>"是我。"林克握紧她的手,"我看到你在森林里醒来,什么记忆都没有。我救了你,但没能告诉你真相。"</p>
|
||||
<p>"你为什么不告诉我?"</p>
|
||||
<p>"因为时空之门即将关闭。"林克的声音有些苦涩,"我必须离开,否则会被困在过去。"</p>
|
||||
<p>赛丽亚沉默了。</p>
|
||||
<p>过了许久,她轻声说:"没关系。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"没关系。"赛丽亚看向林克,眼中满是温柔,"不管过去发生了什么,重要的是现在。现在,你在我身边,这就够了。"</p>
|
||||
<p>她抬起手,抚摸着林克的脸:"我爱你,林克。不管500年前,还是现在,我都爱你。"</p>
|
||||
<p>林克的眼中闪过一丝感动,他伸手将赛丽亚拉进怀里。</p>
|
||||
<p>"我也爱你。"他在她耳边轻声说,"从500年前救你的那一刻起,我就爱上你了。"</p>
|
||||
<p>"真的?"</p>
|
||||
<p>"真的。"林克轻声说,"你回头看我时的那个眼神...我记了500年。"</p>
|
||||
<p>赛丽亚的眼泪再次滑落,但这次是幸福的泪水。</p>
|
||||
<p>"林克...我好幸福..."</p>
|
||||
<p>"我也是。"林克紧紧抱着她,"能和你在一起,是我最大的幸福。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,两人回到旅馆。</p>
|
||||
<p>赛丽亚的脸红扑扑的,眼中满是爱意。她拉着林克的手,走向自己的房间。</p>
|
||||
<p>"赛丽亚?"林克有些意外。</p>
|
||||
<p>"今晚..."赛丽亚低下头,声音小小的,"我想和你在一起。"</p>
|
||||
<p>林克愣了一下,然后笑了。</p>
|
||||
<p>"好。"</p>
|
||||
<p>他抱起赛丽亚,走进了房间。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>房间里,月光透过窗户洒在床上。</p>
|
||||
<p>林克将赛丽亚轻轻放在床上,然后俯下身,吻住了她的唇。</p>
|
||||
<p>这个吻热烈而深情,带着500年的等待和思念。</p>
|
||||
<p>赛丽亚生涩地回应着,双手环上林克的脖子。</p>
|
||||
<p>"林克..."她在吻的间隙轻声说,"我爱你..."</p>
|
||||
<p>"我也爱你。"</p>
|
||||
<p>两人的身影在月光中交缠,呼吸声和心跳声交织在一起。</p>
|
||||
<p>这是他们的时刻,只属于他们的时刻。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,林克睁开眼睛。</p>
|
||||
<p>赛丽亚蜷缩在他怀里,金色的长发散落在枕头上,脸上带着满足的笑容。</p>
|
||||
<p>"早安。"他轻声说,吻了吻她的额头。</p>
|
||||
<p>赛丽亚睁开眼睛,看到林克,脸上露出幸福的笑容:"早安..."</p>
|
||||
<p>她主动凑上去,吻住了他的唇。</p>
|
||||
<p>"谢谢你,林克。"她在吻的间隙轻声说,"谢谢你给我这么美好的一天。"</p>
|
||||
<p>"以后还会有很多这样的日子。"林克轻声说,"我保证。"</p>
|
||||
<p>赛丽亚笑了,靠在他的胸口:"嗯。我相信你。"</p>
|
||||
<p>窗外,阳光正好。</p>
|
||||
<p>新的一天,开始了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十七章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·赛丽亚篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-116.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-118.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-87.html" class="sidebar-chapter ">第87章:特伦斯发电站·熔岩之萨姆</a>
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter current">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(117)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,965 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与奥菲利亚的重逢 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 118</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>清晨,林克找到了奥菲利亚。</p>
|
||||
<p>她正站在旅馆的阳台上,金色的长发在晨风中飘动,望着远方的天际线出神。</p>
|
||||
<p>"在想什么?"林克走到她身边。</p>
|
||||
<p>"在想...过去。"奥菲利亚轻声说,"想起我们第一次相遇的时候。"</p>
|
||||
<p>"天帷巨兽?"</p>
|
||||
<p>"嗯。"奥菲利亚转过身,眼中满是回忆,"那时候我只是一个被罗特斯控制的傀儡,是你救了我。"</p>
|
||||
<p>她看向林克:"能...陪我去一趟天帷巨兽吗?我想回去看看。"</p>
|
||||
<p>"好。"林克点头,"就我们两个。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>天帷巨兽,巨大的鲸鱼漂浮在空中。</p>
|
||||
<p>奥菲利亚站在天帷巨兽的入口,深吸了一口气。熟悉的气息扑面而来,带着海洋的咸味和GBL教的神秘感。</p>
|
||||
<p>"好久没回来了。"她轻声说。</p>
|
||||
<p>"害怕吗?"林克问。</p>
|
||||
<p>"不害怕了。"奥菲利亚摇头,"因为有你在。"</p>
|
||||
<p>两人走进天帷巨兽,穿过熟悉的走廊。这里已经不再是当年被罗特斯控制的恐怖之地,而是恢复了平静的神殿。</p>
|
||||
<p>"这里...曾经是我的家。"奥菲利亚轻声说,"我从小就在GBL教长大,教里的每个人都对我很好。"</p>
|
||||
<p>"然后罗特斯来了?"</p>
|
||||
<p>"嗯。"奥菲利亚的眼中闪过一丝痛苦,"它控制了所有人,包括我。我看着自己伤害了那么多无辜的人,却无能为力..."</p>
|
||||
<p>林克握紧她的手:"那不是你的错。"</p>
|
||||
<p>"我知道。"奥菲利亚轻声说,"但有时候...我还是会梦见那些场景。"</p>
|
||||
<p>两人来到了GBL教的神殿核心。这里曾经是罗特斯的囚笼,如今已经变成了一座安静的祈祷室。</p>
|
||||
<p>奥菲利亚跪在祭坛前,双手合十,默默祈祷。</p>
|
||||
<p>林克站在一旁,静静等待。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>祈祷结束后,两人来到天帷巨兽的边缘,坐在突出的平台上,看着云海翻涌。</p>
|
||||
<p>"林克。"奥菲利亚轻声说,"谢谢你。"</p>
|
||||
<p>"谢我什么?"</p>
|
||||
<p>"谢谢你救了我。"奥菲利亚看向他,眼中满是感激,"如果不是你,我可能早就死在罗特斯手里了。"</p>
|
||||
<p>"我只是做了应该做的事。"林克说。</p>
|
||||
<p>"不。"奥菲利亚摇头,"你做的...远比应该做的多。"</p>
|
||||
<p>她低下头,声音变小:"你知道吗?当你第一次出现在我面前时,我就感觉到...你是不一样的。"</p>
|
||||
<p>"不一样?"</p>
|
||||
<p>"嗯。"奥菲利亚抬起头,"你的眼睛里有光。那种...不屈的光芒。"</p>
|
||||
<p>她轻声说:"从那一刻起,我就知道...你会改变一切。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>奥菲利亚继续说:"后来,你真的做到了。你击败了罗特斯,解放了GBL教,也...拯救了我。"</p>
|
||||
<p>她看向林克,眼中闪着泪光:"林克,我..."</p>
|
||||
<p>"我知道。"林克轻声说,"我也...很喜欢你。"</p>
|
||||
<p>奥菲利亚的眼泪滑落,但嘴角带着幸福的笑容。</p>
|
||||
<p>"谢谢你..."她扑进林克的怀里,"谢谢你愿意接受这样的我..."</p>
|
||||
<p>林克紧紧抱住她:"你很坚强,奥菲利亚。经历了那么多,还能站起来,你是真正的战士。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,两人来到了GBL教的图书馆。</p>
|
||||
<p>这里收藏着无数古老的典籍,记录着GBL教数百年的历史。</p>
|
||||
<p>"我小时候最喜欢来这里。"奥菲利亚看着熟悉的书架,眼中满是怀念,"那时候我总是一个人躲在角落里看书,一待就是一整天。"</p>
|
||||
<p>"看的什么书?"林克问。</p>
|
||||
<p>"各种各样的。"奥菲利亚微笑道,"历史、神话、魔法...我对这个世界充满了好奇。"</p>
|
||||
<p>她从书架上抽出一本古旧的书籍:"这是我最喜欢的一本。"</p>
|
||||
<p>林克接过书,看到封面上写着《海洋之歌》。</p>
|
||||
<p>"是诗集?"</p>
|
||||
<p>"嗯。"奥菲利亚点头,"小时候,我总梦想着有一天能去看真正的海洋。"</p>
|
||||
<p>"现在呢?"</p>
|
||||
<p>"现在..."奥菲利亚看向林克,眼中带着期待,"我想和你一起去看。"</p>
|
||||
<p>林克笑了:"那就去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人来到了西海岸的海边。</p>
|
||||
<p>夕阳将海面染成了金色,海浪轻轻拍打着沙滩。海鸥在天空中飞翔,发出清脆的叫声。</p>
|
||||
<p>"好美..."奥菲利亚脱下鞋子,赤脚走在沙滩上,"这是我第一次看到真正的海洋。"</p>
|
||||
<p>林克站在她身后,看着她的背影在夕阳中显得格外美丽。</p>
|
||||
<p>"奥菲利亚。"他轻声唤道。</p>
|
||||
<p>"嗯?"奥菲利亚转过身。</p>
|
||||
<p>林克从怀里取出一个小盒子,递给她。</p>
|
||||
<p>"这是..."奥菲利亚惊讶地看着他。</p>
|
||||
<p>"打开看看。"</p>
|
||||
<p>奥菲利亚打开盒子,里面是一枚精致的发簪。发簪是银色的,顶端镶嵌着一颗蓝色宝石,像极了大海的颜色。</p>
|
||||
<p>"这是...海神的眼泪?"奥菲利亚惊讶道。</p>
|
||||
<p>"嗯。"林克点头,"据说这颗宝石来自深海,能够带来好运。"</p>
|
||||
<p>他拿起发簪,轻轻插在奥菲利亚的金发上:"希望它能守护你。"</p>
|
||||
<p>奥菲利亚摸着发簪,眼泪再次滑落:"谢谢你...林克...谢谢你..."</p>
|
||||
<p>林克伸手擦去她的泪水,然后低下头,轻轻吻住了她的唇。</p>
|
||||
<p>海风吹过,夕阳慢慢落下,两人的身影在沙滩上被拉得很长很长。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,两人坐在沙滩上,看着星空。</p>
|
||||
<p>"林克。"奥菲利亚靠在他的肩上,"你以后...还会继续冒险吗?"</p>
|
||||
<p>"会。"林克点头,"赫尔德的阴谋还没有结束。"</p>
|
||||
<p>"那...能不能带上我?"</p>
|
||||
<p>林克看向她:"你想?"</p>
|
||||
<p>"嗯。"奥菲利亚认真地说,"我想和你一起,去看看这个世界。"</p>
|
||||
<p>"好。"林克握紧她的手,"我们一起。"</p>
|
||||
<p>奥菲利亚笑了,那是发自内心的幸福笑容。</p>
|
||||
<p>"谢谢你...林克..."</p>
|
||||
<p>"不用谢。"林克轻声说,"能和你在一起,是我的幸运。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,两人回到旅馆。</p>
|
||||
<p>奥菲利亚的脸红红的,拉着林克的手不放。</p>
|
||||
<p>"林克..."她轻声说,"今晚...能不能...陪陪我?"</p>
|
||||
<p>林克看着她期待的眼神,点了点头。</p>
|
||||
<p>"好。"</p>
|
||||
<p>他抱起奥菲利亚,走进了房间。</p>
|
||||
<p>月光下,两颗心紧紧相连。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十八章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·奥菲利亚篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-117.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-119.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-88.html" class="sidebar-chapter ">第88章:格兰迪发电站·虚空之弗曼</a>
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter current">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(118)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,962 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与敏泰的雪山之行 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 119</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>三天后,林克踏上了前往雪山的旅程。</p>
|
||||
<p>这一次,他要去看望敏泰。</p>
|
||||
<p>那座熟悉的雪山营地在风雪中若隐若现,林克加快脚步,心中满是期待。</p>
|
||||
<p>"林克哥哥!"</p>
|
||||
<p>远处传来熟悉的声音,一个银发的小身影从营地跑了出来,扑进了林克的怀里。</p>
|
||||
<p>"敏泰!"林克稳住身形,笑着抱住她。</p>
|
||||
<p>"你终于来看我了!"敏泰的声音带着哭腔,"我好想你!"</p>
|
||||
<p>"我也想你。"林克轻轻抚摸她的银发。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>班图族营地,布万加正在喝茶。</p>
|
||||
<p>看到林克进来,他放下茶杯,脸上露出笑容:"林克,好久不见。"</p>
|
||||
<p>"族长。"林克点头致意。</p>
|
||||
<p>"叫我布万加就好。"布万加拍了拍身边的座位,"坐,我们聊聊。"</p>
|
||||
<p>两人坐在火炉旁,布万加倒了一杯热茶递给林克。</p>
|
||||
<p>"敏泰这几天一直在念叨你。"布万加笑着说,"每天都问'林克哥哥什么时候来'。"</p>
|
||||
<p>林克有些不好意思:"抱歉,最近一直在冒险..."</p>
|
||||
<p>"没关系。"布万加摆摆手,"我知道你肩负着重任。"</p>
|
||||
<p>他看向林克,眼神变得认真:"但我有一个请求。"</p>
|
||||
<p>"什么请求?"</p>
|
||||
<p>"照顾好敏泰。"布万加轻声说,"她从小就没有母亲,只有我这个不称职的父亲。如果可以...希望你能给她更多的关爱。"</p>
|
||||
<p>林克点头:"我会的。"</p>
|
||||
<p>布万加笑了,拍了拍他的肩膀:"那就好。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,林克和敏泰在雪地里散步。</p>
|
||||
<p>"林克哥哥,你看!"敏泰指着远处的冰晶,"好漂亮!"</p>
|
||||
<p>林克顺着她的手指看去,阳光下,冰晶折射出七彩的光芒,美得像童话世界。</p>
|
||||
<p>"想去那边看看吗?"他问。</p>
|
||||
<p>"想!"</p>
|
||||
<p>两人朝着冰晶的方向走去。雪地很软,每走一步都会留下深深的脚印。</p>
|
||||
<p>"林克哥哥。"敏泰突然说,"你还记得我们第一次见面吗?"</p>
|
||||
<p>"记得。"林克微笑道,"那时候你被冰龙斯卡萨的冰晶封住了。"</p>
|
||||
<p>"嗯。"敏泰点头,"我那时候好害怕...以为自己要死了。"</p>
|
||||
<p>她看向林克,眼中满是感激:"然后你出现了,打破冰晶,救了我。"</p>
|
||||
<p>"我只是做了应该做的事。"</p>
|
||||
<p>"不。"敏泰摇头,"你做的不只是应该做的。你还...安慰我,陪着我,告诉我一切都会好起来。"</p>
|
||||
<p>她低下头,声音变小:"从那一刻起,我就知道...你是特别的人。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>敏泰继续说:"后来,每次你来看我,我都好开心。我知道你有很多重要的事情要做,但你还是抽出时间来看我..."</p>
|
||||
<p>她抬起头,眼中闪着泪光:"谢谢你,林克哥哥...谢谢你愿意陪着我..."</p>
|
||||
<p>林克伸手擦去她的泪水:"傻丫头,哭什么。"</p>
|
||||
<p>"我...我只是太开心了..."敏泰破涕为笑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人来到一处温泉。</p>
|
||||
<p>"这是我们班图族最私密的温泉。"敏泰说,"只有在特别的日子才会开放。"</p>
|
||||
<p>"今天是什么特别的日子?"林克问。</p>
|
||||
<p>"你来的日子。"敏泰认真地说,"对我来说,你来的每一天都是特别的日子。"</p>
|
||||
<p>林克有些感动,轻轻揉了揉她的头发。</p>
|
||||
<p>两人换上浴衣,走进温泉。温热的泉水瞬间包裹了全身,驱散了雪山的寒冷。</p>
|
||||
<p>"好舒服..."敏泰靠在池边,发出满足的叹息。</p>
|
||||
<p>林克坐在她对面,看着蒸汽中敏泰的脸庞。她的银发被水浸湿,贴在脸颊上,显得格外可爱。</p>
|
||||
<p>"林克哥哥..."敏泰轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我有话想对你说。"敏泰鼓起勇气,"我...我喜欢你。"</p>
|
||||
<p>林克愣了一下。</p>
|
||||
<p>敏泰继续说:"不是对哥哥那种喜欢,是...是那种喜欢。"</p>
|
||||
<p>她的脸红得像熟透的苹果:"我知道我还小,可能不够成熟,但是...但是我真的很喜欢你..."</p>
|
||||
<p>林克沉默了片刻,然后笑了。</p>
|
||||
<p>"我也喜欢你,敏泰。"</p>
|
||||
<p>敏泰猛地抬起头,眼中满是不可置信:"真的?"</p>
|
||||
<p>"真的。"林克点头,"你活泼、善良、真诚...和你在一起,我总是很开心。"</p>
|
||||
<p>敏泰的眼泪夺眶而出,但嘴角带着幸福的笑容:"谢谢你...林克哥哥...谢谢你..."</p>
|
||||
<p>她扑进林克的怀里,紧紧抱着他。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人走出温泉,来到一处可以看到雪山的平台。</p>
|
||||
<p>"林克哥哥。"敏泰靠在他身上,"你以后...还会继续冒险吗?"</p>
|
||||
<p>"会。"林克点头。</p>
|
||||
<p>"那...带我一起去吧。"敏泰认真地说,"我想陪在你身边。"</p>
|
||||
<p>林克看向她:"雪山呢?你的族人需要你。"</p>
|
||||
<p>"我知道。"敏泰点头,"但我可以在你休息的时候回来。我想...去看看这个世界,和你一起。"</p>
|
||||
<p>林克沉思片刻,然后点头:"好。我们一起。"</p>
|
||||
<p>敏泰开心地笑了,在林克脸上印下一个吻。</p>
|
||||
<p>"谢谢你,林克哥哥!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>晚上,林克在敏泰的房间陪她。</p>
|
||||
<p>敏泰蜷缩在他怀里,银发散落在枕头上。</p>
|
||||
<p>"林克哥哥..."她轻声说,"能一直陪着我吗?"</p>
|
||||
<p>"我会的。"林克轻声说,"不管去哪里,我都会带着你。"</p>
|
||||
<p>敏泰笑了,闭上眼睛,沉沉睡去。</p>
|
||||
<p>月光透过窗户,照在这一对恋人身上。</p>
|
||||
<p>雪山的夜晚,格外宁静。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,林克告别布万加和敏泰。</p>
|
||||
<p>"下次再来看我!"敏泰站在营地门口,依依不舍。</p>
|
||||
<p>"我会的。"林克点头,"好好照顾自己。"</p>
|
||||
<p>"嗯!"敏泰用力点头,"你也是!"</p>
|
||||
<p>林克转身离去,敏泰一直目送他的身影消失在风雪中。</p>
|
||||
<p>"林克哥哥...一定要平安..."她轻声说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百一十九章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·敏泰篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-118.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-120.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-89.html" class="sidebar-chapter ">第89章:安图恩攻坚战·黑雾之源</a>
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter current">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(119)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,908 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>西海岸 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 12</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>转职仪式结束,林克和赛丽亚在赫顿玛尔休整了两天后,准备前往天空之城。</p>
|
||||
<p>按照GSD的指引,他们先来到了西海岸。</p>
|
||||
<p>西海岸位于赫顿玛尔的西边,是一座港口城市。与赫顿玛尔的繁华不同,这里充满了海洋的气息。空气中弥漫着咸咸的海风,街道上到处都是渔民和商人。</p>
|
||||
<p>"这里就是西海岸……"赛丽亚好奇地看着四周。</p>
|
||||
<p>"据说这里的海鲜很有名。"林克笑着说,"等从天空之城回来,我请你吃。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>莎兰住在城西的一座高塔里。</p>
|
||||
<p>那是一座魔法塔,外墙由蓝色的水晶构成,在阳光下闪烁着柔和的光芒。</p>
|
||||
<p>林克走到塔门前,轻轻敲了敲门。</p>
|
||||
<p>"进来吧,我已经等你们很久了。"</p>
|
||||
<p>门内传来一个优雅的女声。林克推开门,和赛丽亚一起走了进去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>塔内的装饰充满了魔法的气息。</p>
|
||||
<p>一个身穿紫色长袍的女子站在窗边。她有着一头银白色的长发,眼睛是深紫色的,像是蕴含着无尽的星空。</p>
|
||||
<p>"你就是林克?GSD的新弟子?"女子转过身来。</p>
|
||||
<p>"是的,莎兰小姐。"林克恭敬地行礼。</p>
|
||||
<p>"我知道你想去天空之城。"莎兰微微一笑,"坐吧,我们慢慢聊。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>莎兰开始讲述天空之城的事情。</p>
|
||||
<p>"天空之城,是数千年前天界与阿拉德大陆连接的通道。后来发生了'龙之战争',天界的暴君巴卡尔被封印,天空之城也因此封闭。"</p>
|
||||
<p>"那里的怪物比格兰之森强大得多——龙人、石巨人、人偶……各种各样的危险。"</p>
|
||||
<p>林克认真地听着。</p>
|
||||
<p>"对了,莎兰小姐。"林克想起什么,"GSD师父说,您可能会告诉我一些关于光剑的事情?"</p>
|
||||
<p>莎兰看向林克手中的晨曦。</p>
|
||||
<p>"这把剑……能让我看看吗?"</p>
|
||||
<p>林克拔出晨曦,递给莎兰。</p>
|
||||
<p>莎兰仔细端详着。</p>
|
||||
<p>"果然……"莎兰轻声说,"这把剑,和天空之城有关。"</p>
|
||||
<p>"什么意思?"</p>
|
||||
<p>"光剑的能量来源,是天空之城的'光之核心'。"莎兰说,"数千年前,一位剑魂从天空之城带出了一块光之核心的碎片,铸造了这把剑。"</p>
|
||||
<p>"如果你想发挥这把剑的真正力量,就必须去天空之城,找到光之核心。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开莎兰的魔法塔后,林克陷入了沉思。</p>
|
||||
<p>原来晨曦还有这样的来历……</p>
|
||||
<p>"林克?"赛丽亚担心地看着他。</p>
|
||||
<p>"我在想……我的剑道。"林克看着手中的晨曦,"GSD师父教我,剑魂要精通所有武器。但晨曦对我来说,似乎有着特殊的意义。"</p>
|
||||
<p>"走吧,去天空之城。"林克抬起头,眼中闪烁着坚定的光芒,"我要找到答案。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人来到西海岸的传送阵前。</p>
|
||||
<p>那是一个巨大的魔法阵,散发着淡淡的蓝色光芒。传送阵的中央,有一道直通天际的光柱——那就是通往天空之城的通道。</p>
|
||||
<p>"准备好了吗?"林克问赛丽亚。</p>
|
||||
<p>"准备好了!"</p>
|
||||
<p>就在这时,一个熟悉的声音从身后传来。</p>
|
||||
<p>"等等。"</p>
|
||||
<p>林克转身,惊讶地看到GSD正拄着拐杖走来。</p>
|
||||
<p>"师父?您怎么来了?"</p>
|
||||
<p>"天空之城不是你们现在的实力能单独闯荡的。"GSD说,"我陪你们走一趟。"</p>
|
||||
<p>"真的吗?"赛丽亚惊喜地问。</p>
|
||||
<p>"嗯。"GSD点点头,"正好……我也很久没去过那里了。"</p>
|
||||
<p>林克心中涌起一股暖流。有师父在,他就安心多了。</p>
|
||||
<p>"走吧。"GSD走到传送阵前,"跟紧我。"</p>
|
||||
<p>三人一起踏入传送阵,光芒闪烁中,他们的身影消失在西海岸。</p>
|
||||
<p>新的冒险,即将开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-11.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-13.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter ">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter ">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter ">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter ">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter ">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter ">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter ">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter ">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter ">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter ">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter ">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter current">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter ">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter ">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter ">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter ">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter ">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter ">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter ">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter ">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter ">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter ">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter ">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter ">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter ">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter ">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter ">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter ">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter ">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter ">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter ">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter ">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter ">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter ">第34章:暗精灵墓地·剩余三将军</a>
|
||||
<a href="chapter-35.html" class="sidebar-chapter ">第35章:邪龙斯皮兹</a>
|
||||
<a href="chapter-36.html" class="sidebar-chapter ">第36章:莎兰的探望</a>
|
||||
<a href="chapter-37.html" class="sidebar-chapter ">第37章:暗影迷宫·影子剑士</a>
|
||||
<a href="chapter-38.html" class="sidebar-chapter ">第38章:熔岩穴·泰坦之怒</a>
|
||||
<a href="chapter-39.html" class="sidebar-chapter ">第39章:暗黑城入口·无头骑士</a>
|
||||
<a href="chapter-40.html" class="sidebar-chapter ">第40章:万年雪山·冰心少年</a>
|
||||
<a href="chapter-41.html" class="sidebar-chapter ">第41章:敏泰的加入</a>
|
||||
<a href="chapter-42.html" class="sidebar-chapter ">第42章:山脊·野兽师</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(12)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,949 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与莎兰的魔法时光 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 120</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>西海岸的魔法塔,是魔法师公会的所在地。</p>
|
||||
<p>林克推开塔门,走进这座充满神秘气息的建筑。塔内弥漫着淡淡的魔法波动,墙上挂满了各种魔法阵和符文。</p>
|
||||
<p>"林克?"</p>
|
||||
<p>熟悉的声音从二楼传来。林克抬头,看到莎兰正站在楼梯上,紫色的长发垂落在肩上,眼中满是惊喜。</p>
|
||||
<p>"我来看你了。"林克微笑道。</p>
|
||||
<p>莎兰快步走下楼梯,来到林克面前:"怎么不提前说一声?"</p>
|
||||
<p>"想给你一个惊喜。"</p>
|
||||
<p>莎兰笑了,那是发自内心的笑容:"那就...谢谢你了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"今天想做点什么?"莎兰问。</p>
|
||||
<p>"随便。"林克说,"想看看你工作的地方。"</p>
|
||||
<p>"那就来我的研究室吧。"</p>
|
||||
<p>莎兰带着林克来到塔顶的研究室。这里到处都是书籍、水晶球、魔法阵,还有各种奇怪的装置。</p>
|
||||
<p>"这就是我平时工作的地方。"莎兰说,"我在这里研究各种魔法。"</p>
|
||||
<p>"研究什么?"</p>
|
||||
<p>"各种。"莎兰走到书架前,"空间魔法、时间魔法、元素魔法...最近在研究一个新的方向。"</p>
|
||||
<p>"什么方向?"</p>
|
||||
<p>"剑气与魔法的融合。"莎兰转身,眼中闪烁着光芒,"我想...如果能将魔法附加在剑气上,威力会更大。"</p>
|
||||
<p>林克来了兴趣:"怎么做?"</p>
|
||||
<p>"需要你的配合。"莎兰说,"你的剑气很强,我想测试一下魔法与剑气的融合效果。"</p>
|
||||
<p>"好。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人来到魔法塔的试验场。</p>
|
||||
<p>莎兰站在一旁,双手结印,一道紫色的魔法阵在空中浮现。</p>
|
||||
<p>"林克,用剑气攻击这个魔法阵。"</p>
|
||||
<p>林克拔出细雪之舞,剑气斩向魔法阵。</p>
|
||||
<p>"铛——!"</p>
|
||||
<p>剑气与魔法阵碰撞,发出清脆的声响。但让两人惊讶的是,剑气竟然被魔法阵吸收了!</p>
|
||||
<p>"成功了!"莎兰兴奋地说,"剑气被魔法阵吸收了!"</p>
|
||||
<p>"这意味着什么?"林克问。</p>
|
||||
<p>"意味着...我们可以创造一种新的战斗方式。"莎兰眼中满是期待,"剑士与魔法师的配合,会产生意想不到的效果。"</p>
|
||||
<p>她看向林克:"谢谢你配合我。"</p>
|
||||
<p>"不客气。"林克微笑,"我也学到了很多。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,两人坐在魔法塔的屋顶,看着西海岸的风景。</p>
|
||||
<p>"林克。"莎兰轻声说,"你还记得我们第一次见面吗?"</p>
|
||||
<p>"记得。"林克点头,"那时候我刚转职成剑魂,你告诉了我晨曦的来历。"</p>
|
||||
<p>"嗯。"莎兰的眼中满是回忆,"那时候你还是一个青涩的少年,眼神中充满了对力量的渴望。"</p>
|
||||
<p>她看向林克:"现在,你已经成长为真正的剑神了。"</p>
|
||||
<p>"因为有你。"林克轻声说,"如果没有你的教导,我不可能成长这么快。"</p>
|
||||
<p>莎兰的脸微微泛红:"我只是...做了一些小事而已。"</p>
|
||||
<p>"不。"林克摇头,"你教会了我很多。不只是魔法,还有...如何看待力量。"</p>
|
||||
<p>他看向莎兰:"你说,力量本身没有善恶,关键在于使用它的心。这句话,我一直记着。"</p>
|
||||
<p>莎兰的眼中闪过一丝感动:"林克..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,夕阳将西海岸染成了金色。</p>
|
||||
<p>两人走在海边,感受着海风的轻拂。</p>
|
||||
<p>"林克。"莎兰停下脚步,"我有话想对你说。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>莎兰深吸一口气,鼓起勇气:"我...喜欢你。"</p>
|
||||
<p>林克愣了一下。</p>
|
||||
<p>莎兰继续说:"从第一次见面开始,我就被你吸引了。你的勇气、你的决心、你对力量的追求...都让我着迷。"</p>
|
||||
<p>她低下头:"我知道你是剑士,我是魔法师,我们的世界似乎很远。但是...我控制不住自己的心。"</p>
|
||||
<p>林克沉默了片刻,然后笑了。</p>
|
||||
<p>"我也喜欢你,莎兰。"</p>
|
||||
<p>莎兰猛地抬起头,眼中满是不可置信:"真的?"</p>
|
||||
<p>"真的。"林克点头,"你温柔、智慧、美丽...和你在一起,我总是能学到很多。"</p>
|
||||
<p>莎兰的眼泪滑落,但嘴角带着幸福的笑容。</p>
|
||||
<p>"谢谢你...林克...谢谢你..."</p>
|
||||
<p>林克伸手擦去她的泪水,然后低下头,轻轻吻住了她的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,两人坐在沙滩上,看着星空。</p>
|
||||
<p>"林克。"莎兰靠在他的肩上,"你以后还会继续冒险吗?"</p>
|
||||
<p>"会。"林克点头。</p>
|
||||
<p>"那...能带上我吗?"</p>
|
||||
<p>林克看向她:"你想?"</p>
|
||||
<p>"嗯。"莎兰认真地说,"我想和你一起,去看看这个世界。"</p>
|
||||
<p>"好。"林克握紧她的手,"我们一起。"</p>
|
||||
<p>莎兰笑了,那是发自内心的幸福笑容。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,两人回到莎兰的房间。</p>
|
||||
<p>"林克..."莎兰轻声说,"今晚...留下来吧。"</p>
|
||||
<p>林克看着她期待的眼神,点了点头。</p>
|
||||
<p>月光下,两颗心紧紧相连。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·莎兰篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-119.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-121.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-90.html" class="sidebar-chapter ">第90章:安图恩攻坚战·震颤的大地</a>
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter current">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(120)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,982 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与帕丽丝的格斗训练 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 121</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>诺斯玛尔,曾经的瘟疫之地。</p>
|
||||
<p>黄沙漫天,废墟绵延。林克和帕丽丝并肩走在荒废的街道上,脚下的石板已经被岁月侵蚀得坑坑洼洼。周围的建筑大多已经坍塌,只剩下断壁残垣在风中呜咽。</p>
|
||||
<p>"好久没回来了。"帕丽丝轻声说,她的声音在空旷的街道上回荡,"这里...曾经是我的家。"</p>
|
||||
<p>林克看向她。帕丽丝穿着标志性的格斗家服饰,紧身的上衣和短裙勾勒出她健美的身材。她的紫色长发在风中飘动,眼神中带着复杂的情绪——怀念、痛苦、还有一丝释然。</p>
|
||||
<p>"后悔吗?"林克问,"离开这里。"</p>
|
||||
<p>帕丽丝停下脚步,转身看向林克。</p>
|
||||
<p>"不后悔。"她摇头,嘴角浮现一丝苦笑,"这里给了我太多痛苦,也让我成长。如果没有那场瘟疫,我可能一辈子都是月光酒馆里那个普通的服务员,永远不知道自己还能战斗。"</p>
|
||||
<p>她的目光变得锐利起来:"而且,离开这里之后,我遇到了你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人继续前行,来到了一片开阔地。</p>
|
||||
<p>这里曾经是诺斯玛尔的中心广场,如今只剩下破碎的喷泉和半截石柱。但在废墟的一角,帕丽丝看到了一个熟悉的轮廓。</p>
|
||||
<p>"那是...月光酒馆?"她快步走过去。</p>
|
||||
<p>曾经热闹的酒馆如今只剩下一面墙壁和半个屋顶。斑驳的招牌上,"月光"两个字依稀可辨。帕丽丝伸手抚摸着粗糙的墙面,眼中闪过回忆的神色。</p>
|
||||
<p>"这是我曾经打工的地方。"她轻声说,"那时候我还是一个普通的服务员,每天忙忙碌碌,给客人们端酒送菜,听着他们吹牛聊天。生活简单而平静,我以为这样的日子会一直持续下去。"</p>
|
||||
<p>"然后狄瑞吉来了?"林克走到她身边。</p>
|
||||
<p>帕丽丝点头,眼中闪过痛苦:"嗯。一夜之间,一切都变了。瘟疫席卷了整个城市,我看着熟悉的人一个个倒下...酒馆的老板、常来的客人、街边的邻居...他们变成了怪物,或者直接死在了瘟疫中。"</p>
|
||||
<p>她的身体微微颤抖:"那时候我以为自己也会死。我躲在酒馆的地下室里,听着外面的惨叫声,感受着自己的身体一点点被瘟疫侵蚀..."</p>
|
||||
<p>林克握住她的手,感受到她冰凉的温度。</p>
|
||||
<p>帕丽丝深吸一口气,继续说:"但就在我以为一切都结束的时候,你出现了。你带着冒险家们闯入这个被诅咒的城市,一路杀到瘟疫之源,把狄瑞吉赶回了魔界。"</p>
|
||||
<p>她转向林克,眼中满是感激:"你救了所有人,包括我。"</p>
|
||||
<p>林克摇头:"我只是做了应该做的事。"</p>
|
||||
<p>"不。"帕丽丝认真地看着他,"你做的远比应该做的多。你不只是救了我,还帮我找到了新的方向。是你让我知道,我不只是一个被瘟疫诅咒的人,我还可以成为一个战士,一个格斗家,一个能为别人而战的人。"</p>
|
||||
<p>她松开林克的手,后退几步,活动着手腕:"说起来,我们还没好好打过一场呢。今天,让我看看你变强了多少!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午的阳光洒在废墟上,给断壁残垣镀上了一层金色。</p>
|
||||
<p>帕丽丝站在林克对面,摆出了格斗家的架势。她的双拳散发着淡淡的毒气,眼神中带着战意和兴奋。</p>
|
||||
<p>"来吧!"她喊道,"让我看看你的实力有没有退步!"</p>
|
||||
<p>林克笑了,拔出细雪之舞。剑身反射着阳光,闪烁着寒光。</p>
|
||||
<p>"你确定?"他问,"我可是剑神。"</p>
|
||||
<p>"剑神又怎样!本小姐才不怕!"</p>
|
||||
<p>话音未落,帕丽丝已经冲了过来。她的速度快得惊人,拳头带着剧毒直击林克的面门。林克侧身闪避,同时挥剑反击,剑尖划出一道弧线。</p>
|
||||
<p>两人你来我往,打得难解难分。</p>
|
||||
<p>帕丽丝的拳头带着剧毒,每一击都蕴含着致命的威胁。她的身法灵活诡异,时而贴身攻击,时而后撤躲避。她的毒功已经到了炉火纯青的境界,每一次出拳都伴随着紫色的毒雾。</p>
|
||||
<p>林克的剑气凌厉而精准,每一次格挡都恰到好处。他的动作流畅如水,攻守之间转换自如。剑神境界的他已经能感受到剑与人的合一,每一剑都带着玄妙的韵律。</p>
|
||||
<p>"不错!"帕丽丝喘着气,跳后几步,"你的实力确实强!比你刚来诺斯玛尔的时候强太多了!"</p>
|
||||
<p>林克收剑:"你也不差。进步很大,尤其是毒功的运用,比我上次见你的时候精进了不少。"</p>
|
||||
<p>帕丽丝得意地笑了:"那当然!本小姐可是很努力地修炼呢!"</p>
|
||||
<p>她的表情突然变得认真起来:"林克,再来!这次我不会手下留情!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二轮训练更加激烈。</p>
|
||||
<p>帕丽丝的速度更快了,她的身影如同鬼魅,在林克周围不断闪烁。每一拳都带着凌厉的风声,每一脚都蕴含着巨大的力量。她的毒雾也越来越浓,几乎笼罩了整个战斗区域。</p>
|
||||
<p>林克不得不认真起来。他开启流心状态,剑气变得更加锋利。每一次挥剑都带着流心的加持,威力倍增。</p>
|
||||
<p>两人的战斗持续了很久,从下午打到了黄昏。夕阳西下,金色的光芒洒在废墟上,为这场激烈的对决增添了一层浪漫的色彩。</p>
|
||||
<p>终于,帕丽丝停下了动作,大口喘着气。汗水浸透了她的衣服,勾勒出她健美的身材。</p>
|
||||
<p>"够了...够了..."她摆手,"我认输了..."</p>
|
||||
<p>林克也收起细雪之舞,走到她身边:"你很强,帕丽丝。如果是我刚成为剑神那会儿,说不定真的会输给你。"</p>
|
||||
<p>帕丽丝瞪了他一眼:"你是在夸我还是在夸你自己?"</p>
|
||||
<p>林克笑了:"都是在夸。你真的很厉害,帕丽丝。"</p>
|
||||
<p>帕丽丝的脸微微泛红,她别过头:"哼,油嘴滑舌..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人并肩坐在废墟的高处,看着夕阳慢慢沉入地平线。</p>
|
||||
<p>天边的云霞被染成了橙红色,美得像一幅画。风吹过废墟,带起一阵沙尘,却没有破坏这份宁静。</p>
|
||||
<p>帕丽丝靠在林克肩上,身体有些疲惫,但心情很放松。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"谢谢你陪我来这里。"她的声音很轻,"我以为回到诺斯玛尔会很痛苦,但...和你在一起,我发现自己可以平静地面对这些回忆了。"</p>
|
||||
<p>林克握住她的手:"过去的已经过去了,帕丽丝。你现在有了新的生活,新的方向,还有...我在你身边。"</p>
|
||||
<p>帕丽丝沉默了片刻,然后深吸一口气。</p>
|
||||
<p>"林克,我有话想对你说。"</p>
|
||||
<p>林克转向她,看着她的眼睛。</p>
|
||||
<p>帕丽丝的眼神很认真,带着一丝紧张和期待:"我...我喜欢你。"</p>
|
||||
<p>她的声音很轻,但每一个字都很清晰:"我知道我不够温柔,不够可爱,性格也不好。我说话直,脾气暴,有时候还很凶...但是...我真的很喜欢你。"</p>
|
||||
<p>她低下头:"从你救我的那天开始,我就一直把你放在心里。你是我遇到的第一个不把我当怪物的人,第一个愿意接受我的人,第一个...让我想要变强的人。"</p>
|
||||
<p>林克没有说话,只是静静地看着她。</p>
|
||||
<p>帕丽丝有些紧张:"你...你会不会觉得我很烦?"</p>
|
||||
<p>林克笑了,伸手抬起她的下巴,让她看向自己。</p>
|
||||
<p>"帕丽丝,"他认真地说,"我也喜欢你。"</p>
|
||||
<p>帕丽丝愣住了:"真...真的?你不嫌弃我?"</p>
|
||||
<p>"不嫌弃。"林克摇头,"你直爽、勇敢、真实。你从不掩饰自己的情感,从不虚伪做作。和你在一起,我总是很开心,很放松。我喜欢你这样的性格。"</p>
|
||||
<p>帕丽丝的眼眶湿润了,眼泪不自觉地滑落。但她的嘴角带着幸福的笑容。</p>
|
||||
<p>"你这个傻瓜..."她轻声说,"为什么不早说...害我担心了这么久..."</p>
|
||||
<p>林克伸手擦去她的眼泪:"因为我一直在等你准备好。"</p>
|
||||
<p>帕丽丝的心跳加速了。她看着林克的眼睛,看到了里面深深的温柔。然后,她主动凑过去,吻住了他的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>这是一个温柔的吻,带着等待已久的深情。</p>
|
||||
<p>夕阳的余晖洒在两人身上,为这个吻镀上了一层金色的光芒。帕丽丝的双臂环住林克的脖子,身体紧紧贴着他。林克的手轻轻搂住她的腰,将她拥入怀中。</p>
|
||||
<p>吻了很久,两人才分开。帕丽丝的脸红得像晚霞,眼睛亮晶晶的。</p>
|
||||
<p>"林克..."她轻声说,声音带着羞涩,"今晚...我们可以不回去吗?"</p>
|
||||
<p>林克看着她,读懂了她眼中的期待。他伸手抚摸着她的脸颊,感受着她微热的温度。</p>
|
||||
<p>"你想在这里?"他问。</p>
|
||||
<p>帕丽丝点头,眼神中带着一丝期待和紧张:"我想和你在一起...在这片废墟上...这里是我的起点,也是..."</p>
|
||||
<p>她的声音越来越小:"也是我想和你开始新生活的地方..."</p>
|
||||
<p>林克没有说话,只是再次吻住了她。这一次的吻更加热烈,更加深入。帕丽丝发出一声轻哼,紧紧抱住了他。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,星星出现在天空中。</p>
|
||||
<p>废墟的角落里,两人依偎在一起。帕丽丝的头靠在林克胸口,手指在他的胸口画着圈。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我好幸福。"她的声音带着满足,"这是我第一次觉得...原来生活可以这么美好。"</p>
|
||||
<p>林克搂紧了她:"以后会更好的,帕丽丝。我会一直在你身边。"</p>
|
||||
<p>帕丽丝抬起头,看着他:"说话算数?"</p>
|
||||
<p>"算数。"</p>
|
||||
<p>她笑了,凑过去又吻了他一下:"那...我们再来一次?"</p>
|
||||
<p>林克笑了:"你今天精力很旺盛啊。"</p>
|
||||
<p>帕丽丝红着脸,但还是倔强地说:"本小姐想怎样就怎样,你管得着吗?"</p>
|
||||
<p>林克没有回答,只是将她拉入怀中,再次吻住了她。</p>
|
||||
<p>月光洒在废墟上,见证着这对恋人的甜蜜时光。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,两人并肩离开诺斯玛尔。</p>
|
||||
<p>帕丽丝的脸上带着幸福的笑容,她紧紧握着林克的手,再也不愿放开。</p>
|
||||
<p>"林克。"她说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"下次...我们还来这里吗?"</p>
|
||||
<p>林克看了她一眼,笑了:"你想来就来。"</p>
|
||||
<p>帕丽丝开心地笑了,把头靠在他的肩上。</p>
|
||||
<p>曾经,诺斯玛尔是她痛苦的回忆。但现在,这里成了她和林克爱情开始的地方。</p>
|
||||
<p>废墟依然存在,但她的心中已经没有了恐惧。因为,她知道,无论发生什么,都有一个人会一直陪在她身边。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十一章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·帕丽丝篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-120.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-122.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-91.html" class="sidebar-chapter ">第91章:安图恩攻坚战·擎天之柱</a>
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter current">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(121)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,984 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与莫纳亨的念动力 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 122</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>绿都格罗兹尼,曾经的念动力者聚居地。</p>
|
||||
<p>阳光透过稀疏的云层,洒在这片曾经被诅咒的土地上。林克和莫纳亨并肩走在重建的街道上,周围是新建的房屋和正在生长的绿植。</p>
|
||||
<p>空气中弥漫着泥土和青草的芬芳,与过去那股腐朽的气息截然不同。</p>
|
||||
<p>"这里变化好大。"林克环顾四周,感慨道。</p>
|
||||
<p>曾经破败的建筑已经被修复,街道两旁种满了各色花草。有孩子在广场上玩耍,他们的笑声回荡在空中,给这片曾经死寂的土地带来了生机。</p>
|
||||
<p>"嗯。"莫纳亨点头,她的脸上带着温柔的笑意,"在你救了我之后,卡勒特的控制被彻底解除了。念动力者们不再被当作武器,而是可以自由地生活。"</p>
|
||||
<p>她停下脚步,转向林克:"谢谢你...林克。谢谢你给了我新的生活。"</p>
|
||||
<p>林克看着她。莫纳亨穿着淡绿色的长裙,银白色的短发在阳光下闪着柔和的光芒。她的紫色眼睛清澈如水,与曾经那个被控制、充满恐惧的少女判若两人。</p>
|
||||
<p>"你不需要谢我。"林克说,"我只是做了应该做的事。"</p>
|
||||
<p>莫纳亨摇头:"不,你做的远比应该做的多。你不只是救了我,还让我学会了如何面对自己的力量,如何用它来保护别人。"</p>
|
||||
<p>她低下头,声音变得轻柔:"以前,我一直以为这份力量是诅咒。但现在,我知道它也可以是礼物。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,莫纳亨带着林克来到一片开阔的空地。</p>
|
||||
<p>"我想给你看看我的修炼成果。"她说,眼中带着期待。</p>
|
||||
<p>林克点头:"好,让我看看你进步了多少。"</p>
|
||||
<p>莫纳亨深吸一口气,闭上眼睛。她的身体周围开始浮现淡淡的紫色光芒,那是念动力的具象化。</p>
|
||||
<p>先是几块小石子漂浮起来,然后是几根树枝,接着是更大的石块...越来越多的物体被她的念动力托举到空中,在她身边旋转飞舞。</p>
|
||||
<p>林克看着这一幕,眼中闪过赞许的神色。</p>
|
||||
<p>莫纳亨的念动力控制力比以前精进了太多。以前她的力量虽然强大,但缺乏控制,经常会伤及无辜。现在,她能精准地操控每一个物体,让它们按照自己的意愿移动。</p>
|
||||
<p>慢慢地,空中的物体越来越多,从小石子到大石块,从树枝到整根圆木,甚至还有几辆废弃的推车。它们在空中形成一个巨大的漩涡,围绕着莫纳亨旋转。</p>
|
||||
<p>"厉害。"林克由衷地赞叹。</p>
|
||||
<p>莫纳亨睁开眼睛,对着林克笑了。然后她轻轻挥手,空中的物体缓缓降落,稳稳地放回原位。</p>
|
||||
<p>"如何?"她问,眼中带着期待。</p>
|
||||
<p>"很厉害。"林克鼓掌,"你的控制力进步很大,比以前精准多了。"</p>
|
||||
<p>莫纳亨开心地笑了:"我每天都在练习,想着有一天能用这份力量保护重要的人。"</p>
|
||||
<p>她的眼神变得认真:"林克,我想和你切磋一下。"</p>
|
||||
<p>林克愣了一下:"你确定?"</p>
|
||||
<p>"确定。"莫纳亨点头,"我想知道,自己和你之间的差距还有多大。"</p>
|
||||
<p>林克想了想,点头:"好,那我们就比划比划。不过点到为止。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>切磋开始了。</p>
|
||||
<p>莫纳亨率先出手,她的念动力如同无形的巨手,朝林克压来。林克侧身闪避,同时拔出细雪之舞,剑气斩向那股无形的力量。</p>
|
||||
<p>两人的战斗激烈而精彩。</p>
|
||||
<p>莫纳亨的念动力变幻莫测,她可以将物体化为武器,也可以直接用精神力量攻击。她的攻击如同潮水,一波接一波,不给对手喘息的机会。</p>
|
||||
<p>林克的剑术凌厉而流畅,他在念动力的风暴中穿梭,时而闪避,时而反击。他的剑气所到之处,念动力形成的障碍纷纷瓦解。</p>
|
||||
<p>战斗持续了很久。莫纳亨越战越勇,她的念动力越来越强,几乎将整片空地都纳入了攻击范围。但林克依然游刃有余,他的剑神境界让他能够感知到念动力的流动,提前做出应对。</p>
|
||||
<p>终于,莫纳亨停下了动作,大口喘着气。她的额头上渗出了细密的汗珠,身体周围的光芒也慢慢消散。</p>
|
||||
<p>"我输了。"她喘息着说,"你的实力...还是比我强太多了。"</p>
|
||||
<p>林克收起剑,走到她身边:"你已经很强了,莫纳亨。能和我打这么久,已经证明你的实力。"</p>
|
||||
<p>莫纳亨苦笑:"但还是赢不了你。"</p>
|
||||
<p>"赢不了我很正常。"林克笑着说,"我是剑神,你才修炼了多久?能有这样的实力已经很厉害了。"</p>
|
||||
<p>他伸手拍了拍她的肩膀:"而且,你还有很大的进步空间。继续努力,总有一天你会超越我的。"</p>
|
||||
<p>莫纳亨看着他的眼睛,认真地点头:"嗯,我会继续努力的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人坐在空地的边缘,看着夕阳慢慢西沉。</p>
|
||||
<p>莫纳亨靠在林克肩上,身体微微疲惫,但心情很轻松。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"你知道吗,曾经我以为自己永远不会有正常的生活。"她的声音带着回忆,"被卡勒特抓走的时候,我以为一切都完了。他们强迫我使用念动力,用它伤害无辜的人...我每天都活在恐惧和自责中。"</p>
|
||||
<p>林克握住她的手,没有说话,只是静静听着。</p>
|
||||
<p>莫纳亨继续说:"当你救我出来的时候,我甚至不敢相信这是真的。我以为你是来杀我的,毕竟我做了那么多坏事..."</p>
|
||||
<p>"你没有做坏事。"林克打断她,"那些都是卡勒特逼你的,不是你的错。"</p>
|
||||
<p>莫纳亨看着他,眼中闪过感激:"你也是这么说的...从第一天开始,你就告诉我,我不需要为被迫做的事负责。你还说,我的力量可以用来保护别人,而不是伤害别人。"</p>
|
||||
<p>她深吸一口气:"是你让我重新找到了活下去的意义,林克。"</p>
|
||||
<p>林克转向她,看着她的眼睛:"莫纳亨..."</p>
|
||||
<p>"林克,我有话想对你说。"她打断他,眼神变得认真,"我...我喜欢你。"</p>
|
||||
<p>她的声音很轻,但每一个字都很清晰:"从你救我的那天开始,我就把你放在心里了。你是我遇到的第一个把我当人看的人,第一个愿意相信我的人,第一个...让我想要变强的人。"</p>
|
||||
<p>她低下头,声音变得更轻:"我知道,你可能已经有很多人喜欢了...我可能不是最特别的那个...但是...我还是想告诉你我的心意。"</p>
|
||||
<p>林克沉默了片刻。</p>
|
||||
<p>莫纳亨紧张地等待着他的回应,心脏跳得很快。她不知道自己为什么会这么紧张,明明已经做好了被拒绝的准备,但还是害怕听到那个答案。</p>
|
||||
<p>然后,她感觉到一只手轻轻抬起她的下巴。</p>
|
||||
<p>她抬起头,看到林克正温柔地看着她。</p>
|
||||
<p>"莫纳亨。"他说,"我也喜欢你。"</p>
|
||||
<p>莫纳亨愣住了:"真...真的?"</p>
|
||||
<p>"真的。"林克点头,"你善良、坚强、勇敢。你经历了那么多苦难,却依然保持着善良的心。我很欣赏你,也很喜欢你。"</p>
|
||||
<p>莫纳亨的眼眶湿润了,眼泪不自觉地滑落。她等这句话等了太久太久,久到她几乎以为自己永远听不到。</p>
|
||||
<p>"林克..."她轻声说,声音带着哽咽。</p>
|
||||
<p>林克伸手擦去她的眼泪:"傻瓜,哭什么。"</p>
|
||||
<p>莫纳亨破涕为笑:"我太开心了嘛..."</p>
|
||||
<p>然后,她主动凑过去,吻住了他的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>这是一个温柔的吻,带着等待已久的深情。</p>
|
||||
<p>夕阳的余晖洒在两人身上,为这个吻镀上了一层温暖的光芒。莫纳亨的双臂环住林克的脖子,身体紧紧贴着他。她的念动力不自觉地发动,让两人周围的物体都漂浮起来,形成一个浪漫的环绕。</p>
|
||||
<p>林克感觉到了周围的变化,但并没有在意。他的手轻轻搂住莫纳亨的腰,将她拥入怀中。</p>
|
||||
<p>吻了很久,两人才分开。莫纳亨的脸红得像晚霞,眼睛亮晶晶的。</p>
|
||||
<p>"抱歉..."她注意到周围漂浮的物体,有些不好意思,"我一激动,念动力就..."</p>
|
||||
<p>林克笑了:"没关系,挺浪漫的。"</p>
|
||||
<p>莫纳亨的脸更红了。她低下头,把脸埋在林克胸口。</p>
|
||||
<p>"林克..."她轻声说,声音带着羞涩,"今晚...我们可以不回去吗?"</p>
|
||||
<p>林克看着她,读懂了她眼中的期待。他伸手抚摸着她的银发,感受着她柔软的温度。</p>
|
||||
<p>"你想在这里?"他问。</p>
|
||||
<p>莫纳亨点头,眼神中带着一丝期待和紧张:"我想和你在一起...在这片重获新生的土地上...这里是我的新起点,也是..."</p>
|
||||
<p>她的声音越来越小:"也是我想和你开始新生活的地方..."</p>
|
||||
<p>林克没有说话,只是再次吻住了她。这一次的吻更加热烈,更加深入。莫纳亨发出一声轻哼,紧紧抱住了他。</p>
|
||||
<p>周围的物体在念动力的作用下缓缓降落,为两人留出一片私密的空间。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,星星出现在天空中。</p>
|
||||
<p>空地的角落里,两人依偎在一起。莫纳亨的头靠在林克胸口,手指在他的胸口画着圈。她的念动力时不时发动,让周围的萤火虫飞舞,为这个夜晚增添了几分梦幻的色彩。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我好幸福。"她的声音带着满足,"这是我第一次觉得...原来被爱是这么美好的事情。"</p>
|
||||
<p>林克搂紧了她:"以后会更美好的,莫纳亨。我会一直在你身边。"</p>
|
||||
<p>莫纳亨抬起头,看着他:"说话算数?"</p>
|
||||
<p>"算数。"</p>
|
||||
<p>她笑了,凑过去又吻了他一下。然后,她用念动力让一朵花飘到林克面前。</p>
|
||||
<p>"送给你。"她说,脸上带着羞涩的笑容。</p>
|
||||
<p>林克接过花,闻了闻:"很香。"</p>
|
||||
<p>莫纳亨开心地把头埋进他的胸口,享受着这份宁静和甜蜜。</p>
|
||||
<p>月光洒在两人身上,见证着这份新的爱情。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,两人并肩离开绿都。</p>
|
||||
<p>莫纳亨的脸上带着幸福的笑容,她紧紧握着林克的手,再也不愿放开。</p>
|
||||
<p>"林克。"她说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我想要变得更强。"她的眼神坚定,"强到可以保护你,保护我们。"</p>
|
||||
<p>林克看了她一眼,笑了:"好,那我们一起变强。"</p>
|
||||
<p>莫纳亨开心地笑了,把头靠在他的肩上。</p>
|
||||
<p>曾经,她以为自己的力量是诅咒。但现在,她知道这份力量可以用来保护最重要的人。</p>
|
||||
<p>绿都重新焕发了生机,而她的心,也因为爱情而重新燃烧。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十二章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·莫纳亨篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-121.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-123.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-92.html" class="sidebar-chapter ">第92章:安图恩攻坚战·黑色火山</a>
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter current">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(122)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,999 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与泽丁的天界巡逻 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 123</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>天界,皇都根特的城墙上。</p>
|
||||
<p>阳光从云层中穿透,洒在这座宏伟的城市上。远处的天空海呈现出淡淡的蓝色,仿佛一幅美丽的画卷。泽丁穿着守备队长的铠甲,站在城墙边缘,望着远处的风景。</p>
|
||||
<p>她的身姿挺拔而英武,金色的长发在风中飘动。铠甲上刻着天界的徽章,那是她作为守备队长的荣耀。她的腰间挂着长剑,手里握着巡逻的记录簿。</p>
|
||||
<p>林克走到她身边,两人并肩看着天界的风景。</p>
|
||||
<p>"好久没来天界了。"林克感慨道。</p>
|
||||
<p>自从上次卡勒特入侵之后,他已经很久没有回到这里了。那时候的根特满目疮痍,到处都是战火的痕迹。但现在,这座城市已经恢复了往日的繁华。</p>
|
||||
<p>"嗯。"泽丁点头,"最近皇都恢复了平静,一切都在变好。卡勒特的残党已经被清除,人民的生活也重新稳定下来。"</p>
|
||||
<p>她转向林克,眼中带着感激:"谢谢你...林克。谢谢你帮助我们。如果不是你,根特可能已经被卡勒特彻底占领了。"</p>
|
||||
<p>林克摇头:"我只是做了应该做的事。你们才是真正的英雄,在卡勒特的压迫下坚持抵抗,从未放弃。"</p>
|
||||
<p>泽丁笑了,有些不好意思:"我们只是做了必须做的事。保护家园,保护人民,这是守备队的职责。"</p>
|
||||
<p>她的目光变得深邃:"但有时候,真的很难坚持下去。看着战友一个个倒下,看着城市被敌人践踏...我曾经一度以为,我们再也夺不回根特了。"</p>
|
||||
<p>"但你没有放弃。"林克说。</p>
|
||||
<p>"因为有你。"泽丁认真地看着他,"当你带着冒险家们来到根特的时候,我看到了希望。你让我知道,我们不是孤军奋战,还有人愿意帮助我们。"</p>
|
||||
<p>她的声音变得轻柔:"是你给了我继续战斗的勇气。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,两人一起巡逻。</p>
|
||||
<p>泽丁带着林克走过城墙的每一个角落,介绍着皇都的变化。她的讲解详细而认真,每到一个地方都会讲述这里曾经发生的事情,以及现在的修复情况。</p>
|
||||
<p>"这里是曾经的粮仓。"她指着一座新建的建筑,"卡勒特入侵的时候,他们烧毁了所有的粮食,让人民陷入饥荒。现在,我们已经重新建立了粮仓,储备充足。"</p>
|
||||
<p>"这里是曾经的医院。"她指着另一座建筑,"那时候伤员太多,医院根本无法容纳。很多战友因为没有及时治疗而牺牲。现在,我们扩建了医院,增加了很多医护人员。"</p>
|
||||
<p>"这里是..."她停顿了一下,指着一块空地,"曾经是我的队长倒下的地方。"</p>
|
||||
<p>林克看向她,看到了她眼中的悲伤。</p>
|
||||
<p>泽丁深吸一口气:"卡勒特入侵的第一天,我的队长就牺牲了。他为了保护我,挡住了敌人的攻击...我看着他倒下,却什么都做不了。"</p>
|
||||
<p>她的声音变得哽咽:"他最后对我说的是..."泽丁,活下去,保护根特"。"</p>
|
||||
<p>林克伸手握住她的手,感受到她冰凉的温度。</p>
|
||||
<p>泽丁看着他,眼中闪过感激:"谢谢你,林克。谢谢你愿意听我说这些。"</p>
|
||||
<p>"你有权利回忆。"林克说,"那些逝去的战友,应该被记住。"</p>
|
||||
<p>泽丁点头,深吸一口气,继续说:"后来,我接替了队长的职位,带领守备队继续抵抗。那段时间真的很艰难,我们缺人、缺武器、缺补给...每一天都在生死边缘徘徊。"</p>
|
||||
<p>她的目光变得坚定:"但我没有放弃,因为我知道,队长在看着我。我不能辜负他的期望,不能辜负根特的人民。"</p>
|
||||
<p>林克看着她,眼中闪过赞赏:"你很坚强,泽丁。能在这种环境下坚持下来,很不容易。"</p>
|
||||
<p>泽丁苦笑:"坚强是被逼出来的。如果不够坚强,我早就倒下了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>巡逻结束后,两人来到了城墙上的一处高点。</p>
|
||||
<p>这里是根特最高的位置,可以看到整个城市的全景。远处的天空海呈现出淡淡的蓝色,近处的房屋整齐排列,街道上行人来来往往,一片繁荣的景象。</p>
|
||||
<p>"真美。"林克感慨道。</p>
|
||||
<p>"嗯。"泽丁点头,"这就是我们守护的城市。每一栋房屋,每一条街道,都是我们的心血。"</p>
|
||||
<p>她转向林克:"林克,我想问你一个问题。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>泽丁的目光变得认真:"你以后...还会来天界吗?"</p>
|
||||
<p>林克想了想:"如果有需要的话,我会来的。"</p>
|
||||
<p>泽丁的眼神有些失落:"只是有需要的时候吗?"</p>
|
||||
<p>林克看着她,读懂了她眼中的期待。</p>
|
||||
<p>"泽丁。"他说,"你是想让我经常来吗?"</p>
|
||||
<p>泽丁低下头,声音变得轻柔:"我...我只是想知道,你会不会想念这里。"</p>
|
||||
<p>林克走近一步,看着她的眼睛:"我会想念这里的。不只是这座城市,还有...这里的人。"</p>
|
||||
<p>泽丁抬起头,看着他:"包括我吗?"</p>
|
||||
<p>林克笑了:"当然包括你。"</p>
|
||||
<p>泽丁的心跳加速了。她看着林克的眼睛,看到了里面深深的温柔。</p>
|
||||
<p>"林克。"她轻声说,"我有话想对你说。"</p>
|
||||
<p>林克静静地看着她,等待着她的下一句话。</p>
|
||||
<p>泽丁深吸一口气,鼓起勇气说:"我...我喜欢你。"</p>
|
||||
<p>她的声音很轻,但每一个字都很清晰:"从你来到根特的那天开始,我就把你放在心里了。你是我遇到的第一个真正帮助我们的人,第一个让我看到希望的人,第一个...让我想要依靠的人。"</p>
|
||||
<p>她的眼睛湿润了:"我知道,你是阿拉德大陆的冒险家,你有很多事情要做,可能不会一直留在天界。但是...我还是想告诉你我的心意。"</p>
|
||||
<p>她低下头:"至少,让你知道,有人在天界等你。"</p>
|
||||
<p>林克沉默了片刻。</p>
|
||||
<p>泽丁紧张地等待着他的回应,心脏跳得很快。她不知道自己为什么会这么紧张,明明已经做好了被拒绝的准备。</p>
|
||||
<p>然后,她感觉到一只手轻轻握住她的手。</p>
|
||||
<p>她抬起头,看到林克正温柔地看着她。</p>
|
||||
<p>"泽丁。"他说,"我也喜欢你。"</p>
|
||||
<p>泽丁愣住了:"真...真的?"</p>
|
||||
<p>"真的。"林克点头,"你勇敢、坚强、负责。你为了守护家园付出了那么多,我很敬佩你,也很喜欢你。"</p>
|
||||
<p>泽丁的眼眶湿润了,眼泪不自觉地滑落。她等这句话等了太久太久。</p>
|
||||
<p>"林克..."她轻声说,声音带着哽咽。</p>
|
||||
<p>林克伸手擦去她的眼泪:"傻瓜,哭什么。"</p>
|
||||
<p>泽丁破涕为笑:"我太开心了嘛..."</p>
|
||||
<p>然后,她主动凑过去,吻住了他的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>这是一个温柔的吻,带着等待已久的深情。</p>
|
||||
<p>夕阳的余晖洒在两人身上,为这个吻镀上了一层金色的光芒。泽丁的双臂环住林克的脖子,身体紧紧贴着他。她的铠甲发出轻微的碰撞声,但这并不影响这份亲密。</p>
|
||||
<p>林克的手轻轻搂住她的腰,将她拥入怀中。</p>
|
||||
<p>吻了很久,两人才分开。泽丁的脸红得像晚霞,眼睛亮晶晶的。</p>
|
||||
<p>"林克..."她轻声说,声音带着羞涩,"今晚...你可以陪我在这里吗?"</p>
|
||||
<p>林克看着她,读懂了她眼中的期待。他伸手抚摸着她的脸颊,感受着她微热的温度。</p>
|
||||
<p>"你想在这里?"他问。</p>
|
||||
<p>泽丁点头,眼神中带着一丝期待和紧张:"我想和你一起看星星...在这座我守护的城市上..."</p>
|
||||
<p>她的声音变得轻柔:"这是我第一次...想要和别人分享这份宁静。"</p>
|
||||
<p>林克没有说话,只是再次吻住了她。这一次的吻更加热烈,更加深入。泽丁发出一声轻哼,紧紧抱住了他。</p>
|
||||
<p>夕阳慢慢沉入地平线,夜幕开始降临。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,星星出现在天空中。</p>
|
||||
<p>天界的星空比阿拉德大陆更加明亮,因为这里没有地面的遮挡,可以直接看到整个天穹。无数星星闪烁着,如同钻石洒在黑色的绸缎上。</p>
|
||||
<p>两人并肩坐在城墙的高点上,看着这美丽的星空。</p>
|
||||
<p>泽丁的头靠在林克胸口,手指在他的胸口画着圈。她的铠甲已经脱下,只穿着简单的衣物,更显出她的柔美。</p>
|
||||
<p>"好美。"她感慨道。</p>
|
||||
<p>"嗯。"林克同意。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"你知道吗,我曾经以为,自己一辈子都会孤独地守护这座城市。"她的声音带着回忆,"我的队长牺牲了,我的战友越来越少,我看不到希望...我以为,我的命运就是战斗到最后一刻,然后倒在这片土地上。"</p>
|
||||
<p>林克握住她的手,没有说话,只是静静听着。</p>
|
||||
<p>泽丁继续说:"但当你出现的时候,一切都变了。你给了我希望,给了我勇气,还给了我...爱情。"</p>
|
||||
<p>她转向林克,眼中满是温柔:"谢谢你,林克。谢谢你让我知道,守护者也可以被守护。"</p>
|
||||
<p>林克看着她,眼中闪过心疼:"泽丁,从今以后,我会守护你。"</p>
|
||||
<p>泽丁的眼眶湿润了:"真的?"</p>
|
||||
<p>"真的。"林克点头,"无论你在哪里,我都会守护你。"</p>
|
||||
<p>她笑了,凑过去吻了他。然后,她把头埋进他的胸口,享受着这份宁静和甜蜜。</p>
|
||||
<p>"林克..."她轻声说,声音带着羞涩。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我们可以...再靠近一点吗?"</p>
|
||||
<p>林克笑了:"你想怎样?"</p>
|
||||
<p>泽丁的脸红了,但还是勇敢地说:"我想和你...更亲密一点..."</p>
|
||||
<p>林克没有说话,只是将她拉入怀中,再次吻住了她。这一次的吻更加热烈,更加深入。</p>
|
||||
<p>泽丁的身体变得柔软,她紧紧抱住林克,感受着他的温度。</p>
|
||||
<p>月光洒在两人身上,见证着这份新的爱情。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,两人依偎在一起。</p>
|
||||
<p>泽丁的头靠在林克胸口,听着他的心跳声。她的身体有些疲惫,但心情无比满足。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我好幸福。"她的声音带着满足,"这是我第一次觉得,原来守护者也可以有依靠。"</p>
|
||||
<p>林克搂紧了她:"以后会更好的,泽丁。我会一直在你身边。"</p>
|
||||
<p>泽丁抬起头,看着他:"你什么时候会再来天界?"</p>
|
||||
<p>林克想了想:"很快。我会经常来的。"</p>
|
||||
<p>泽丁开心地笑了:"那我等你。"</p>
|
||||
<p>她再次把头埋进他的胸口,享受着这份宁静和甜蜜。</p>
|
||||
<p>星空依旧明亮,见证着这对恋人的甜蜜时光。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,两人并肩离开城墙。</p>
|
||||
<p>泽丁重新穿上铠甲,恢复了守备队长的威严。但她的脸上带着幸福的笑容,眼神中也多了几分柔和。</p>
|
||||
<p>"林克。"她说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"谢谢你...给我这份回忆。"她的声音很轻,但很真诚。</p>
|
||||
<p>林克握住她的手:"这只是开始,泽丁。以后我们会有更多的回忆。"</p>
|
||||
<p>泽丁开心地笑了,紧紧握着他的手。</p>
|
||||
<p>曾经,她以为自己的命运是孤独地守护这座城市。但现在,她知道,守护者也可以被守护。</p>
|
||||
<p>根特的城墙依旧坚固,而她的心,也因为爱情而变得更加坚强。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十三章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·泽丁篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-122.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-124.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-93.html" class="sidebar-chapter ">第93章:安图恩攻坚战·使徒陨落</a>
|
||||
<a href="chapter-94.html" class="sidebar-chapter ">第94章:克洛诺斯岛·寂静城的召唤</a>
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter current">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(123)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,993 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>番外·与皇女的皇家约会 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 125</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>皇女艾丽婕的行宫,天界最华丽的宫殿。</p>
|
||||
<p>金色的阳光洒在宫殿的琉璃瓦上,反射出耀眼的光芒。这座宫殿是天界皇族的专属居所,只有最高级别的贵族才能进入。而今天,林克作为皇女的特邀客人,被侍从引入这座华丽的殿堂。</p>
|
||||
<p>宫殿内部装饰得金碧辉煌。精美的壁画、华丽的吊灯、柔软的地毯...每一个细节都彰显着皇家的尊贵。侍从们恭敬地站在两侧,目光中带着好奇和敬意。</p>
|
||||
<p>林克走进宫殿深处,看到了等待他的身影。</p>
|
||||
<p>艾丽婕穿着华丽的礼服,银白色的长发梳理成优雅的样式,头上戴着皇冠。她的礼服是天界最顶级的丝绸制成,绣着精美的花纹,勾勒出她纤细而优美的身材。她的蓝色眼眸清澈如水,脸上带着期待的笑容。</p>
|
||||
<p>"林克,你来了。"她的声音温柔而高贵,带着明显的期待。</p>
|
||||
<p>林克微微躬身:"皇女殿下,感谢您的邀请。"</p>
|
||||
<p>艾丽婕笑了,走近他:"今天,不需要那么拘束。"她的声音轻柔,"今天...就我们两个。"</p>
|
||||
<p>林克看着她,眼中闪过温柔:"好的。"</p>
|
||||
<p>艾丽婕开心地笑了,伸手握住他的手:"走吧,我带你参观我的行宫。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人并肩走在宫殿中,艾丽婕带着林克参观每一个房间。</p>
|
||||
<p>"这是我的书房。"她指着一间装饰精美的房间,"我平时在这里处理政务,阅读文件。"</p>
|
||||
<p>林克看向书房,看到桌上堆满了文件和书籍。虽然房间很华丽,但透露出繁忙的气息。</p>
|
||||
<p>"你很辛苦。"林克感慨道。</p>
|
||||
<p>艾丽婕点头:"作为皇女,我有责任管理天界的事务。虽然很辛苦,但这是我的职责。"</p>
|
||||
<p>她的声音变得轻柔:"有时候,我会觉得很累。但想到天界的人民,想到那些在卡勒特入侵中牺牲的战士,我就知道我不能放弃。"</p>
|
||||
<p>林克看着她,眼中闪过心疼:"你承受了很多。"</p>
|
||||
<p>艾丽婕转向他:"但有你在,我就觉得不那么累了。"她的眼中带着温柔,"是你帮我们夺回了根特,是你帮助我们重建家园。你给了我希望和勇气。"</p>
|
||||
<p>林克握紧她的手:"我只是做了应该做的事。"</p>
|
||||
<p>"不。"艾丽婕认真地看着他,"你做的远比应该做的多。你不只是救了天界,还救了我。"</p>
|
||||
<p>她的声音变得深沉:"你知道吗,在卡勒特入侵的时候,我以为一切都结束了。我被困在皇宫里,看着自己的城市被敌人践踏,看着人民遭受苦难...我曾经一度失去了希望。"</p>
|
||||
<p>她的眼眶湿润了:"但当你出现的时候,一切都变了。你带着冒险家们闯入根特,一路击败卡勒特的军队。当我得知你打败了兰蒂卢斯的时候,我真的哭了。我终于看到了希望。"</p>
|
||||
<p>林克伸手擦去她眼角的泪痕:"不要再哭了。"</p>
|
||||
<p>艾丽婕破涕为笑:"对不起,我太激动了..."</p>
|
||||
<p>她深吸一口气,继续说:"是你让我重新找到了活下去的意义。林克,谢谢你。谢谢你救了我,救了天界。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>参观结束后,两人来到了皇家的花园。</p>
|
||||
<p>这里是天界最美的花园,种满了各色花卉。玫瑰、百合、兰花...每一种花都散发着迷人的芳香。花园的中心有一座喷泉,清澈的水流不断涌出,发出悦耳的声音。</p>
|
||||
<p>两人在花园里漫步,欣赏着美丽的风景。</p>
|
||||
<p>"真美。"林克感慨道。</p>
|
||||
<p>"嗯。"艾丽婕点头,"这是我最喜欢的地方。每次累了,我都会来这里散步。"</p>
|
||||
<p>她转向林克:"今天,我想和你分享这份宁静。"</p>
|
||||
<p>林克看着她,眼中闪过温柔:"我很荣幸。"</p>
|
||||
<p>艾丽婕笑了,走近喷泉。她伸出手,让水流从指尖滑过。银白色的长发在阳光下闪着柔和的光芒,礼服勾勒出她优美的曲线。</p>
|
||||
<p>林克站在她身后,看着这幅美丽的画面。</p>
|
||||
<p>艾丽婕转身,面向林克。她的蓝色眼眸清澈如水,脸上带着柔和的笑容。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"你知道吗,作为皇女,我有很多责任。"她的声音带着回忆,"我要管理天界的政务,要照顾人民的生活,要维护皇族的尊严...这些责任让我几乎没有属于自己的时间。"</p>
|
||||
<p>林克静静地听着。</p>
|
||||
<p>艾丽婕继续说:"但今天,我想放下这些责任。今天,我想只是作为一个普通的女孩,和你在一起。"</p>
|
||||
<p>她的眼中闪过期待:"林克,你愿意接受这样的我吗?"</p>
|
||||
<p>林克看着她,眼中闪过心疼:"我愿意。"</p>
|
||||
<p>艾丽婕开心地笑了,走近他,握住他的手。</p>
|
||||
<p>"谢谢你,林克。谢谢你愿意接受我。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人坐在花园的角落,看着夕阳。</p>
|
||||
<p>夕阳的余晖洒在两人身上,为花园镀上了一层金色的光芒。艾丽婕靠在林克肩上,身体放松,脸上带着幸福的笑容。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我有话想对你说。"她的声音变得认真,"我...我喜欢你。"</p>
|
||||
<p>林克转向她,看着她的眼睛。</p>
|
||||
<p>艾丽婕的眼神很认真,带着一丝紧张和期待:"从你救天界的那天开始,我就把你放在心里了。你是我遇到的第一个让我看到希望的人,第一个让我相信天界可以重建的人,第一个...让我想要依靠的人。"</p>
|
||||
<p>她低下头:"我知道,我是皇女,有很多责任和束缚。我不能像普通人一样自由地追求爱情...但是...我还是想告诉你我的心意。"</p>
|
||||
<p>她的声音变得轻柔:"至少,让你知道,有人在天界等你。有人愿意放下皇女的身份,只做一个普通女孩等你。"</p>
|
||||
<p>林克没有说话,只是静静地看着她。</p>
|
||||
<p>艾丽婕紧张地等待着他的回应,心脏跳得很快。她不知道自己为什么会这么紧张,明明已经做好了被拒绝的准备。毕竟她是皇女,有很多责任和束缚,林克可能不愿意接受这样的她。</p>
|
||||
<p>然后,她感觉到一只手轻轻抬起她的下巴。</p>
|
||||
<p>她抬起头,看到林克正温柔地看着她。</p>
|
||||
<p>"艾丽婕。"他说,"我也喜欢你。"</p>
|
||||
<p>艾丽婕愣住了:"真...真的?你不介意我的身份吗?"</p>
|
||||
<p>"不介意。"林克摇头,"你是皇女,但你也是一个普通的女孩。你有责任,但你也有追求幸福的权利。我很喜欢你,愿意接受你的一切。"</p>
|
||||
<p>艾丽婕的眼眶湿润了,眼泪不自觉地滑落。她等这句话等了太久太久。</p>
|
||||
<p>"林克..."她轻声说,声音带着哽咽。</p>
|
||||
<p>林克伸手擦去她的眼泪:"不要再哭了。"</p>
|
||||
<p>艾丽婕破涕为笑:"我忍不住嘛..."</p>
|
||||
<p>然后,她主动凑过去,吻住了他的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>这是一个温柔的吻,带着等待已久的深情。</p>
|
||||
<p>夕阳的余晖洒在两人身上,为这个吻镀上了一层金色的光芒。艾丽婕的双臂环住林克的脖子,身体紧紧贴着他。她的礼服发出轻微的摩擦声,但这并不影响这份亲密。</p>
|
||||
<p>林克的手轻轻搂住她的腰,将她拥入怀中。</p>
|
||||
<p>吻了很久,两人才分开。艾丽婕的脸红得像晚霞,眼睛亮晶晶的。</p>
|
||||
<p>"林克..."她轻声说,声音带着羞涩,"今晚...我们可以不回去吗?"</p>
|
||||
<p>林克看着她,读懂了她眼中的期待。他伸手抚摸着她的银发,感受着她柔软的温度。</p>
|
||||
<p>"你想在这里?"他问。</p>
|
||||
<p>艾丽婕点头,眼神中带着一丝期待和紧张:"我想和你在一起...在这片美丽的花园里..."</p>
|
||||
<p>她的声音变得轻柔:"这是我第一次...想要放下皇女的身份,只做一个普通的女孩和你在一起。"</p>
|
||||
<p>林克看着她,眼中闪过温柔:"艾丽婕,你确定吗?"</p>
|
||||
<p>艾丽婕认真地点头:"我确定。"她的声音很轻,但很坚定,"我想要和你...更亲密。"</p>
|
||||
<p>林克没有说话,只是再次吻住了她。这一次的吻更加热烈,更加深入。艾丽婕发出一声轻哼,紧紧抱住了他。</p>
|
||||
<p>夕阳慢慢沉入地平线,夜幕开始降临。花园的灯光亮起,为两人增添了几分浪漫的氛围。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜幕降临,星星出现在天空中。</p>
|
||||
<p>花园的角落里,两人依偎在一起。艾丽婕的头靠在林克胸口,手指在他的胸口画着圈。她的礼服已经有些凌乱,但这并不影响她的美丽。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我好幸福。"她的声音带着满足,"这是我第一次觉得,原来皇女也可以有属于自己的幸福。"</p>
|
||||
<p>林克搂紧了她:"以后会更幸福的,艾丽婕。我会一直在你身边。"</p>
|
||||
<p>艾丽婕抬起头,看着他:"真的吗?你不会离开我吗?"</p>
|
||||
<p>"不会。"林克认真地说,"我会一直陪伴你。"</p>
|
||||
<p>艾丽婕开心地笑了,再次吻了他。然后,她把头埋进他的胸口,享受着这份宁静和甜蜜。</p>
|
||||
<p>"林克。"她轻声说,声音带着羞涩。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"我希望...我们能经常见面。"她的眼神带着期待,"即使我有责任,即使我很忙...但我还是想和你在一起。"</p>
|
||||
<p>林克看了她一眼,笑了:"好,我会经常来天界的。"</p>
|
||||
<p>艾丽婕开心地笑了,把头靠在他的肩上。</p>
|
||||
<p>月光洒在两人身上,见证着这份新的爱情。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深夜,两人依偎在一起。</p>
|
||||
<p>艾丽婕的头靠在林克胸口,听着他的心跳声。她的身体有些疲惫,但心情无比满足。</p>
|
||||
<p>"林克。"她轻声说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"谢谢你...给我这份回忆。"她的声音很轻,但很真诚,"这是我第一次,真正放下皇女的身份,做一个普通的女孩。"</p>
|
||||
<p>林克搂紧了她:"这只是开始,艾丽婕。以后我们会有更多的回忆。"</p>
|
||||
<p>艾丽婕开心地笑了,紧紧抱住他。</p>
|
||||
<p>曾经,她以为自己的命运只是皇女的责任,没有属于自己的幸福。但现在,她知道,皇女也可以追求爱情,责任和幸福可以共存。</p>
|
||||
<p>花园的灯光依旧明亮,见证着这对恋人的甜蜜时光。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,两人并肩离开花园。</p>
|
||||
<p>艾丽婕重新整理好礼服,恢复了皇女的姿态。但她的脸上带着幸福的笑容,眼神中也多了几分柔和。</p>
|
||||
<p>"林克。"她说。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"谢谢你...给我这份回忆。"她的声音很轻,但很真诚。</p>
|
||||
<p>林克握住她的手:"这只是开始,艾丽婕。以后我们会有更多的回忆。"</p>
|
||||
<p>艾丽婕开心地笑了,紧紧握着他的手。</p>
|
||||
<p>曾经,她以为皇女的身份是束缚。但现在,她知道,身份不是障碍,责任和爱情可以共存。</p>
|
||||
<p>她的心中有了希望,有了勇气,也有了最重要的那个人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十五章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(番外·皇女篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-124.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-126.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-95.html" class="sidebar-chapter ">第95章:寂静城的秘密</a>
|
||||
<a href="chapter-96.html" class="sidebar-chapter ">第96章:番外·贝奇的献身</a>
|
||||
<a href="chapter-97.html" class="sidebar-chapter ">第97章:光之舞会</a>
|
||||
<a href="chapter-98.html" class="sidebar-chapter ">第98章:钢铁之臂</a>
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter current">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(125)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,970 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>魔界的召唤 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 129</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>清晨的阳光透过窗帘洒进房间,林克被一阵轻轻的敲门声唤醒。</p>
|
||||
<p>"林克哥哥,有你的信!"敏泰的声音从门外传来。</p>
|
||||
<p>林克起身开门,敏泰递给他一封紫色信封。信封上没有寄信人的名字,只有一个熟悉的印记——艾丽丝的占卜牌花纹。</p>
|
||||
<p>"艾丽丝..."林克心中一震。</p>
|
||||
<p>他拆开信封,展开信纸。熟悉的字迹映入眼帘:</p>
|
||||
<p>"林克:</p>
|
||||
<p>我到魔界了。</p>
|
||||
<p>三个月的赎罪之路比想象中更艰难,但也让我看到了很多东西。我在魔界营地帮助那些被赫尔德伤害的人,每一天都在弥补过去的过错。</p>
|
||||
<p>但我知道,我的罪还没有赎清。还需要更多时间。</p>
|
||||
<p>不过,我想见你。</p>
|
||||
<p>如果可以的话,来魔界找我。我在魔界营地等你。</p>
|
||||
<p>艾丽丝"</p>
|
||||
<p>林克握着信纸,心中涌起复杂的情绪。三个月了,艾丽丝一直在魔界独自赎罪...</p>
|
||||
<p>"林克哥哥,怎么了?"敏泰看到他的表情,关切地问道。</p>
|
||||
<p>"艾丽丝...在魔界。"林克轻声说,"她让我去找她。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐时,林克将艾丽丝的信告诉了后宫们。</p>
|
||||
<p>赛丽亚听完,轻轻点头:"你应该去。"</p>
|
||||
<p>"我也觉得。"帕丽丝说道,"艾丽丝姐姐一个人在魔界,太孤单了。"</p>
|
||||
<p>"但魔界很危险。"莎兰皱眉,"赫尔德的大本营就在那里,你去会有危险。"</p>
|
||||
<p>"我必须去。"林克说道,"艾丽丝是我的人,我不能让她一个人承受。"</p>
|
||||
<p>他看向后宫们:"但我需要你们在这里,帮我守护阿拉德大陆。"</p>
|
||||
<p>"当然。"赛丽亚握住他的手,"我们会等你回来。"</p>
|
||||
<p>其他少女也纷纷点头,虽然眼中满是不舍,但都表示理解。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下午,林克来到寂静城。</p>
|
||||
<p>卢克坐在古老能量核心旁边,看到林克,脸上露出微笑:"年轻人,我猜你要来找我。"</p>
|
||||
<p>"卢克爷爷。"林克在他身边坐下,"我想去魔界。"</p>
|
||||
<p>"因为艾丽丝?"</p>
|
||||
<p>"是的。"</p>
|
||||
<p>卢克沉默了片刻,然后说道:"魔界...是一个危险的地方。赫尔德的势力在那里根深蒂固,你去了可能会遇到很多麻烦。"</p>
|
||||
<p>"我知道。"林克点头,"但我必须去。"</p>
|
||||
<p>卢克看着他,浑浊的眼睛中闪过一丝欣慰:"你是一个重情重义的人。海伯伦星的王,欣赏你。"</p>
|
||||
<p>他缓缓站起身,走到控制台前:"寂静城本来就在魔界。我可以帮你开启返回魔界的通道。"</p>
|
||||
<p>"真的?"</p>
|
||||
<p>"是的。"卢克点头,"但我只能送你到魔界的地轨中心。从那里到魔界营地,你需要自己走。"</p>
|
||||
<p>他在控制台上输入了一串符文,整个寂静城开始轻微震动。</p>
|
||||
<p>"通道会在一小时内开启。"卢克说道,"准备一下吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克回到赛丽亚旅馆,开始收拾行装。</p>
|
||||
<p>敏泰帮他整理衣物,眼中满是不舍:"林克哥哥,你一定要平安回来。"</p>
|
||||
<p>"我会的。"林克轻轻揉了揉她的头发。</p>
|
||||
<p>帕丽丝递给他几瓶药剂:"这是解毒剂和恢复药,你带着。"</p>
|
||||
<p>"谢谢。"</p>
|
||||
<p>莎兰给了他一块水晶:"这是魔法通讯石,如果遇到危险,可以用它联系我们。"</p>
|
||||
<p>奥菲利亚、莫纳亨、泽丁、马琳、皇女艾丽婕、米娅、贝奇、艾泽拉...每个人都送上了自己的祝福和礼物。</p>
|
||||
<p>最后,赛丽亚走到他面前,轻轻吻了他的唇。</p>
|
||||
<p>"等你回来。"她轻声说。</p>
|
||||
<p>"嗯。"林克紧紧抱住她,"我会的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>告别后宫们,林克回到寂静城。</p>
|
||||
<p>卢克站在一扇巨大的门前——那是一扇由金色符文构成的传送门,门内闪烁着神秘的光芒。</p>
|
||||
<p>"准备好了吗?"卢克问道。</p>
|
||||
<p>"准备好了。"林克点头。</p>
|
||||
<p>卢克伸手在他肩上拍了拍:"年轻人,魔界和阿拉德大陆不同。那里的规则更加残酷,力量才是生存的根本。你要小心。"</p>
|
||||
<p>"我会的。"</p>
|
||||
<p>"还有..."卢克看着他,浑浊的眼睛中带着一丝期待,"如果你在魔界找到了对抗赫尔德的方法...请告诉我们。海伯伦星的王,也想看到那个女人倒台。"</p>
|
||||
<p>林克郑重地点头:"我一定会。"</p>
|
||||
<p>他深吸一口气,踏入传送门。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的光芒瞬间将他包围,他感到身体在飞速移动,周围的一切都变得模糊。</p>
|
||||
<p>当他再次睁开眼睛时,发现自己站在一个陌生的平台上。</p>
|
||||
<p>这里的天空是暗紫色的,没有太阳,只有漂浮的能量球散发微弱的光芒。空气中弥漫着一股古老而压抑的气息,让人感到呼吸困难。</p>
|
||||
<p>"这就是...魔界..."</p>
|
||||
<p>林克环顾四周,远处是一座座奇异的建筑——有的悬浮在空中,有的建造在悬崖边缘。紫色的能量流在建筑之间穿梭,仿佛一条条血管。</p>
|
||||
<p>他低头看了看手中的地图——艾丽丝给的坐标显示,魔界营地在地轨中心的东南方向,大约半天的路程。</p>
|
||||
<p>"艾丽丝...等着我..."</p>
|
||||
<p>林克握紧细雪之舞,朝东南方向走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约一个时辰,林克开始感受到魔界的异常。</p>
|
||||
<p>这里的空间似乎在扭曲,有时候走直线却会突然转向。空气中弥漫的能量也让他感到不适——那是一种混合了无数使徒力量的混乱气息。</p>
|
||||
<p>"赫尔德的气息..."林克皱眉。</p>
|
||||
<p>突然,前方传来一阵打斗声。</p>
|
||||
<p>林克警觉地握紧光剑,悄悄靠近。</p>
|
||||
<p>在一座废弃的建筑旁,他看到了一群身穿黑色铠甲的士兵正在围攻一个身影。那是一个年轻的女人,手持法杖,正在艰难地抵抗。</p>
|
||||
<p>"是魔界的冒险家?"</p>
|
||||
<p>林克正要上前帮忙,那女人突然回头,看到了他。</p>
|
||||
<p>"快跑!"她大喊,"他们是赫尔德的爪牙!"</p>
|
||||
<p>林克没有退缩,而是拔出细雪之舞,冲了上去。</p>
|
||||
<p>"极·鬼剑术!"</p>
|
||||
<p>冰蓝色的剑气瞬间斩倒了三个士兵。其他士兵见状,纷纷后退。</p>
|
||||
<p>"你是谁?!"领头的士兵警惕地看着林克。</p>
|
||||
<p>"路过的剑士。"林克冷声说道,"想找死就继续。"</p>
|
||||
<p>士兵们对视一眼,然后转身逃跑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束后,林克走到女人面前。</p>
|
||||
<p>"你没事吧?"</p>
|
||||
<p>"我没事...谢谢你。"女人喘着气,"我是尼梅尔,魔界营地的冒险家。你...你是从阿拉德大陆来的?"</p>
|
||||
<p>"是的。"林克点头,"我叫林克。我在找人。"</p>
|
||||
<p>"找谁?"</p>
|
||||
<p>"艾丽丝。"林克说道,"她应该在魔界营地。"</p>
|
||||
<p>尼梅尔愣了一下,然后眼中闪过惊喜:"艾丽丝姐姐?你认识她?"</p>
|
||||
<p>"她是我的..."林克顿了顿,"重要的人。"</p>
|
||||
<p>尼梅尔笑了:"那我带你去!艾丽丝姐姐经常提起你,她一定会很高兴的!"</p>
|
||||
<p>两人朝着魔界营地的方向走去,远处,紫色的天空下,一座由废墟组成的营地逐渐显现。</p>
|
||||
<p>艾丽丝,我来了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百二十九章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-128.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-130.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-99.html" class="sidebar-chapter ">第99章:能源熔炉</a>
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter current">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(129)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,925 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>龙人之塔 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 13</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>踏入传送阵的瞬间,林克感觉身体被一股柔和的力量托起。</p>
|
||||
<p>眼前的景象快速变化——西海岸的街道消失了,取而代之的是一片云海。当他们再次睁开眼睛时,已经来到了一片完全陌生的天地。</p>
|
||||
<p>这里是一座巨大的石塔,塔身由白色的石材建成,在阳光的照射下泛着柔和的光芒。塔的四周是无尽的云海,偶尔能看到其他浮空建筑的轮廓。</p>
|
||||
<p>"这就是……天空之城?"赛丽亚惊叹道,"好壮观……"</p>
|
||||
<p>"小心,有东西来了!"林克拔出光剑晨曦,警惕地看着前方。</p>
|
||||
<p>从石塔的拐角处,走出几只怪物。</p>
|
||||
<p>它们有着人类的身形,但头部却是龙的样子,浑身覆盖着青色的鳞片,手中握着长枪。</p>
|
||||
<p>"龙人!"林克认出了这些怪物。莎兰提到过,它们是天空之城的守卫。</p>
|
||||
<p>龙人们发出尖锐的嘶叫,挥舞着长枪冲了过来!</p>
|
||||
<p>"来了!"林克握紧光剑,准备迎战。</p>
|
||||
<p>但GSD却轻轻抬起了手。</p>
|
||||
<p>"让我来吧。"他说,"你们看着就行。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>龙人们冲到了GSD面前,长枪齐齐刺出!</p>
|
||||
<p>但GSD连拐杖都没用。</p>
|
||||
<p>他只是轻轻抬起右手,一道无形的波动从他掌心扩散开来。</p>
|
||||
<p>"波动·地裂。"</p>
|
||||
<p>"轰——!!!"</p>
|
||||
<p>整个地面瞬间崩裂,强大的冲击波将十几只龙人全部掀飞!它们在空中翻滚着,重重撞在石塔的墙壁上,化作一团团血雾。</p>
|
||||
<p>一击……全灭?</p>
|
||||
<p>林克和赛丽亚瞪大了眼睛,难以置信地看着这一幕。</p>
|
||||
<p>"师父……您这也太强了吧?"林克咽了口唾沫。</p>
|
||||
<p>"这只是基础。"GSD收回手,淡淡地说,"走吧,前面还有更多。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一路上,GSD展现出了让林克瞠目结舌的实力。</p>
|
||||
<p>遇到龙人围攻,他只是随手一挥,波动剑气就将它们全部斩杀。</p>
|
||||
<p>遇到飞行怪物,他连头都不抬,一道向上的波动斩就将它们切成两半。</p>
|
||||
<p>遇到陷阱,他像是提前知道一样,总能带着两人轻松避开。</p>
|
||||
<p>"师父,您明明看不见……"林克忍不住问,"为什么能像看得见一样?"</p>
|
||||
<p>"心眼。"GSD说,"放弃双眼,用心感受世界。这是阿修罗的修炼方式,但作为剑魂,也可以借鉴。"</p>
|
||||
<p>"心眼……"</p>
|
||||
<p>"你体内的鬼手,其实也是一种感知方式。"GSD解释道,"只是你一直太依赖眼睛,没有好好利用它。"</p>
|
||||
<p>林克若有所思。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当他们来到龙人之塔的中层时,龙人首领终于出现了。</p>
|
||||
<p>那是一只身高超过三米的巨大龙人,浑身覆盖着金色的鳞片,手中握着一把巨大的龙枪。</p>
|
||||
<p>它的眼中燃烧着愤怒的火焰,看到GSD后,竟然露出了一丝恐惧。</p>
|
||||
<p>"你……你是当年的那个瞎子……"龙人首领的声音有些颤抖。</p>
|
||||
<p>"你认识我?"GSD微微侧头。</p>
|
||||
<p>"二十年前……你一个人闯到了天空之海深海……"龙人首领后退了一步,"连赛格哈特大人都没有拦住你……"</p>
|
||||
<p>"哦,我记起来了。"GSD点点头,"那时候的你,还只是个小家伙。"</p>
|
||||
<p>龙人首领怒吼一声,举起龙枪冲向GSD!</p>
|
||||
<p>"去死吧,瞎子!"</p>
|
||||
<p>GSD叹了口气。</p>
|
||||
<p>"这么多年了,天空之城的怪物还是这么不长进。"</p>
|
||||
<p>他抬起手,没有任何蓄力,一道巨大的波动剑气凭空出现!</p>
|
||||
<p>"波动·爆炎。"</p>
|
||||
<p>"轰——!!!"</p>
|
||||
<p>剑气瞬间吞噬了龙人首领,将它连带着身后的一片石塔墙壁一起摧毁!</p>
|
||||
<p>当烟尘散去时,龙人首领已经消失不见,只留下一地金色的鳞片。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克站在原地,久久说不出话来。</p>
|
||||
<p>这就是GSD的真正实力?</p>
|
||||
<p>一剑……就把那么强大的龙人首领秒杀了?</p>
|
||||
<p>"师父……"林克的声音有些干涩,"您到底有多强?"</p>
|
||||
<p>GSD收起手,淡淡地说:"我只是一个瞎了眼的老头子而已。"</p>
|
||||
<p>"您太谦虚了……"</p>
|
||||
<p>"不,我说的是真的。"GSD转身看向林克,"真正的强者,不是看谁的力量更大,而是看谁能更好地运用自己的力量。"</p>
|
||||
<p>"你的剑魂之路还很长。等你什么时候能理解这句话,你就离真正的强者不远了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开龙人之塔时,GSD将一枚金色的鳞片交给了林克。</p>
|
||||
<p>"龙人首领的鳞片,可以用来强化你的武器。"他说,"特别是光剑晨曦,它和龙族的力量有着某种共鸣。"</p>
|
||||
<p>林克接过鳞片,郑重地点头。</p>
|
||||
<p>"谢谢师父。"</p>
|
||||
<p>"不用谢。"GSD转身向传送阵走去,"人偶玄关在上一层,那里的敌人比龙人更危险。你们先休整一下,明天继续。"</p>
|
||||
<p>"您还要带我们?"赛丽亚惊喜地问。</p>
|
||||
<p>"嗯。"GSD头也不回,"既然来了,就把你们送到安全的地方再说。"</p>
|
||||
<p>林克看着GSD的背影,心中涌起一股暖流。</p>
|
||||
<p>这个看似冷漠的老人,其实一直在用自己的方式保护着他们。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第十三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-12.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-14.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter ">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter ">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter ">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter ">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter ">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter ">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter ">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter ">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter ">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter ">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter ">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter ">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter current">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter ">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter ">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter ">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter ">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter ">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter ">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter ">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter ">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter ">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter ">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter ">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter ">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter ">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter ">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter ">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter ">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter ">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter ">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter ">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter ">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter ">第34章:暗精灵墓地·剩余三将军</a>
|
||||
<a href="chapter-35.html" class="sidebar-chapter ">第35章:邪龙斯皮兹</a>
|
||||
<a href="chapter-36.html" class="sidebar-chapter ">第36章:莎兰的探望</a>
|
||||
<a href="chapter-37.html" class="sidebar-chapter ">第37章:暗影迷宫·影子剑士</a>
|
||||
<a href="chapter-38.html" class="sidebar-chapter ">第38章:熔岩穴·泰坦之怒</a>
|
||||
<a href="chapter-39.html" class="sidebar-chapter ">第39章:暗黑城入口·无头骑士</a>
|
||||
<a href="chapter-40.html" class="sidebar-chapter ">第40章:万年雪山·冰心少年</a>
|
||||
<a href="chapter-41.html" class="sidebar-chapter ">第41章:敏泰的加入</a>
|
||||
<a href="chapter-42.html" class="sidebar-chapter ">第42章:山脊·野兽师</a>
|
||||
<a href="chapter-43.html" class="sidebar-chapter ">第43章:番外·雪山温泉</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(13)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,970 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>魔界营地 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 130</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>魔界营地坐落在地轨中心的东南角,是一片由废墟构成的避难所。</p>
|
||||
<p>林克跟着尼梅尔走过崎岖的道路,眼前的景象逐渐清晰——残破的建筑被改造成了临时的住所,街道上行人稀少,每个人脸上都带着疲惫和警惕。</p>
|
||||
<p>"这里就是魔界营地。"尼梅尔介绍道,"是被赫尔德伤害的人聚集的地方。有被使徒力量侵蚀的幸存者,有被驱逐的魔界人,还有一些像我一样的冒险家。"</p>
|
||||
<p>"赫尔德...伤害了这么多人?"林克皱眉。</p>
|
||||
<p>"是的。"尼梅尔点头,"她的『创新世纪』计划需要大量能量,而能量的来源就是使徒死亡时释放的力量。为了收集能量,她不惜牺牲无数生命。"</p>
|
||||
<p>她指向远处一座破旧的教堂:"艾丽丝姐姐就住在那边。她来这里三个月,已经帮助了很多人。"</p>
|
||||
<p>林克加快脚步,朝着教堂走去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>教堂内部比外面看起来更加简陋。</p>
|
||||
<p>几张破旧的桌椅,一些简单的医疗用品,还有几个躺在担架上的人。空气中弥漫着草药的味道,还有一丝若有若无的血腥气。</p>
|
||||
<p>"艾丽丝姐姐在后面。"尼梅尔轻声说,"我去外面守着,你们慢慢聊。"</p>
|
||||
<p>林克点了点头,穿过教堂,来到后方的小院。</p>
|
||||
<p>那里有一个小小的菜园,种着一些不知名的植物。一个紫发的身影正蹲在地上,认真地给植物浇水。</p>
|
||||
<p>"艾丽丝..."</p>
|
||||
<p>那身影猛地转过身,紫色的眼睛睁大,满是惊喜。</p>
|
||||
<p>"林克?!"</p>
|
||||
<p>她放下水壶,快步走向林克,眼眶瞬间红了。</p>
|
||||
<p>"你真的来了..."</p>
|
||||
<p>"我收到你的信。"林克伸出手,轻轻擦去她眼角的泪水,"你瘦了。"</p>
|
||||
<p>艾丽丝笑了,但眼泪还是滑落:"魔界的食物不好吃...而且我也没什么胃口。"</p>
|
||||
<p>"为什么不照顾好自己?"</p>
|
||||
<p>"因为...因为我要赎罪。"艾丽丝低下头,"我做了太多错事,伤害了太多人...如果不弥补,我没脸见你。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>他看着眼前这个女人,心中涌起复杂的情绪。她曾经是赫尔德的傀儡,伤害了无数人。但那不是她的错。</p>
|
||||
<p>"艾丽丝。"他轻声说,"看着我。"</p>
|
||||
<p>艾丽丝抬起头。</p>
|
||||
<p>"那不是你的错。"林克认真地说,"你是被控制的,你没有选择。"</p>
|
||||
<p>"但...但我亲手做了那些事..."</p>
|
||||
<p>"所以你来赎罪。"林克握住她的手,"你已经付出了代价。三个月,你在这里帮助别人,弥补过去的过错。这还不够吗?"</p>
|
||||
<p>艾丽丝的眼泪流得更凶了:"我不知道...我不知道要多久才能原谅自己..."</p>
|
||||
<p>林克将她拥入怀中,轻声说道:"那就让我帮你。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"我陪你一起赎罪。"林克说,"不管需要多久,我都陪着你。"</p>
|
||||
<p>艾丽丝抬起头,看着他坚定的眼神,心中某个柔软的地方被触动了。</p>
|
||||
<p>"林克..."</p>
|
||||
<p>"你是我的人。"林克轻声说,"我不会让你一个人承受。"</p>
|
||||
<p>他低下头,轻轻吻住了她的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,两人坐在小院的台阶上,看着紫色的天空。</p>
|
||||
<p>"这三个月,你都在做什么?"林克问道。</p>
|
||||
<p>"帮助那些被赫尔德伤害的人。"艾丽丝轻声说,"有些被使徒力量侵蚀,有些被魔法诅咒,还有些失去了家人...我用我的魔法帮助他们,尽我所能。"</p>
|
||||
<p>"辛苦吗?"</p>
|
||||
<p>"辛苦。"艾丽丝点头,"但看到他们恢复,我觉得自己至少做了一些有用的事。"</p>
|
||||
<p>她看向林克:"你呢?阿拉德大陆怎么样?"</p>
|
||||
<p>"都好。"林克微笑道,"赛丽亚、敏泰、帕丽丝、莎兰...她们都很想你。"</p>
|
||||
<p>艾丽丝的眼中闪过一丝温暖:"我也想她们。"</p>
|
||||
<p>"等你赎罪完成,我们一起回去。"</p>
|
||||
<p>"嗯。"艾丽丝点头,"但还需要时间...赫尔德在这里还有很多受害者,我想帮助他们。"</p>
|
||||
<p>"我陪你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>这时,尼梅尔从外面跑进来。</p>
|
||||
<p>"艾丽丝姐姐!不好了!"</p>
|
||||
<p>"怎么了?"艾丽丝站起来。</p>
|
||||
<p>"有一群赫尔德的爪牙在营地外面游荡,可能是发现林克了!"</p>
|
||||
<p>林克站起身,握紧细雪之舞:"我去解决。"</p>
|
||||
<p>"我和你一起去!"艾丽丝举起法杖。</p>
|
||||
<p>"我也去!"尼梅尔也站了出来。</p>
|
||||
<p>三人走出教堂,来到营地边缘。</p>
|
||||
<p>果然,十几个身穿黑色铠甲的士兵正在营地外徘徊。看到林克,他们立刻围了上来。</p>
|
||||
<p>"就是他!从阿拉德大陆来的剑士!"</p>
|
||||
<p>"抓住他!赫尔德大人会重赏!"</p>
|
||||
<p>林克冷笑:"想抓我?来试试。"</p>
|
||||
<p>他拔出细雪之舞,冰蓝色的光芒在紫色的天空下格外耀眼。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>赫尔德的爪牙虽然数量众多,但实力并不强。林克的剑气所向披靡,艾丽丝的魔法从旁协助,尼梅尔也挥舞着短剑加入战斗。</p>
|
||||
<p>"极·鬼剑术!"</p>
|
||||
<p>冰蓝色的剑气横扫而出,将数个士兵击倒。艾丽丝的元素魔法紧随其后,火球和冰锥精准地命中敌人的要害。</p>
|
||||
<p>尼梅尔看着两人默契的配合,心中暗暗羡慕。</p>
|
||||
<p>"好厉害...他们真的很般配..."</p>
|
||||
<p>她咬了咬牙,也冲了上去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗很快就结束了。</p>
|
||||
<p>赫尔德的爪牙要么被击败,要么逃走。营地恢复了平静。</p>
|
||||
<p>"谢谢你们!"营地的人们纷纷走出来,向林克和艾丽丝道谢。</p>
|
||||
<p>林克收起光剑,看向艾丽丝:"你经常遇到这种情况?"</p>
|
||||
<p>"偶尔。"艾丽丝点头,"赫尔德的眼线遍布魔界,她的爪牙时不时会来骚扰营地。"</p>
|
||||
<p>"那以后我来保护营地。"林克说。</p>
|
||||
<p>艾丽丝看着他,眼中满是感动:"林克...谢谢你..."</p>
|
||||
<p>尼梅尔在一旁看着两人,心中涌起一股异样的感觉。</p>
|
||||
<p>"艾丽丝姐姐真的很幸福..."她想,"有一个愿意为她来到魔界的人..."</p>
|
||||
<p>她看向林克的背影,脸微微泛红。</p>
|
||||
<p>"林克...真的很厉害..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,林克在教堂旁边的小房间里休息。</p>
|
||||
<p>艾丽丝为他准备了简单的晚餐,虽然不好吃,但林克还是全部吃光了。</p>
|
||||
<p>"明天,我带你在营地转转。"艾丽丝说,"有些地方你需要了解。"</p>
|
||||
<p>"好。"</p>
|
||||
<p>"还有..."艾丽丝犹豫了一下,"我想带你去见一个人。"</p>
|
||||
<p>"谁?"</p>
|
||||
<p>"凯蒂。"艾丽丝说,"她是营地最好的魔法师,也是...我的朋友。她知道很多关于赫尔德的事。"</p>
|
||||
<p>林克点头:"好。"</p>
|
||||
<p>艾丽丝看着他,眼中闪着温柔的光芒。</p>
|
||||
<p>"林克...能再陪我一会儿吗?"</p>
|
||||
<p>林克伸出手,将她拉入怀中:"当然。"</p>
|
||||
<p>两人在紫色的月光下相拥,享受着难得的宁静时光。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-129.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-131.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-100.html" class="sidebar-chapter ">第100章:王之书库</a>
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter current">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(130)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,995 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>凯蒂的指引 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 131</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>清晨,紫色的天空依然没有变化。</p>
|
||||
<p>林克走出教堂,艾丽丝已经在外面等着了。她穿着简单的长袍,法杖握在手中,紫色的长发在微风中轻轻飘动。</p>
|
||||
<p>"早安。"艾丽丝微笑道。</p>
|
||||
<p>"早安。"林克走到她身边,"今天要见凯蒂?"</p>
|
||||
<p>"是的。"艾丽丝点头,"她住在营地东侧,我带你去。"</p>
|
||||
<p>尼梅尔也跑了过来:"我也去!我想听听凯蒂姐姐讲赫尔德的事!"</p>
|
||||
<p>艾丽丝看了看林克,见他点头,便说:"好,一起走吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人沿着营地的街道向东走去。</p>
|
||||
<p>林克边走边观察周围的环境——残破的建筑被改造成住所,街道上行人稀少,大多是老人和伤者。偶尔有几个冒险家走过,脸上都带着警惕和疲惫。</p>
|
||||
<p>"魔界营地有多少人?"林克问道。</p>
|
||||
<p>"大约三百多人。"艾丽丝回答,"大多是赫尔德计划的受害者,有些被使徒力量侵蚀,有些失去了家园,还有些是被驱逐的魔界人。"</p>
|
||||
<p>"三百多人..."林克皱眉,"赫尔德伤害了这么多人?"</p>
|
||||
<p>"这只是冰山一角。"艾丽丝轻声说,"在整个魔界,被她伤害的人不计其数。"</p>
|
||||
<p>尼梅尔在一旁补充:"凯蒂姐姐说,赫尔德的计划需要大量能量,而能量的来源就是使徒死亡时释放的力量。为了收集能量,她不惜牺牲无数生命。"</p>
|
||||
<p>林克握紧拳头,眼中闪过一丝冷意。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>正走着,前方突然传来一阵尖叫。</p>
|
||||
<p>"救命!有怪物!"</p>
|
||||
<p>林克立刻拔出细雪之舞,朝声音传来的方向冲去。</p>
|
||||
<p>转过一个街角,他看到一群黑色的蝙蝠正在围攻一个老人。那些蝙蝠体型硕大,眼睛泛着红光,口中露出尖锐的獠牙。</p>
|
||||
<p>"魔界蝙蝠!"尼梅尔喊道,"它们会吸血!"</p>
|
||||
<p>林克没有犹豫,直接冲入蝙蝠群中。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>他的身影瞬间变得模糊,进入流心状态。紧接着,光剑划出一道冰蓝色的弧线。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他腾空而起,剑气从空中劈下,瞬间斩落了五六只蝙蝠。剩余的蝙蝠尖叫着四散而逃。</p>
|
||||
<p>"没事吧?"林克走到老人面前。</p>
|
||||
<p>"没...没事..."老人颤抖着说,"谢谢你,年轻人..."</p>
|
||||
<p>艾丽丝和尼梅尔也赶到了。</p>
|
||||
<p>"这些蝙蝠最近越来越多了。"艾丽丝皱眉,"可能是赫尔德的爪牙在附近活动,惊扰了它们。"</p>
|
||||
<p>林克收起光剑:"走吧,别让凯蒂久等。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>凯蒂的住所是一栋半塌的建筑,但内部被魔法加固过,显得十分坚固。</p>
|
||||
<p>门口站着两个年轻的女魔法师,看到艾丽丝,立刻行礼:"艾丽丝大人!"</p>
|
||||
<p>"凯蒂在里面吗?"艾丽丝问道。</p>
|
||||
<p>"在的,请进。"</p>
|
||||
<p>三人走进建筑,穿过一条走廊,来到一间宽敞的房间。</p>
|
||||
<p>房间里摆满了书籍和魔法道具,墙上挂着各种符文和地图。一个中年女人坐在书桌前,正在翻阅一本古老的典籍。她有着灰白色的短发,眼神锐利而智慧,身上穿着法师长袍。</p>
|
||||
<p>"艾丽丝,你来了。"凯蒂抬起头,看到林克,眼中闪过一丝惊讶,"这位就是...?"</p>
|
||||
<p>"林克。"艾丽丝介绍道,"从阿拉德大陆来的剑士,也是...我的重要的人。"</p>
|
||||
<p>凯蒂放下典籍,站起身来,仔细打量林克。</p>
|
||||
<p>"果然不同凡响。"她点头,"能被艾丽丝这样评价的人,一定不简单。"</p>
|
||||
<p>她伸出手:"我是凯蒂,魔界营地的魔法师。欢迎来到魔界。"</p>
|
||||
<p>林克握住她的手:"幸会。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人围坐在一张圆桌旁。</p>
|
||||
<p>尼梅尔好奇地四处张望,艾丽丝安静地坐在林克身边,凯蒂则从书架上取下一张地图,铺在桌上。</p>
|
||||
<p>"林克,你知道赫尔德是谁吗?"凯蒂问道。</p>
|
||||
<p>"只知道她是魔界的统治者,也是使徒之一。"林克回答。</p>
|
||||
<p>凯蒂点头:"这不够。你需要了解更多,才能对抗她。"</p>
|
||||
<p>她指着地图上的一个位置:"这里是地轨中心,赫尔德的大本营。她在那里进行着一个叫'创新世纪'的计划。"</p>
|
||||
<p>"创新世纪?"林克皱眉。</p>
|
||||
<p>"是的。"凯蒂严肃地说,"赫尔德想要重造整个世界,创造一个全新的宇宙。但这需要极其庞大的能量,而能量的来源...就是使徒死亡时释放的力量。"</p>
|
||||
<p>艾丽丝接过话头:"她策划了一系列事件,让冒险家杀死使徒。希洛克、罗特斯、狄瑞吉、安徒恩...每一个使徒的死亡,都为她的计划提供了能量。"</p>
|
||||
<p>林克脸色一沉:"她把使徒当成燃料?"</p>
|
||||
<p>"没错。"凯蒂点头,"下一个目标是卢克,海伯伦星的王。但现在..."</p>
|
||||
<p>她看向林克,眼中闪过一丝欣慰:"因为你救了卢克,她的计划被打乱了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"所以我救卢克是对的。"林克说。</p>
|
||||
<p>"非常正确。"凯蒂赞许道,"卢克是光与暗的使徒,他死亡会释放巨大的能量。赫尔德本来计划让他在寂静城被杀,但你的介入改变了这一切。"</p>
|
||||
<p>她叹了口气:"但也因此,赫尔德开始重视你了。在她眼中,你是一个威胁。"</p>
|
||||
<p>"我不在乎。"林克冷声说,"她想杀我,随时可以来试试。"</p>
|
||||
<p>凯蒂笑了笑:"有志气。但你要小心,赫尔德不是普通的敌人。她是第二使徒,拥有操纵空间的能力,被称为'魔界女王'。在魔界,她的势力根深蒂固,爪牙遍布各地。"</p>
|
||||
<p>"她有什么弱点吗?"林克问道。</p>
|
||||
<p>凯蒂沉思了片刻:"有。她的计划需要使徒死亡,如果你能保护剩余的使徒,她就无法完成创新世纪。"</p>
|
||||
<p>"剩余的使徒还有谁?"</p>
|
||||
<p>"米歇尔,第七使徒,目前在黑色大地。"凯蒂说,"还有卡西利亚斯,第九使徒,他是剑圣,可能在魔界某处。"</p>
|
||||
<p>"卡西利亚斯?剑圣?"林克眼中闪过兴趣。</p>
|
||||
<p>"是的。"凯蒂点头,"他是公认的最强剑士,如果你能找到他,也许能学到更多剑术。"</p>
|
||||
<p>林克心中一动。剑圣卡西利亚斯,这个名字他听过。如果能见到他...</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"凯蒂姐姐。"尼梅尔突然开口,"赫尔德的爪牙会来找林克吗?"</p>
|
||||
<p>"一定会。"凯蒂严肃地说,"昨天那些士兵只是试探,真正的追兵很快就会来。"</p>
|
||||
<p>她看向林克:"你有两个选择。第一,离开魔界,回到阿拉德大陆,这样赫尔德的爪牙很难追杀你。第二,留下来,与她正面对抗。"</p>
|
||||
<p>"我选第二条路。"林克毫不犹豫地说。</p>
|
||||
<p>凯蒂眼中闪过一丝赞许:"我就知道你会这么说。"</p>
|
||||
<p>她站起身,从书架上取下一枚水晶,递给林克:"这是通讯水晶,遇到危险可以联系我。另外..."</p>
|
||||
<p>她从抽屉里取出一张令牌:"这是营地的通行证,有了它,你可以自由进出魔界营地的各个区域。"</p>
|
||||
<p>林克接过两样东西:"谢谢。"</p>
|
||||
<p>"不用谢。"凯蒂微笑道,"你救了卢克,已经帮了我们大忙。如果你愿意继续对抗赫尔德,我们是盟友。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开凯蒂的住所后,三人沿着街道往回走。</p>
|
||||
<p>艾丽丝一直沉默着,直到快到教堂时,她才开口:"林克..."</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"谢谢你...愿意陪我对抗赫尔德。"她轻声说。</p>
|
||||
<p>林克握住她的手:"我说过,你是我的人,我不会让你一个人承受。"</p>
|
||||
<p>艾丽丝的眼眶微微泛红,她低下头,轻声说:"我知道...但我还是很害怕。"</p>
|
||||
<p>"怕什么?"</p>
|
||||
<p>"怕连累你..."艾丽丝抬起头,紫色的眼睛里满是担忧,"赫尔德太强大了,如果因为我的事让你受伤..."</p>
|
||||
<p>林克打断她的话,将她拥入怀中。</p>
|
||||
<p>"艾丽丝。"他在她耳边轻声说,"我既然来了,就不会退缩。不管赫尔德有多强,我都会保护你。"</p>
|
||||
<p>艾丽丝靠在他怀里,眼泪终于滑落。</p>
|
||||
<p>"林克..."</p>
|
||||
<p>尼梅尔站在一旁,看着两人相拥的身影,心中涌起一股复杂的情绪。</p>
|
||||
<p>"艾丽丝姐姐真的很幸福..."她想,"有一个愿意为她冒险的人..."</p>
|
||||
<p>她看向林克的侧脸,脸微微泛红。</p>
|
||||
<p>"林克...真的好温柔..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,林克坐在教堂后面的小院里,看着紫色的天空。</p>
|
||||
<p>艾丽丝在厨房准备晚餐,尼梅尔则去营地边缘巡逻了。</p>
|
||||
<p>"魔界..."林克喃喃自语。</p>
|
||||
<p>这里与阿拉德大陆完全不同。紫色的天空,扭曲的空间,弥漫的能量...一切都显得压抑而危险。</p>
|
||||
<p>但他并不后悔来这里。</p>
|
||||
<p>为了艾丽丝,为了对抗赫尔德,为了保护那些被伤害的人...这一切都值得。</p>
|
||||
<p>他握紧细雪之舞,眼中闪过一丝坚定。</p>
|
||||
<p>"赫尔德...我一定会阻止你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,尼梅尔匆匆跑进小院。</p>
|
||||
<p>"林克!艾丽丝姐姐!"</p>
|
||||
<p>"怎么了?"林克站起身。</p>
|
||||
<p>"营地外面有动静!"尼梅尔喘着气说,"好像是赫尔德的主力部队!"</p>
|
||||
<p>林克脸色一变,拔出细雪之舞。</p>
|
||||
<p>"走,去看看。"</p>
|
||||
<p>艾丽丝也拿着法杖跑了出来,三人一起朝营地边缘走去。</p>
|
||||
<p>远处,数十个身穿黑色铠甲的士兵正在集合,为首的是一个身材高大的男人,手持巨剑,眼中闪烁着凶光。</p>
|
||||
<p>"那个男人..."尼梅尔脸色发白,"是赫尔德麾下的将军,'铁血'卡尔!"</p>
|
||||
<p>林克眯起眼睛,看着那个男人。</p>
|
||||
<p>"终于来了个像样的对手..."</p>
|
||||
<p>他握紧光剑,冰蓝色的光芒在紫色的天空下格外耀眼。</p>
|
||||
<p>战斗,即将开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-130.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-132.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-101.html" class="sidebar-chapter ">第101章:不灭回廊</a>
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter current">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(131)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,995 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>营地危机 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 132</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>营地边缘,气氛紧绷如弦。</p>
|
||||
<p>数十名黑甲士兵排成阵列,手持长剑和盾牌,眼中闪烁着凶光。在他们身后,一个身材高大的男人缓缓走出——他穿着暗红色的铠甲,手中握着一把足有半人高的巨剑,剑身上刻着诡异的符文,散发着血色的光芒。</p>
|
||||
<p>"铁血卡尔..."尼梅尔的声音微微颤抖,"他是赫尔德麾下最强的将军之一,号称'血狱之剑'..."</p>
|
||||
<p>林克眯起眼睛,打量着这个对手。</p>
|
||||
<p>卡尔的气势确实不凡——浑身上下散发着压迫感,巨剑在他手中仿佛没有重量。他的眼神冷漠而傲慢,仿佛一切在他眼中都不值一提。</p>
|
||||
<p>"就是你救了卢克?"卡尔开口,声音低沉而沙哑,"让赫尔德大人的计划被打乱?"</p>
|
||||
<p>"是我。"林克拔出细雪之舞,冰蓝色的光芒亮起,"你想怎样?"</p>
|
||||
<p>"很简单。"卡尔冷笑,"杀了你,把你的头带回去给赫尔德大人。"</p>
|
||||
<p>他举起巨剑,指向林克:"不过,我会给你一个机会。跪下求饶,我可以让你死得痛快些。"</p>
|
||||
<p>林克面无表情地看着他:"废话真多。"</p>
|
||||
<p>他一步踏出,身影瞬间消失。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗爆发的瞬间,整个营地都震动了。</p>
|
||||
<p>林克的身影出现在卡尔面前,细雪之舞划出一道冰蓝色的弧线,直取卡尔的咽喉。但卡尔反应极快,巨剑横档,挡住了林克的攻击。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>金属碰撞的火花四溅,林克感到一股巨大的力量从剑上传来,整个人被震退了几步。</p>
|
||||
<p>"力量不错。"卡尔眼中闪过一丝惊讶,"但还不够。"</p>
|
||||
<p>他挥动巨剑,一道血色的剑气横扫而出。林克迅速后跳闪避,剑气击中地面,留下深深的沟壑。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>林克进入流心状态,身形变得模糊。他再次冲向卡尔,光剑连续刺出。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>冰蓝色的剑影如暴雨般落下,卡尔不得不举起巨剑防御。但林克的攻击太快了,有几剑刺中了卡尔的铠甲,留下了浅浅的痕迹。</p>
|
||||
<p>"哼,速度倒是很快。"卡尔冷哼一声,"但你破不了我的防御!"</p>
|
||||
<p>他猛地踏地,一圈红色的能量从他身上爆发出来,将林克震退。</p>
|
||||
<p>"铁壁!"</p>
|
||||
<p>卡尔的铠甲上亮起红色的光芒,防御力大大增强。林克的剑刺在上面,只能留下浅浅的痕迹。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗进行得异常激烈。</p>
|
||||
<p>林克不断变换攻击角度,流心刺、流心跃、破军升龙击...各种技能轮番上阵,但卡尔的防御实在太厚了。每当林克造成伤害,卡尔就会用某种秘术恢复。</p>
|
||||
<p>"这就是赫尔德的力量吗..."林克皱眉。</p>
|
||||
<p>"没错。"卡尔狂笑,"赫尔德大人赐予了我不死之身!你不可能杀得了我!"</p>
|
||||
<p>他举起巨剑,再次挥出一道血色剑气:"血刃斩!"</p>
|
||||
<p>巨大的剑气横扫营地,几座建筑被削去了一半。林克及时闪避,但身后的几个居民来不及躲避,眼看就要被剑气击中。</p>
|
||||
<p>"元素护盾!"</p>
|
||||
<p>艾丽丝的声音传来,一道紫色的光盾挡在居民面前,挡住了剑气。</p>
|
||||
<p>"艾丽丝!"林克看向她。</p>
|
||||
<p>艾丽丝站在营地中央,法杖高举,紫色的光芒环绕着她:"林克,我们帮你!"</p>
|
||||
<p>尼梅尔也挥舞着短剑冲了过来:"我来对付那些士兵!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>有了艾丽丝和尼梅尔的协助,局势开始改变。</p>
|
||||
<p>艾丽丝用元素魔法牵制卡尔,火球、冰锥、雷电不断轰击着他,让他无法全力攻击林克。尼梅尔则带领营地的冒险家们对抗黑甲士兵,减轻了林克的压力。</p>
|
||||
<p>"该死!"卡尔怒吼,"你们这些蝼蚁!"</p>
|
||||
<p>他挥动巨剑,想要攻击艾丽丝,但林克已经挡在了他面前。</p>
|
||||
<p>"你的对手是我。"林克冷声说道。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑上的光芒更盛,攻击力大幅提升。林克再次冲向卡尔,这次他的攻击更加凌厉。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>林克的身影化作一道闪电,连续四次斩击,每一次都精准地命中卡尔的关节部位。卡尔的铠甲开始出现裂痕,他发出痛苦的吼叫。</p>
|
||||
<p>"你这只蝼蚁!"</p>
|
||||
<p>卡尔疯狂了,他浑身燃起血色的火焰,力量暴增。</p>
|
||||
<p>"狂暴!"</p>
|
||||
<p>他的速度突然加快,巨剑横扫而来。林克来不及躲避,只能用光剑格挡。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>巨大的力量将林克击飞出去,他撞在一座建筑上,吐出一口鲜血。</p>
|
||||
<p>"林克!"艾丽丝惊呼。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克从废墟中站起,擦去嘴角的血迹。</p>
|
||||
<p>"这家伙...进入狂暴状态了..."</p>
|
||||
<p>他握紧细雪之舞,眼中闪过一丝冷意。</p>
|
||||
<p>"那就用终结技。"</p>
|
||||
<p>他深吸一口气,全身的力量集中到光剑上。冰蓝色的光芒越来越亮,最终形成了一个巨大的剑影。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>林克的身影化作无数道剑光,朝着卡尔席卷而去。每一道剑光都带着撕裂空气的力量,连续不断地击中卡尔。</p>
|
||||
<p>"啊啊啊!"</p>
|
||||
<p>卡尔发出痛苦的吼叫,他的铁壁防御终于被击破,身上出现了无数道伤口。血色的光芒逐渐消散,他的狂暴状态结束了。</p>
|
||||
<p>"不可能...我...我是赫尔德大人最强的将军..."</p>
|
||||
<p>最后一道剑光贯穿了他的胸膛,卡尔跪倒在地,巨剑从手中滑落。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克走到卡尔面前,光剑指着他。</p>
|
||||
<p>"结束了。"</p>
|
||||
<p>卡尔抬起头,眼中满是怨恨:"你以为...这样就结束了?赫尔德大人...一定会为我报仇..."</p>
|
||||
<p>他突然从怀中掏出一块水晶,捏碎。一道红色的光芒将他包裹,他的身影开始消失。</p>
|
||||
<p>"这是传送水晶!"艾丽丝大喊,"他要逃!"</p>
|
||||
<p>林克挥剑斩下,但只击中了空气。卡尔已经消失了。</p>
|
||||
<p>"该死..."林克收起光剑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束了。</p>
|
||||
<p>黑甲士兵见将军逃跑,纷纷溃散。营地的居民们从躲藏的地方走出来,欢呼着。</p>
|
||||
<p>"我们赢了!"</p>
|
||||
<p>"谢谢你!林克!"</p>
|
||||
<p>"你是我们的英雄!"</p>
|
||||
<p>艾丽丝走到林克身边,关切地看着他:"你受伤了?"</p>
|
||||
<p>"没事。"林克摇了摇头,"那个卡尔...还会回来的。"</p>
|
||||
<p>尼梅尔也跑了过来,脸上满是兴奋:"林克,你好厉害!那个铁血卡尔都被你打败了!"</p>
|
||||
<p>"他逃走了。"林克说,"不算真正的胜利。"</p>
|
||||
<p>"但他被你打跑了!"尼梅尔眼中满是崇拜,"你是第一个把他打得那么惨的人!"</p>
|
||||
<p>凯蒂也赶到了,她看着战后的营地,叹了口气。</p>
|
||||
<p>"损失不大,只有几座建筑被毁。"她说,"多亏了你,林克。"</p>
|
||||
<p>"这是我应该做的。"林克说。</p>
|
||||
<p>凯蒂摇头:"不,你不明白。铁血卡尔只是赫尔德众多将军中的一个。她手下还有很多强大的战士,甚至还有其他使徒..."</p>
|
||||
<p>她看着林克:"你确定要继续对抗她吗?"</p>
|
||||
<p>林克毫不犹豫地点头:"确定。"</p>
|
||||
<p>凯蒂沉默了片刻,然后微微一笑:"好。有你这样的盟友,是我们的幸运。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,林克坐在教堂后面的院子里,艾丽丝陪在他身边。</p>
|
||||
<p>"今天辛苦了。"艾丽丝轻声说。</p>
|
||||
<p>"嗯。"林克靠在墙上,看着紫色的月亮。</p>
|
||||
<p>艾丽丝犹豫了一下,然后靠在他肩上:"林克...谢谢你保护营地。"</p>
|
||||
<p>"我说过,我会陪你对抗赫尔德。"林克握住她的手,"这只是开始。"</p>
|
||||
<p>艾丽丝抬头看着他,紫色的眼睛里满是柔情:"林克..."</p>
|
||||
<p>她踮起脚尖,轻轻吻了他的唇。</p>
|
||||
<p>林克将她拥入怀中,两人在月光下静静相拥。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>不远处的阴影中,尼梅尔默默看着这一幕。</p>
|
||||
<p>她捂着胸口,感受着那里传来的悸动。</p>
|
||||
<p>"艾丽丝姐姐真的很幸福..."</p>
|
||||
<p>她转身离开,心中暗暗下定决心。</p>
|
||||
<p>"我也要...变得更强...帮林克分担..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,凯蒂来到教堂。</p>
|
||||
<p>"林克,我有件事要告诉你。"</p>
|
||||
<p>"什么事?"</p>
|
||||
<p>凯蒂从怀中取出一张地图:"我得到消息,赫尔德正在地轨中心进行一个新的实验。如果成功,她的力量会大大增强。"</p>
|
||||
<p>林克看着地图:"你想让我去阻止?"</p>
|
||||
<p>"不急。"凯蒂说,"你需要先增强自己的实力。我建议你先去中央公园,那里有很多强大的冒险家和魔法师,也许能学到新的东西。"</p>
|
||||
<p>"中央公园?"</p>
|
||||
<p>"是的。"凯蒂点头,"从魔界营地往西走,大约两天的路程。那里是魔界的另一个聚集地,比营地更加繁荣。"</p>
|
||||
<p>林克思考了片刻,然后点头:"好,我去。"</p>
|
||||
<p>艾丽丝站起身:"我陪你去。"</p>
|
||||
<p>尼梅尔也跑了过来:"我也去!"</p>
|
||||
<p>凯蒂笑了笑:"那就这么定了。中央公园...也许那里有你们需要的东西。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-131.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-133.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-102.html" class="sidebar-chapter ">第102章:机械王座</a>
|
||||
<a href="chapter-103.html" class="sidebar-chapter ">第103章:番外·寂静城的早晨</a>
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter current">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(132)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,972 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>中央公园 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 134</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>经过两天的跋涉,三人终于看到了中央公园的轮廓。</p>
|
||||
<p>与魔界营地的破败不同,中央公园显得繁华许多。高耸的建筑、热闹的街道、来往的人群...这里仿佛是另一个世界。</p>
|
||||
<p>"好漂亮..."尼梅尔睁大眼睛,"和营地完全不一样!"</p>
|
||||
<p>艾丽丝也有些惊讶:"中央公园发展得很快,据说是因为有强大的冒险家公会保护。"</p>
|
||||
<p>林克打量着周围的环境。街道两旁是各种商铺,卖武器、药剂、食物...冒险家们在街道上穿梭,脸上带着警惕和期待。</p>
|
||||
<p>"先找个地方住下。"林克说,"然后去找莎莎。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人在一家叫「魔界旅店」的地方订了房间。</p>
|
||||
<p>旅店老板是个胖胖的中年女人,看到林克,眼睛一亮。</p>
|
||||
<p>"你是从阿拉德大陆来的?"她热情地问。</p>
|
||||
<p>"是的。"林克点头。</p>
|
||||
<p>"欢迎欢迎!"老板笑眯眯地说,"阿拉德的冒险家很少来魔界呢。你们是来冒险的?"</p>
|
||||
<p>"来找人。"</p>
|
||||
<p>"找人?找谁?"</p>
|
||||
<p>"莎莎。"林克说,"听说她是这里的情报商。"</p>
|
||||
<p>老板的脸色微微变化:"莎莎啊...她住在东边的巷子里,门口有个紫色灯笼的店铺。不过她脾气不太好,你要小心。"</p>
|
||||
<p>"谢谢。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>放下行李后,三人前往东边的巷子。</p>
|
||||
<p>巷子比主街安静许多,两旁是一些老旧的建筑。走了大约五分钟,林克看到了一个挂着紫色灯笼的小店。</p>
|
||||
<p>店门紧闭,上面挂着一块木牌:「莎莎情报屋」。</p>
|
||||
<p>林克敲了敲门。</p>
|
||||
<p>"谁?"一个冷漠的女声从里面传来。</p>
|
||||
<p>"凯蒂介绍来的。"林克说。</p>
|
||||
<p>沉默了片刻,然后门"吱呀"一声打开了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>店内昏暗,只有几盏紫色的小灯提供微弱的光芒。</p>
|
||||
<p>一个身穿黑色长袍的女人坐在柜台后面,脸上戴着半张面具,只露出嘴巴和下巴。她的头发是深紫色的,眼睛在黑暗中闪着神秘的光。</p>
|
||||
<p>"凯蒂的朋友?"她打量着林克,"有点意思。进来吧。"</p>
|
||||
<p>三人走进店里,莎莎指了指对面的椅子:"坐。"</p>
|
||||
<p>林克坐下,开门见山:"我需要关于赫尔德的情报。"</p>
|
||||
<p>"赫尔德?"莎莎冷笑,"这可不是便宜的情报。"</p>
|
||||
<p>"凯蒂说你会给我优惠。"</p>
|
||||
<p>莎莎沉默了片刻,然后叹了口气:"那个女人...总是给别人添麻烦。"</p>
|
||||
<p>她从柜台下拿出一本厚厚的本子,翻开几页。</p>
|
||||
<p>"赫尔德最近在地轨中心很活跃,据说在进行一个新的实验。具体内容我不清楚,但有不少冒险家被她抓走了。"</p>
|
||||
<p>"抓走?"艾丽丝皱眉。</p>
|
||||
<p>"是的。"莎莎点头,"她需要实验体,而冒险家是最好的选择。所以你们要小心,别被抓到。"</p>
|
||||
<p>林克思考了片刻:"赫尔德麾下有哪些强者?"</p>
|
||||
<p>"很多。"莎莎说,"铁血卡尔你应该见过了,他是赫尔德的将军之一。除了他,还有'暗影刺客'莉莉丝、'魔剑士'阿斯兰、'血法师'维恩...每一个都是顶尖强者。"</p>
|
||||
<p>林克记下这些名字。</p>
|
||||
<p>"还有其他情报吗?"</p>
|
||||
<p>莎莎看了他一眼:"你还想知道什么?"</p>
|
||||
<p>"卡西利亚斯。"林克说,"魔界最强剑士,剑圣。听说他可能在魔界。"</p>
|
||||
<p>莎莎的眼中闪过一丝惊讶:"你找剑圣?"</p>
|
||||
<p>"是的。"</p>
|
||||
<p>莎莎沉默了片刻,然后从本子里抽出一张纸条。</p>
|
||||
<p>"这是三天前的消息。有人在中央公园北方的'剑冢'附近看到一个紫发的剑士,使唤着很多剑。"</p>
|
||||
<p>"剑冢?"</p>
|
||||
<p>"是的。那是一个古老的地方,据说埋葬着无数剑士的遗骸。有些剑士会去那里修炼,感受剑气。"</p>
|
||||
<p>莎莎看着林克:"不过,剑冢很危险。那里充满了怨念和杀气,普通人进去会发疯。你确定要去?"</p>
|
||||
<p>林克眼中闪过兴奋的光芒:"我要去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开情报屋后,三人走在街上。</p>
|
||||
<p>"林克,你要去剑冢?"艾丽丝问。</p>
|
||||
<p>"是的。"林克点头,"卡西利亚斯是剑圣,如果能见到他,也许能学到更多剑术。"</p>
|
||||
<p>尼梅尔有些担心:"但莎莎说那里很危险..."</p>
|
||||
<p>"危险才有挑战。"林克说,"而且,如果卡西利亚斯真的在那里,这是一个难得的机会。"</p>
|
||||
<p>艾丽丝看着林克眼中的光芒,知道他不会改变主意。</p>
|
||||
<p>"那我们一起去。"她说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>傍晚,三人在酒馆吃饭。</p>
|
||||
<p>酒馆里很热闹,冒险家们三五成群,讨论着各种话题。</p>
|
||||
<p>"听说铁血卡尔被打败了!"</p>
|
||||
<p>"真的假的?"</p>
|
||||
<p>"真的!魔界营地那边传来的消息,一个从阿拉德来的剑士把他打跑了!"</p>
|
||||
<p>"那个剑士是谁?"</p>
|
||||
<p>"不知道,但听说很强!"</p>
|
||||
<p>林克安静地听着这些讨论,没有说话。</p>
|
||||
<p>尼梅尔小声说:"他们在说你呢,林克。"</p>
|
||||
<p>林克摇了摇头:"不重要。明天去剑冢,早点休息。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,林克独自站在旅馆的阳台上,看着紫色的天空。</p>
|
||||
<p>"剑圣卡西利亚斯..."</p>
|
||||
<p>他喃喃自语。</p>
|
||||
<p>在阿拉德大陆,卡西利亚斯是一个传说。魔界最强剑士,剑圣,无数剑士的偶像。</p>
|
||||
<p>如果能见到他,与他切磋...</p>
|
||||
<p>林克握紧细雪之舞,眼中闪过期待的光芒。</p>
|
||||
<p>"等着我,卡西利亚斯。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,三人离开中央公园,前往北方的剑冢。</p>
|
||||
<p>一路上,景色逐渐变得荒凉。树木枯萎,地面布满裂痕,空气中弥漫着一股肃杀之气。</p>
|
||||
<p>"这里的气息...很不对劲。"艾丽丝皱眉。</p>
|
||||
<p>"是剑气。"林克说,"很多很多剑气。"</p>
|
||||
<p>他看着前方,那里有一片黑色的土地,无数断剑插在地上,如同墓碑。</p>
|
||||
<p>"剑冢..."</p>
|
||||
<p>林克深吸一口气,踏入这片死亡之地。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一个紫色的身影出现在剑冢深处。</p>
|
||||
<p>那个人背对着林克,手中没有武器,但周围却漂浮着无数把剑。</p>
|
||||
<p>"又有人来送死吗?"</p>
|
||||
<p>那个人的声音冷漠而傲慢。</p>
|
||||
<p>林克眯起眼睛,感受到一股强烈的压迫感。</p>
|
||||
<p>"你是...卡西利亚斯?"</p>
|
||||
<p>那人缓缓转过身,紫色的眼睛在黑暗中闪着光芒。</p>
|
||||
<p>"哦?"</p>
|
||||
<p>他看着林克,嘴角微微上扬。</p>
|
||||
<p>"有点意思的气息...你是个剑士?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十四章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-133.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-135.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-104.html" class="sidebar-chapter ">第104章:番外·贝奇与艾泽拉</a>
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter current">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(134)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,978 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>剑圣的试炼 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 135</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>剑冢之中,两股剑气遥遥相对。</p>
|
||||
<p>卡西利亚斯站在无数断剑之间,紫色的眼睛上下打量林克。他周身漂浮着十几把剑,每一把都散发着凌厉的剑气。</p>
|
||||
<p>"来自阿拉德大陆的剑士..."他淡淡地说,"你的气息不错,但还不够。"</p>
|
||||
<p>林克握紧细雪之舞,能感受到对方身上那股深不可测的力量。</p>
|
||||
<p>"我想与你切磋。"林克说。</p>
|
||||
<p>卡西利亚斯嘴角微微上扬:"切磋?"</p>
|
||||
<p>他轻笑一声:"有意思。已经很久没有人敢向我提出挑战了。"</p>
|
||||
<p>他抬起手,三把漂浮的剑缓缓转向林克:"好,我给你一个机会。能在我手下撑过十招,我就认你合格。"</p>
|
||||
<p>林克深吸一口气:"请指教!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>卡西利亚斯手指轻轻一动,三把剑如同利箭般射向林克。速度快得惊人,林克只来得及举剑格挡。</p>
|
||||
<p>"铛!铛!铛!"</p>
|
||||
<p>三声脆响,林克被震退了三步。手臂发麻,虎口隐隐作痛。</p>
|
||||
<p>"太慢了。"卡西利亚斯摇了摇头,"你的反应速度还可以,但剑意太散。"</p>
|
||||
<p>他手指再次一动,这次是五把剑同时攻击,从不同的角度刺向林克。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>林克进入流心状态,身形变得模糊。他连续闪避,同时挥剑反击。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他腾空而起,躲过了三把剑,然后从空中劈下。</p>
|
||||
<p>但卡西利亚斯只是轻轻挥手,一把剑就挡住了林克的攻击。</p>
|
||||
<p>"力度不够,角度太正。"卡西利亚斯点评道,"你的剑术有形,但无魂。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克落地,皱起眉头。</p>
|
||||
<p>这个对手...太强了。</p>
|
||||
<p>他的每一招都被轻松化解,而卡西利亚斯甚至没有移动过脚步,只是用意念御剑。</p>
|
||||
<p>"再来。"林克咬牙,再次冲了上去。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>细雪之舞的光芒更盛,攻击力大幅提升。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>林克的身影化作闪电,连续四次斩击。每一剑都带着破空之声,直取卡西利亚斯。</p>
|
||||
<p>但卡西利亚斯周围的剑自动形成了一道剑网,将林克的攻击全部挡下。</p>
|
||||
<p>"招式不错,但太死板。"卡西利亚斯说,"你以为我在夸你?"</p>
|
||||
<p>他手指一弹,一把剑突然加速,刺向林克的肩膀。</p>
|
||||
<p>林克来不及躲避,只能侧身。剑锋划过他的肩膀,留下一道血痕。</p>
|
||||
<p>"第一招到第十招。"卡西利亚斯淡淡地说,"你输了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝和尼梅尔在远处紧张地看着这一幕。</p>
|
||||
<p>"林克受伤了!"尼梅尔惊呼。</p>
|
||||
<p>艾丽丝握紧法杖,但没有出手。她知道这是林克想要的切磋,她不能插手。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克捂着肩膀,看着卡西利亚斯。</p>
|
||||
<p>"确实...我输了。"他承认。</p>
|
||||
<p>卡西利亚斯收起漂浮的剑,走向林克。</p>
|
||||
<p>"你的天赋不错,基础也扎实。"他说,"但你的剑术...缺少灵魂。"</p>
|
||||
<p>"灵魂?"林克疑惑。</p>
|
||||
<p>"是的。"卡西利亚斯点头,"你把剑当成武器,当成工具。但真正的剑术,剑是身体的延伸,是灵魂的延伸。"</p>
|
||||
<p>他伸出手,一把断剑从地上飘起,落入他手中。</p>
|
||||
<p>"看好了。"</p>
|
||||
<p>他挥剑一斩,一道紫色的剑气横扫而出,将远处的巨石劈成两半。</p>
|
||||
<p>"这是剑气。"他说,"你的剑只能伤人,我的剑可以断山。区别不在于力量,而在于心境。"</p>
|
||||
<p>林克看着那道剑痕,陷入沉思。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你叫什么名字?"卡西利亚斯问。</p>
|
||||
<p>"林克。"</p>
|
||||
<p>"林克..."卡西利亚斯重复了一遍,"记住我今天说的话。剑不是用来杀人的工具,而是用来守护的力量。当你明白了这一点,你的剑术才能真正进化。"</p>
|
||||
<p>他转身,背对着林克:"你还有很长的路要走。但我看好你。"</p>
|
||||
<p>林克看着他的背影:"卡西利亚斯先生,我能再问一个问题吗?"</p>
|
||||
<p>"说。"</p>
|
||||
<p>"您为什么要帮助我?"</p>
|
||||
<p>卡西利亚斯停下脚步,没有回头:"因为很久以前,也有人对我说过同样的话。"</p>
|
||||
<p>他迈步走向剑冢深处:"去吧,去地轨中心。那里有你需要的答案。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克站在原地,看着卡西利亚斯消失的方向。</p>
|
||||
<p>"剑是身体的延伸...是灵魂的延伸..."</p>
|
||||
<p>他喃喃自语。</p>
|
||||
<p>艾丽丝和尼梅尔跑过来,检查他的伤势。</p>
|
||||
<p>"林克,你没事吧?"艾丽丝担心地问。</p>
|
||||
<p>"我没事。"林克摇头,"只是皮外伤。"</p>
|
||||
<p>尼梅尔看着他肩膀上的伤口,眼眶微红:"那个卡西利亚斯...太厉害了...林克你完全不是对手..."</p>
|
||||
<p>"是啊。"林克苦笑,"实力差距太大了。但...我学到了很多。"</p>
|
||||
<p>他看向剑冢深处,眼中闪过坚定。</p>
|
||||
<p>"总有一天,我会追上他。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开剑冢后,三人返回中央公园。</p>
|
||||
<p>林克一边走,一边回味卡西利亚斯的话。</p>
|
||||
<p>"剑不是工具,是灵魂的延伸..."</p>
|
||||
<p>他握着细雪之舞,感受着剑身传来的冰凉触感。</p>
|
||||
<p>"我以前...真的只是把剑当成武器吗?"</p>
|
||||
<p>他想起在阿拉德大陆的日子。从拿起第一把剑开始,他就不断战斗、不断变强。但他从未思考过剑对他的意义。</p>
|
||||
<p>"守护..."</p>
|
||||
<p>他想起赛丽亚、艾丽丝、尼梅尔...还有所有他在乎的人。</p>
|
||||
<p>"我想变强,是为了守护她们。"</p>
|
||||
<p>他停下脚步,看向手中的光剑。</p>
|
||||
<p>"细雪之舞...你也是这么想的吗?"</p>
|
||||
<p>剑身微微震动,仿佛在回应他。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到中央公园已经是傍晚。</p>
|
||||
<p>三人在旅馆休息,林克的伤口已经包扎好。</p>
|
||||
<p>"接下来怎么办?"艾丽丝问。</p>
|
||||
<p>"去地轨中心。"林克说,"卡西利亚斯说的。那里有我需要的答案。"</p>
|
||||
<p>"地轨中心..."艾丽丝神色凝重,"那是赫尔德的大本营,非常危险。"</p>
|
||||
<p>"我知道。"林克点头,"但我们迟早要面对她。"</p>
|
||||
<p>尼梅尔握紧他的手:"林克,我陪你。"</p>
|
||||
<p>艾丽丝也点了点头:"我也去。"</p>
|
||||
<p>林克看着两人,露出微笑:"谢谢。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,林克独自站在阳台上,看着紫色的天空。</p>
|
||||
<p>他从怀中取出一块水晶——那是凯蒂给他的通讯水晶。</p>
|
||||
<p>"凯蒂...我见到卡西利亚斯了。"</p>
|
||||
<p>他低声说,仿佛在自言自语。</p>
|
||||
<p>"他比我强太多。但我知道了...我的剑还缺少东西。"</p>
|
||||
<p>他看向天空,眼中闪过坚定。</p>
|
||||
<p>"等着我,赫尔德。我一定会阻止你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十五章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-134.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-136.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-105.html" class="sidebar-chapter ">第105章:番外·卢克的嘱托</a>
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter current">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(135)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,959 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>地轨中心 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 136</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>地轨中心,魔界最神秘的地方。</p>
|
||||
<p>三人站在入口处,看着眼前扭曲的空间。这里的天空不是紫色,而是深黑色,偶尔闪过诡异的光芒。地面布满了裂痕,从中涌出幽蓝色的能量。</p>
|
||||
<p>"这里就是地轨中心..."艾丽丝轻声说,"赫尔德的大本营。"</p>
|
||||
<p>林克握紧细雪之舞,感受到空气中弥漫的压抑气息。这里的空间似乎在扭曲,让人产生一种眩晕感。</p>
|
||||
<p>"跟紧我。"他说,踏入这片危险之地。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>刚进入地轨中心不久,林克就感觉到不对劲。</p>
|
||||
<p>"有东西过来了。"他低声说。</p>
|
||||
<p>话音刚落,几个身穿银色铠甲的身影从扭曲的空间中显现。他们没有脸,头盔上只有一个发光的眼睛。</p>
|
||||
<p>"空间守卫!"艾丽丝认出了他们,"赫尔德的眼线!"</p>
|
||||
<p>"发现入侵者。"领头的守卫发出机械般的声音,"执行清除程序。"</p>
|
||||
<p>六名空间守卫同时拔剑,朝林克冲来。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>林克迎上第一个守卫,光剑划出一道弧线。但守卫的身影突然消失,出现在他身后。</p>
|
||||
<p>"瞬移?"林克反应极快,转身格挡。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>守卫的剑被挡下,但另外两个守卫已经从两侧攻来。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>林克进入流心状态,身形变得模糊。他连续闪避,同时寻找敌人的破绽。</p>
|
||||
<p>"这些家伙...会瞬移,很难抓住。"</p>
|
||||
<p>他闭上眼睛,感受周围的气息。</p>
|
||||
<p>"剑是灵魂的延伸..."</p>
|
||||
<p>卡西利亚斯的话在他脑海中回响。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克深吸一口气,放松身体。</p>
|
||||
<p>他不再用眼睛去追踪敌人,而是用感觉。</p>
|
||||
<p>空间守卫的瞬移会留下微弱的能量波动...在这里!</p>
|
||||
<p>林克猛然睁眼,转身一斩。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>光剑精准地命中了刚出现的守卫,将其击倒。</p>
|
||||
<p>"找到了。"</p>
|
||||
<p>林克的嘴角微微上扬。他开始适应这些敌人的节奏,预判他们的出现位置。</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>他冲向另一个守卫,将其击飞。紧接着,他又连续攻击,不给敌人喘息的机会。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>闪电般的四连斩,两个守卫同时倒下。</p>
|
||||
<p>艾丽丝和尼梅尔在一旁协助,对付剩下的敌人。艾丽丝的元素魔法精准地命中目标,尼梅尔的短剑也刺穿了一个守卫的盔甲。</p>
|
||||
<p>战斗很快就结束了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克,你的剑...好像不一样了。"艾丽丝看着林克,眼中带着惊讶。</p>
|
||||
<p>"感觉更流畅了。"尼梅尔也说。</p>
|
||||
<p>林克低头看着细雪之舞:"我只是...找到了一些感觉。"</p>
|
||||
<p>他收起光剑:"走吧,我们继续前进。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人深入地轨中心。</p>
|
||||
<p>越往里走,扭曲的空间越严重。有时候走直线却会突然转向,有时候眼前的路会突然消失。</p>
|
||||
<p>"赫尔德在用空间魔法控制这里。"艾丽丝说,"她可以把整个地轨中心变成迷宫。"</p>
|
||||
<p>"有办法破解吗?"林克问。</p>
|
||||
<p>"我试试。"艾丽丝闭上眼睛,紫色的光芒在她手中凝聚。</p>
|
||||
<p>片刻后,她睁开眼睛:"那边。"她指向左前方,"有一个很大的能量源,应该是赫尔德的实验室。"</p>
|
||||
<p>三人朝着艾丽丝指的方向前进。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>大约走了半个小时,他们看到了一座巨大的建筑。</p>
|
||||
<p>那是一座高耸的黑色塔楼,周围环绕着紫色的能量环。塔楼上刻满了诡异的符文,散发着压迫感。</p>
|
||||
<p>"这就是赫尔德的实验室..."艾丽丝轻声说。</p>
|
||||
<p>林克注意到塔楼周围有一些笼子,里面关着人。</p>
|
||||
<p>"那些是...冒险家?"</p>
|
||||
<p>他快步走过去,看到笼子里的人都是来自各地的冒险家。他们有的昏迷,有的在痛苦地挣扎,还有的已经...</p>
|
||||
<p>"他们被当作实验体。"艾丽丝的声音颤抖,"赫尔德...在用他们做什么?"</p>
|
||||
<p>林克握紧拳头,眼中闪过怒火。</p>
|
||||
<p>"我们进去。"他说,"我要看看赫尔德到底在做什么。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人潜入塔楼。</p>
|
||||
<p>内部比外面更加诡异。墙壁上挂满了各种魔法道具,地上是复杂的魔法阵。空气中弥漫着一股奇怪的味道,让人感到不适。</p>
|
||||
<p>林克小心翼翼地前进,避免触发警报。</p>
|
||||
<p>他们来到一个巨大的房间,透过玻璃窗,看到了里面的景象。</p>
|
||||
<p>那是一个实验室。中间有一个巨大的容器,里面漂浮着一个发光的球体。周围是各种仪器和屏幕,显示着复杂的数据。</p>
|
||||
<p>"那是..."艾丽丝瞪大眼睛,"使徒能量的结晶?!"</p>
|
||||
<p>"使徒能量?"林克疑惑。</p>
|
||||
<p>"是的。"艾丽丝解释,"当使徒死亡时,会释放巨大的能量。赫尔德在收集这些能量..."</p>
|
||||
<p>她的脸色变得苍白:"她真的在进行'创新世纪'计划。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一个声音从身后传来。</p>
|
||||
<p>"看来有老鼠进来了。"</p>
|
||||
<p>林克猛然转身,看到一个身穿黑色铠甲的男人站在门口。他有着银色的短发,脸上带着冷漠的笑容。</p>
|
||||
<p>"阿斯兰..."艾丽丝认出了他,"魔剑士阿斯兰!"</p>
|
||||
<p>阿斯兰拔出背后的魔剑,剑身散发着黑红色的光芒。</p>
|
||||
<p>"你们是怎么进来的?"他问,"算了,不重要。你们会成为新的实验体。"</p>
|
||||
<p>林克挡在艾丽丝和尼梅尔面前,拔出细雪之舞。</p>
|
||||
<p>"想抓我们?"他冷声说,"试试看。"</p>
|
||||
<p>阿斯兰笑了:"有意思。让我看看你有多少本事。"</p>
|
||||
<p>他挥动魔剑,一道黑红色的剑气横扫而出。</p>
|
||||
<p>林克迎了上去,两剑相交。</p>
|
||||
<p>战斗,开始了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十六章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-135.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-137.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-106.html" class="sidebar-chapter ">第106章:时空之门的召唤</a>
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter current">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(136)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,983 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>魔剑士阿斯兰 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 137</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>两剑相交,火花四溅。</p>
|
||||
<p>林克感受到一股巨大的力量从阿斯兰的魔剑上传来,整个人被震退了几步。</p>
|
||||
<p>"力量不错。"阿斯兰冷笑,"但还远远不够。"</p>
|
||||
<p>他挥动魔剑「阿波菲斯」,一道黑红色的剑气横扫而出。剑气所过之处,地面被劈开,空气中弥漫着灼热的气息。</p>
|
||||
<p>林克迅速闪避,但剑气的范围太大,还是被余波击中,肩膀上的伤口再次裂开。</p>
|
||||
<p>"魔剑的力量...确实很强。"林克咬牙。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"魔剑斩!"</p>
|
||||
<p>阿斯兰再次挥剑,这次是三道剑气同时斩出,封锁了林克的所有闪避路线。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>林克腾空而起,躲过了剑气。但阿斯兰的身影突然消失,出现在他头顶。</p>
|
||||
<p>"暗影步!"</p>
|
||||
<p>魔剑从空中劈下,林克举剑格挡。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>巨大的力量将林克砸向地面,他在地上砸出一个坑洞。</p>
|
||||
<p>"林克!"尼梅尔惊呼。</p>
|
||||
<p>艾丽丝举起法杖,紫色的元素魔法凝聚:"元素爆破!"</p>
|
||||
<p>火球、冰锥、雷电同时轰向阿斯兰。但阿斯兰只是挥了挥剑,一道黑色的屏障挡下了所有攻击。</p>
|
||||
<p>"元素魔法?对我来说没用。"他冷笑,"魔剑可以吞噬一切魔法。"</p>
|
||||
<p>他手指一动,一道黑红色的能量束射向艾丽丝。艾丽丝来不及躲避,被击中,整个人飞了出去。</p>
|
||||
<p>"艾丽丝!"林克从坑洞中站起,眼中闪过怒火。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你生气了?"阿斯兰看着林克,"很好。愤怒会让你变得更强...也会让你露出破绽。"</p>
|
||||
<p>林克深吸一口气,强迫自己冷静下来。</p>
|
||||
<p>愤怒...只会让剑变得混乱。</p>
|
||||
<p>他想起卡西利亚斯的话:"剑是灵魂的延伸。"</p>
|
||||
<p>他闭上眼睛,感受细雪之舞的脉动。</p>
|
||||
<p>这把剑...已经陪伴他很久了。从格兰之森到天空之城,从天界到魔界...它见证了他一路的成长。</p>
|
||||
<p>"你不是武器。"他在心中默念,"你是我的伙伴。"</p>
|
||||
<p>细雪之舞微微震动,仿佛在回应他。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克睁开眼睛,眼神变得平静。</p>
|
||||
<p>"哦?"阿斯兰注意到林克的变化,"气息变了...有意思。"</p>
|
||||
<p>林克握剑,主动冲向阿斯兰。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑的光芒更盛,剑身上浮现出冰蓝色的符文。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>林克的身影化作闪电,连续四斩。每一剑都比之前更快、更准。</p>
|
||||
<p>阿斯兰的表情微微变化。他发现...自己无法像之前那样轻松应对了。</p>
|
||||
<p>"这家伙...变强了?"</p>
|
||||
<p>他挥剑反击,魔剑和阿斯兰的力量结合,爆发出惊人的威力。但林克每一次都精准地预判了他的攻击,用最小的动作闪避或格挡。</p>
|
||||
<p>"怎么可能..."阿斯兰皱眉,"你的剑术...好像看到了什么?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗进入白热化。</p>
|
||||
<p>林克和阿斯兰你来我往,剑光交错。地面被劈出无数道裂缝,周围的设备被剑气摧毁。</p>
|
||||
<p>"你的剑术确实不错。"阿斯兰承认,"但在我面前,还是不够!"</p>
|
||||
<p>他高举魔剑,剑身上绽放出黑红色的光芒。</p>
|
||||
<p>"魔剑降临!"</p>
|
||||
<p>无数把黑红色的剑从空中落下,如同剑雨。每一把剑都带着毁灭的气息,将整个房间笼罩。</p>
|
||||
<p>"这是...范围攻击?!"</p>
|
||||
<p>林克无法闪避,只能硬抗。</p>
|
||||
<p>"极·鬼剑术(暴风式)!"</p>
|
||||
<p>他召唤出二十四把光剑,形成剑阵,挡住从天而降的魔剑。</p>
|
||||
<p>"铛铛铛铛!"</p>
|
||||
<p>无数金属碰撞的声音响起,整个房间被剑光充满。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>魔剑降临持续了将近一分钟才结束。</p>
|
||||
<p>林克喘着粗气,身上多了几道伤口。但他的眼神依然坚定。</p>
|
||||
<p>"还没结束。"他说。</p>
|
||||
<p>阿斯兰也有些意外:"能挡住魔剑降临...你确实很强。但你的体力应该快耗尽了吧?"</p>
|
||||
<p>林克没有说话。他确实很累,体力消耗很大。但他不能输。</p>
|
||||
<p>艾丽丝还在地上昏迷,尼梅尔正在照顾她。如果自己倒下,她们都会有危险。</p>
|
||||
<p>"守护..."</p>
|
||||
<p>他想起自己为什么要变强。</p>
|
||||
<p>不是为了杀戮,不是为了荣耀,而是为了守护那些重要的人。</p>
|
||||
<p>"这就是...我的剑道。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克深吸一口气,将剩余的所有力量集中在剑上。</p>
|
||||
<p>细雪之舞发出耀眼的光芒,冰蓝色的剑气冲天而起,在空中凝聚成无数把剑。</p>
|
||||
<p>"这是..."阿斯兰瞪大眼睛,"万剑归宗?!"</p>
|
||||
<p>林克抬起剑,指向阿斯兰。</p>
|
||||
<p>无数把剑从空中落下,如同流星雨,全部朝阿斯兰袭去。</p>
|
||||
<p>"不可能...!"</p>
|
||||
<p>阿斯兰挥动魔剑,想要挡住这攻击。但剑的数量太多了,每一把都带着林克的意志。</p>
|
||||
<p>"铛!铛!铛!"</p>
|
||||
<p>魔剑被击飞,阿斯兰的铠甲被刺穿。他发出痛苦的吼叫,整个人被剑雨淹没。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当光芒散去,阿斯兰跪倒在地。</p>
|
||||
<p>他的铠甲破碎,身上布满了伤口。魔剑「阿波菲斯」插在一旁,光芒黯淡。</p>
|
||||
<p>"你...赢了..."他艰难地说。</p>
|
||||
<p>林克走到他面前,光剑指着他。</p>
|
||||
<p>"赫尔德在哪里?"他问。</p>
|
||||
<p>阿斯兰苦笑:"她在...地轨中心的最深处...但你去不了...她的力量...远超你的想象..."</p>
|
||||
<p>说完,他闭上了眼睛,昏迷过去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克收起光剑,走到艾丽丝和尼梅尔身边。</p>
|
||||
<p>"艾丽丝,你没事吧?"</p>
|
||||
<p>艾丽丝缓缓睁开眼睛,虚弱地笑了笑:"我没事...只是被冲击波震到了..."</p>
|
||||
<p>尼梅尔看着林克,眼中满是崇拜:"林克,你好厉害...万剑归宗真的太帅了!"</p>
|
||||
<p>林克摇了摇头:"我只是运气好。如果阿斯兰再强一点,我就输了。"</p>
|
||||
<p>他看向实验室深处:"我们继续前进。赫尔德就在前面。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人继续深入塔楼。</p>
|
||||
<p>越往里走,气氛越压抑。空气中弥漫着一股古老的力量,让人呼吸都变得困难。</p>
|
||||
<p>终于,他们来到了一扇巨大的门前。</p>
|
||||
<p>门上刻满了符文,散发着紫色的光芒。透过门缝,可以看到里面有一个人影。</p>
|
||||
<p>"赫尔德..."艾丽丝轻声说。</p>
|
||||
<p>林克深吸一口气,推开了门。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>门后是一个巨大的圆形空间。</p>
|
||||
<p>中间有一个王座,一个身穿白色长裙的女人坐在上面。她有着银色的长发,眼睛是深邃的紫色,气质高贵而神秘。</p>
|
||||
<p>那就是赫尔德,第二使徒,泪目之眼。</p>
|
||||
<p>"你们终于来了。"她开口,声音如同银铃般清脆,"林克,我等你很久了。"</p>
|
||||
<p>林克握紧细雪之舞:"你知道我会来?"</p>
|
||||
<p>"当然。"赫尔德站起来,缓缓走向林克,"你打败了铁血卡尔,见到了卡西利亚斯,又击败了阿斯兰...你的成长速度,超出我的预期。"</p>
|
||||
<p>她停下脚步,看着林克:"所以,我给你一个选择。"</p>
|
||||
<p>"什么选择?"</p>
|
||||
<p>"加入我。"赫尔德伸出手,"帮我完成创新世纪。作为回报,我会给你想要的一切——力量、地位、甚至...你爱的人的生命。"</p>
|
||||
<p>林克的眼神变得冰冷:"我拒绝。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十七章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-136.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-138.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-107.html" class="sidebar-chapter ">第107章:格兰之火</a>
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter current">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(137)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,983 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>泪目之眼 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 138</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>"我拒绝。"</p>
|
||||
<p>林克的声音坚定而冰冷。</p>
|
||||
<p>赫尔德的表情没有变化,仿佛早就预料到这个答案。</p>
|
||||
<p>"为什么?"她问,"我可以给你一切。力量、地位、永生...甚至可以复活你失去的人。"</p>
|
||||
<p>"我不需要。"林克说,"你所谓的'创新世纪',是建立在无数人的痛苦之上的。我不会成为你的帮凶。"</p>
|
||||
<p>赫尔德轻轻叹了口气:"你真的不明白..."</p>
|
||||
<p>她转身,走向王座后面的一扇窗户。窗外是扭曲的魔界天空,紫色的光芒在黑暗中闪烁。</p>
|
||||
<p>"林克,你知道这个世界有多少痛苦吗?"她背对着林克说,"战争、疾病、死亡...每一天都有无数人在绝望中死去。"</p>
|
||||
<p>她转过身,紫色的眼睛里带着一种奇异的光芒:"我要消除所有痛苦。创造一个没有战争、没有疾病、没有死亡的世界。这难道不是所有人梦寐以求的吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"代价是什么?"林克冷声问。</p>
|
||||
<p>"代价?"赫尔德微微一笑,"一些人的牺牲,换来所有人的幸福。这是公平的交易。"</p>
|
||||
<p>"对那些被牺牲的人来说,不公平。"</p>
|
||||
<p>赫尔德的笑容消失了。她看着林克,眼中闪过一丝失望。</p>
|
||||
<p>"你果然和那些短视的人一样...只看到眼前的得失,看不到长远的未来。"</p>
|
||||
<p>她走向林克,每一步都带着压迫感:"你知道使徒为什么会死吗?因为他们的存在,本身就是世界的负担。希洛克、罗特斯、狄瑞吉、安徒恩...每一个使徒死亡,都会释放巨大的能量。这些能量,可以用来重造世界。"</p>
|
||||
<p>"卢克呢?"林克问,"他也必须死吗?"</p>
|
||||
<p>"卢克..."赫尔德的眼神微微变化,"他是光与暗的使徒,他的能量比其他使徒都要强大。如果他死了,创新世纪的进度会大大加快。"</p>
|
||||
<p>她看着林克:"但你救了他。这让我的计划推迟了...不过没关系,我可以找到其他方法。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧细雪之舞。</p>
|
||||
<p>这个女人...把生命当作数字,把死亡当作工具。</p>
|
||||
<p>"我不会让你成功。"他说。</p>
|
||||
<p>赫尔德笑了:"你想阻止我?"</p>
|
||||
<p>"是的。"</p>
|
||||
<p>"就凭你?"赫尔德摇头,"林克,你很强,比大多数冒险家都要强。但在我面前...你还太年轻。"</p>
|
||||
<p>她抬起手,紫色的光芒在指尖凝聚:"让我教教你,什么是真正的力量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>林克冲向赫尔德,光剑划出冰蓝色的弧线。但他的剑还没碰到赫尔德,就被一道无形的屏障挡住了。</p>
|
||||
<p>"空间壁垒。"赫尔德淡淡地说,"你的剑无法触及我。"</p>
|
||||
<p>林克退后几步,再次尝试。这次他用上了"猛龙断空斩",连续四斩,每一击都带着强大的力量。</p>
|
||||
<p>但屏障纹丝不动。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>他换成刺击,想要突破屏障。但依然无效。</p>
|
||||
<p>"极·鬼剑术(暴风式)!"</p>
|
||||
<p>二十四把光剑出现,朝赫尔德射去。但它们在接近赫尔德时,突然停在了空中。</p>
|
||||
<p>"空间凝固。"赫尔德说,"我控制了你周围的空间。你的攻击,对我来说没有任何意义。"</p>
|
||||
<p>她轻轻挥手,林克感觉到一股巨大的力量将自己束缚。他无法移动,甚至无法呼吸。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"这就是使徒的力量。"赫尔德走向被束缚的林克,"空间、时间、因果...这些在你眼中无法理解的力量,对我来说只是工具。"</p>
|
||||
<p>她停在林克面前,紫色的眼睛看着他:"你现在明白了吗?你不可能战胜我。"</p>
|
||||
<p>林克咬牙,试图挣脱。但束缚他的力量太强了,完全无法反抗。</p>
|
||||
<p>"艾丽丝...尼梅尔...快跑..."他艰难地说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"想跑?"赫尔德看向艾丽丝和尼梅尔,"我可没允许。"</p>
|
||||
<p>她抬起手,空间屏障将整个房间封锁。</p>
|
||||
<p>"今天,你们都留在这里。"</p>
|
||||
<p>艾丽丝紧握法杖,眼中闪过决然。</p>
|
||||
<p>"林克,听我说!"她大声说,"赫尔德虽然强,但她有一个弱点——她需要维持空间屏障,无法同时攻击!"</p>
|
||||
<p>林克明白了艾丽丝的意思。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>他将所有力量集中在剑上,猛然一斩。</p>
|
||||
<p>"破空斩!"</p>
|
||||
<p>剑气斩在空间屏障上,发出刺耳的声音。屏障出现了裂痕。</p>
|
||||
<p>"什么?"赫尔德微微惊讶,"你能撼动我的屏障?"</p>
|
||||
<p>她加大了力量,屏障重新变得坚固。但就在这个瞬间,艾丽丝的法杖亮起了紫色的光芒。</p>
|
||||
<p>"元素传送!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一道紫色的光芒将林克、艾丽丝和尼梅尔包裹。</p>
|
||||
<p>赫尔德皱眉:"想逃?"</p>
|
||||
<p>她挥手,想要阻止传送。但林克再次挥剑,挡住了她的攻击。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他腾空而起,光剑斩向赫尔德。虽然无法造成伤害,但争取了时间。</p>
|
||||
<p>紫色的光芒越来越亮,传送即将完成。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你们逃不掉的。"赫尔德冷声说,"整个地轨中心都在我的控制之下。"</p>
|
||||
<p>"我们走!"艾丽丝大喊。</p>
|
||||
<p>光芒闪烁,三人的身影开始变得模糊。</p>
|
||||
<p>赫尔德看着他们,没有再追。她只是静静站在原地,嘴角带着一丝微笑。</p>
|
||||
<p>"林克...你还会回来的。"</p>
|
||||
<p>她的声音在三人耳边回荡:"当你真正理解了这个世界的痛苦,你就会明白,我是对的。"</p>
|
||||
<p>然后,光芒吞没了一切。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克再次睁开眼睛时,发现自己躺在一片陌生的土地上。</p>
|
||||
<p>"这是...中央公园?"他辨认出周围的环境。</p>
|
||||
<p>艾丽丝和尼梅尔也在他身边,脸色苍白。</p>
|
||||
<p>"成功逃出来了..."艾丽丝虚弱地说,"但我的魔力几乎耗尽了..."</p>
|
||||
<p>尼梅尔扶着艾丽丝,看向林克:"林克,你没事吧?"</p>
|
||||
<p>"我没事。"林克站起身,看着地轨中心的方向。</p>
|
||||
<p>他能感受到那里传来的压迫感,即使隔着这么远,依然让他心悸。</p>
|
||||
<p>"赫尔德...太强了。"他喃喃自语。</p>
|
||||
<p>那是他第一次感受到如此绝望的实力差距。即使他全力以赴,也无法触及她分毫。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我们暂时不能回去了。"艾丽丝说,"以我们现在的力量,无法对抗赫尔德。"</p>
|
||||
<p>"那怎么办?"尼梅尔问。</p>
|
||||
<p>林克沉默了片刻。</p>
|
||||
<p>"变强。"他说,"继续变强,直到能战胜赫尔德为止。"</p>
|
||||
<p>他看向天空,眼中闪过坚定。</p>
|
||||
<p>"卡西利亚斯说,我的剑还缺少灵魂。如果我能领悟真正的剑道,也许有机会。"</p>
|
||||
<p>他转身,看向中央公园:"我们先在这里休整,然后...去寻找更强的力量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,林克独自坐在旅馆的屋顶上。</p>
|
||||
<p>他回想着与赫尔德的战斗。那种完全被压制的感觉,让他深感无力。</p>
|
||||
<p>"使徒级别的力量..."</p>
|
||||
<p>他握紧细雪之舞:"我还差得太远。"</p>
|
||||
<p>但他没有放弃。</p>
|
||||
<p>"总有一天...我会达到那个境界。"</p>
|
||||
<p>他想起赛丽亚、艾丽丝、尼梅尔...还有所有他在乎的人。</p>
|
||||
<p>"为了守护你们,我一定要变强。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,艾丽丝找到了林克。</p>
|
||||
<p>"林克,我有一个消息。"她说,"莎莎告诉我,近期会有一个大事件在魔界发生。"</p>
|
||||
<p>"什么事件?"</p>
|
||||
<p>"使徒会晤。"艾丽丝说,"据说有几个使徒会在魔界的某个地方会面,讨论赫尔德的计划。"</p>
|
||||
<p>林克眼中闪过光芒:"哪些使徒?"</p>
|
||||
<p>"不确定。但据说...米歇尔可能会出现。"</p>
|
||||
<p>"米歇尔...第七使徒,圣者。"</p>
|
||||
<p>林克站起身:"如果能见到他,也许能获得对抗赫尔德的方法。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百三十八章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-137.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-139.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-108.html" class="sidebar-chapter ">第108章:瘟疫之源</a>
|
||||
<a href="chapter-109.html" class="sidebar-chapter ">第109章:卡勒特之初</a>
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter current">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(138)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,936 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>人偶玄关 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 14</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>第二天,GSD带着林克和赛丽亚来到人偶玄关。</p>
|
||||
<p>与龙人之塔不同,这里是一座巨大的宫殿,到处都是精致的雕像和人偶。但空气中弥漫着一股诡异的气息,让人不寒而栗。</p>
|
||||
<p>"这里是……人偶玄关?"赛丽亚紧紧跟在GSD身后,"感觉好阴森……"</p>
|
||||
<p>"小心点。"GSD停下脚步,"这里的怪物和龙人不同,它们……曾经是活生生的人。"</p>
|
||||
<p>"什么?"林克一惊。</p>
|
||||
<p>"被天空之城的魔力侵蚀,变成了人偶。"GSD的声音有些低沉,"很久以前,有一支冒险队来这里探险,结果全军覆没。他们的灵魂被囚禁在人偶里,永远无法解脱。"</p>
|
||||
<p>"那我们……"</p>
|
||||
<p>"帮他们解脱吧。"GSD抬起拐杖,"这是唯一能做的事。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>刚走进宫殿大厅,四周的雕像突然动了!</p>
|
||||
<p>那些精致的人偶睁开了眼睛,空洞的眼眶中闪烁着幽绿色的光芒。它们缓缓站起身,手中出现了各种各样的武器。</p>
|
||||
<p>"来了。"GSD说,"这次你们来试试,我在旁边看着。"</p>
|
||||
<p>林克握紧光剑,点点头。</p>
|
||||
<p>"好!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>人偶们的攻击方式比龙人更加诡异。</p>
|
||||
<p>它们没有痛觉,不知疲倦,即使被斩断手臂也会继续攻击。而且它们配合默契,像是受过严格训练的士兵。</p>
|
||||
<p>"这些家伙……"林克挥舞光剑斩断一只人偶的头颅,但更多的人偶涌了上来。</p>
|
||||
<p>"数量太多了!"</p>
|
||||
<p>他立刻切换武器,拔出太刀霜刃,身形变得飘忽不定。</p>
|
||||
<p>"不错。"GSD在一旁点评,"但你的攻击太单一了。"</p>
|
||||
<p>"什么意思?"</p>
|
||||
<p>"人偶的核心不止一个。"GSD说,"看好了。"</p>
|
||||
<p>他抬起手,一道波动剑气射出,直接贯穿了它们胸口的水晶!</p>
|
||||
<p>"那是……核心?"</p>
|
||||
<p>"每个人偶的胸口都有一块魔力水晶,那才是它们的真正要害。"GSD说,"你的剑很快,但如果不命中要害,只是浪费体力。"</p>
|
||||
<p>林克恍然大悟。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,宫殿深处传来一阵低沉的笑声。</p>
|
||||
<p>"呵呵呵……有趣的小鬼……"</p>
|
||||
<p>一个身穿华丽铠甲的人偶从阴影中走出。它比其他人大得多,手中握着一把巨大的战斧。</p>
|
||||
<p>"人偶之王……"GSD的表情变得严肃,"终于出现了。"</p>
|
||||
<p>"那个瞎子……"人偶之王看着GSD,声音中带着怨恨,"二十年前,你就是从这里杀出去的……"</p>
|
||||
<p>"你记得我?"GSD微微侧头。</p>
|
||||
<p>"怎么可能忘记!"人偶之王举起战斧,"当年的那支冒险队,就是我的队伍!是你害死了他们!"</p>
|
||||
<p>GSD沉默了一会儿,然后叹了口气。</p>
|
||||
<p>"原来如此……你就是当年的那个队长。"</p>
|
||||
<p>"闭嘴!"人偶之王怒吼,"我要杀了你,为我的兄弟们报仇!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克,赛丽亚,退后。"GSD说,"这个家伙,让我来。"</p>
|
||||
<p>他第一次拔出了腰间的剑。</p>
|
||||
<p>那是一把通体漆黑的长剑,剑身上缠绕着暗红色的纹路,散发着令人心悸的气息。</p>
|
||||
<p>"阿修罗之剑。"GSD轻声说,"我已经很久没用过它了。"</p>
|
||||
<p>人偶之王的战斧斩下,带着撕裂空气的呼啸声。</p>
|
||||
<p>但GSD只是轻轻抬剑,就挡住了这一击!</p>
|
||||
<p>"你的力量比二十年前强了不少。"GSD说,"但……还是不够。"</p>
|
||||
<p>他的剑身上突然爆发出耀眼的光芒——不,那不是光,而是纯粹的波动之力!</p>
|
||||
<p>"觉醒·暗天波动眼。"</p>
|
||||
<p>GSD的身后,出现了一个巨大的眼睛虚影。那是一只紧闭的眼睛,但当它缓缓睁开时,整个世界都仿佛陷入了黑暗!</p>
|
||||
<p>"这……这是什么?!"人偶之王惊恐地后退。</p>
|
||||
<p>"阿修罗的觉醒技能。"GSD说,"用波动之力,创造一个属于我的世界。"</p>
|
||||
<p>在那只巨眼的注视下,人偶之王的身体开始崩解。</p>
|
||||
<p>"不……不可能……"人偶之王跪倒在地,"我明明已经变得这么强了……"</p>
|
||||
<p>"力量本身没有对错。"GSD收起剑,"但你选择了错误的道路。"</p>
|
||||
<p>"现在,安息吧。"</p>
|
||||
<p>"轰——!!!"</p>
|
||||
<p>人偶之王的身体在波动之力中彻底消散。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当一切恢复平静时,林克和赛丽亚依然愣在原地。</p>
|
||||
<p>刚才那一幕……太震撼了。</p>
|
||||
<p>GSD身后的那只巨眼,那种仿佛能掌控一切的力量……</p>
|
||||
<p>"师父……"林克的声音有些颤抖,"那就是……觉醒?"</p>
|
||||
<p>"嗯。"GSD点点头,"阿修罗的觉醒技能——暗天波动眼。"</p>
|
||||
<p>"好强……"</p>
|
||||
<p>"你也有一天能达到这个境界的。"GSD拍了拍林克的肩膀,"剑魂的觉醒,叫做'极·鬼剑术'。当你真正掌握剑魂的精髓时,就能领悟它。"</p>
|
||||
<p>"极·鬼剑术……"</p>
|
||||
<p>林克握紧拳头,眼中闪烁着渴望的光芒。</p>
|
||||
<p>总有一天,他也要变得像师父一样强!</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开人偶玄关时,GSD将一块人偶之王的魔力核心交给了林克。</p>
|
||||
<p>"这个可以用来强化你的短剑影牙。"他说。</p>
|
||||
<p>"谢谢师父!"</p>
|
||||
<p>"不用谢。"GSD转身看向天空之城的更高处,"接下来的路,就要靠你们自己了。"</p>
|
||||
<p>"您不继续带我们了吗?"赛丽亚问。</p>
|
||||
<p>"嗯。"GSD点点头,"石巨人塔以上的区域,对你们来说还太危险。你们先在龙人之塔和人偶玄关修炼,等实力足够了再往上走。"</p>
|
||||
<p>"我明白了。"林克郑重地说,"我们不会让您失望的。"</p>
|
||||
<p>GSD微微一笑,转身向传送阵走去。</p>
|
||||
<p>"我等着你们的好消息。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第十四章完)</p>
|
||||
<p><em>未完待续……</em></p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-13.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-15.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-1.html" class="sidebar-chapter ">第1章:洛兰的风</a>
|
||||
<a href="chapter-2.html" class="sidebar-chapter ">第2章:洛兰深处</a>
|
||||
<a href="chapter-3.html" class="sidebar-chapter ">第3章:幽暗密林</a>
|
||||
<a href="chapter-4.html" class="sidebar-chapter ">第4章:幽暗密林深处</a>
|
||||
<a href="chapter-5.html" class="sidebar-chapter ">第5章:雷鸣废墟</a>
|
||||
<a href="chapter-6.html" class="sidebar-chapter ">第6章:格拉卡</a>
|
||||
<a href="chapter-7.html" class="sidebar-chapter ">第7章:烈焰格拉卡</a>
|
||||
<a href="chapter-8.html" class="sidebar-chapter ">第8章:冰霜幽暗密林</a>
|
||||
<a href="chapter-9.html" class="sidebar-chapter ">第9章:转职之路</a>
|
||||
<a href="chapter-10.html" class="sidebar-chapter ">第10章:暗黑雷鸣废墟</a>
|
||||
<a href="chapter-11.html" class="sidebar-chapter ">第11章:剑魂转职仪式</a>
|
||||
<a href="chapter-12.html" class="sidebar-chapter ">第12章:西海岸</a>
|
||||
<a href="chapter-13.html" class="sidebar-chapter ">第13章:龙人之塔</a>
|
||||
<a href="chapter-14.html" class="sidebar-chapter current">第14章:人偶玄关</a>
|
||||
<a href="chapter-15.html" class="sidebar-chapter ">第15章:石巨人塔</a>
|
||||
<a href="chapter-16.html" class="sidebar-chapter ">第16章:黑暗玄廊</a>
|
||||
<a href="chapter-17.html" class="sidebar-chapter ">第17章:城主宫殿</a>
|
||||
<a href="chapter-18.html" class="sidebar-chapter ">第18章:番外·悬空城</a>
|
||||
<a href="chapter-19.html" class="sidebar-chapter ">第19章:天帷巨兽·神殿外围</a>
|
||||
<a href="chapter-20.html" class="sidebar-chapter ">第20章:树精丛林</a>
|
||||
<a href="chapter-21.html" class="sidebar-chapter ">第21章:炼狱</a>
|
||||
<a href="chapter-22.html" class="sidebar-chapter ">第22章:西海岸的闲暇</a>
|
||||
<a href="chapter-23.html" class="sidebar-chapter ">第23章:极昼</a>
|
||||
<a href="chapter-24.html" class="sidebar-chapter ">第24章:第一脊椎</a>
|
||||
<a href="chapter-25.html" class="sidebar-chapter ">第25章:赫顿玛尔的准备</a>
|
||||
<a href="chapter-26.html" class="sidebar-chapter ">第26章:第二脊椎</a>
|
||||
<a href="chapter-27.html" class="sidebar-chapter ">第27章:重逢的温柔</a>
|
||||
<a href="chapter-28.html" class="sidebar-chapter ">第28章:暗精灵的委托</a>
|
||||
<a href="chapter-29.html" class="sidebar-chapter ">第29章:阿法利亚营地</a>
|
||||
<a href="chapter-30.html" class="sidebar-chapter ">第30章:浅栖之地</a>
|
||||
<a href="chapter-31.html" class="sidebar-chapter ">第31章:蜘蛛洞穴</a>
|
||||
<a href="chapter-32.html" class="sidebar-chapter ">第32章:克伦特的委托</a>
|
||||
<a href="chapter-33.html" class="sidebar-chapter ">第33章:暗精灵墓地·左翼守卫</a>
|
||||
<a href="chapter-34.html" class="sidebar-chapter ">第34章:暗精灵墓地·剩余三将军</a>
|
||||
<a href="chapter-35.html" class="sidebar-chapter ">第35章:邪龙斯皮兹</a>
|
||||
<a href="chapter-36.html" class="sidebar-chapter ">第36章:莎兰的探望</a>
|
||||
<a href="chapter-37.html" class="sidebar-chapter ">第37章:暗影迷宫·影子剑士</a>
|
||||
<a href="chapter-38.html" class="sidebar-chapter ">第38章:熔岩穴·泰坦之怒</a>
|
||||
<a href="chapter-39.html" class="sidebar-chapter ">第39章:暗黑城入口·无头骑士</a>
|
||||
<a href="chapter-40.html" class="sidebar-chapter ">第40章:万年雪山·冰心少年</a>
|
||||
<a href="chapter-41.html" class="sidebar-chapter ">第41章:敏泰的加入</a>
|
||||
<a href="chapter-42.html" class="sidebar-chapter ">第42章:山脊·野兽师</a>
|
||||
<a href="chapter-43.html" class="sidebar-chapter ">第43章:番外·雪山温泉</a>
|
||||
<a href="chapter-44.html" class="sidebar-chapter ">第44章:白色废墟</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(14)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,982 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>复仇之剑 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 140</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>中央公园外围,一片荒芜的平原。</p>
|
||||
<p>林克独自一人站在那里,等待着对手的出现。</p>
|
||||
<p>艾丽丝和尼梅尔想要跟来,但被他拒绝了。这是他和卡尔之间的恩怨,他要亲手了结。</p>
|
||||
<p>"卡西利亚斯的指点...米歇尔的建议...让我看看,我进步了多少。"</p>
|
||||
<p>他握紧细雪之舞,感受着剑身传来的冰凉触感。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>远处,一股恐怖的气息正在接近。</p>
|
||||
<p>大地开始震颤,空气中弥漫着血腥味。紫色的闪电在天空中闪烁,仿佛预示着灾难的降临。</p>
|
||||
<p>然后,他出现了。</p>
|
||||
<p>铁血卡尔。</p>
|
||||
<p>他的外表发生了巨大的变化——暗红色的铠甲变得更加厚重,上面刻满了诡异的符文。他的皮肤变成了苍白色,眼睛燃烧着血色的火焰。他手中的巨剑「血魂」比之前更大,剑身上流动着仿佛活物般的红色能量。</p>
|
||||
<p>"林克..."卡尔的声音沙哑而充满仇恨,"你让我尝到了失败的耻辱。"</p>
|
||||
<p>他举起巨剑,指向林克:"赫尔德大人给了我新的力量。这一次,我会把你撕成碎片!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"血魔化!"</p>
|
||||
<p>卡尔低吼一声,全身被血色的光芒包裹。他的体型暴涨,肌肉变得更加粗壮,身上散发出令人窒息的压迫感。</p>
|
||||
<p>"来吧!"他大吼,冲向林克。</p>
|
||||
<p>林克深吸一口气,进入流心状态。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>两道身影在平原上碰撞,激荡起巨大的能量波动。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗从一开始就进入了白热化。</p>
|
||||
<p>卡尔的每一击都带着毁天灭地的力量。巨剑劈下,地面裂开数十米的沟壑。剑气纵横,将周围的岩石全部粉碎。</p>
|
||||
<p>林克不断闪避,同时寻找反击的机会。</p>
|
||||
<p>"这家伙...比之前强太多了!"</p>
|
||||
<p>他想起上次和卡尔的战斗。那时候,卡尔的铁壁防御虽然棘手,但攻击速度很慢。现在,卡尔不仅力量增强了,速度也大大提升。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>林克腾空而起,躲过卡尔的横扫。同时,他的光剑划出一道弧线,刺向卡尔的肩膀。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>剑尖刺中了卡尔的铠甲,但只留下了一道浅浅的痕迹。</p>
|
||||
<p>"没用的!"卡尔狂笑,"我的防御比之前强十倍!你的剑根本伤不了我!"</p>
|
||||
<p>他挥动巨剑,一道血色的剑气横扫而出。</p>
|
||||
<p>"血刃风暴!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>无数道血色剑气从卡尔身上爆发,形成一道恐怖的剑气风暴。整个平原被剑气覆盖,根本没有躲避的空间。</p>
|
||||
<p>林克咬牙,举起细雪之舞。</p>
|
||||
<p>"极·鬼剑术(斩钢式)!"</p>
|
||||
<p>他将所有力量集中在剑上,挥出一道冰蓝色的剑气,硬抗卡尔的攻击。</p>
|
||||
<p>"轰!"</p>
|
||||
<p>两道剑气碰撞,爆发出刺眼的光芒。林克被震飞了数十米,在地上拖出一道长长的痕迹。</p>
|
||||
<p>他吐出一口鲜血,但眼神依然坚定。</p>
|
||||
<p>"还不够..."</p>
|
||||
<p>他站起身,擦去嘴角的血迹。</p>
|
||||
<p>"卡西利亚斯说过,剑是灵魂的延伸。"</p>
|
||||
<p>他闭上眼睛,感受体内的力量。</p>
|
||||
<p>"我不是在战斗,而是在守护。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>卡尔看到林克闭上了眼睛,冷笑一声:"放弃了?那我就送你上路!"</p>
|
||||
<p>他举起巨剑,朝林克劈下。</p>
|
||||
<p>但就在剑即将命中林克的瞬间,林克的眼睛猛然睁开。</p>
|
||||
<p>"极·神剑术(瞬影斩)!"</p>
|
||||
<p>他的身影突然消失,出现在卡尔的身后。</p>
|
||||
<p>"什么?!"卡尔震惊。</p>
|
||||
<p>林克的光剑刺入了卡尔的后背,穿透了那层厚重的防御。</p>
|
||||
<p>"这是...不可能!"</p>
|
||||
<p>林克拔出剑,再次移动。他的身影如同鬼魅,在卡尔周围不断闪现,每一剑都精准地命中卡尔的弱点。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>连续的攻击让卡尔无法反应,他的身上出现了越来越多的伤口。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"可恶!"卡尔怒吼,"你以为这样就能打败我?!"</p>
|
||||
<p>他身上的血色光芒更盛,力量再次暴涨。</p>
|
||||
<p>"狂暴·极限!"</p>
|
||||
<p>他的眼睛完全变成了血红色,身上散发着恐怖的气息。他不顾身上的伤口,疯狂地挥舞巨剑,将周围的一切都纳入攻击范围。</p>
|
||||
<p>林克被迫后退,但他的眼神没有恐惧。</p>
|
||||
<p>"米歇尔说过,我有改变因果的能力。"</p>
|
||||
<p>他握紧细雪之舞,冰蓝色的剑气冲天而起。</p>
|
||||
<p>"如果注定要赢,那就让我赢吧!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"万剑归宗!"</p>
|
||||
<p>林克召唤出无数把光剑,每一把都带着他的意志和灵魂。</p>
|
||||
<p>剑雨落下,穿透了卡尔的防御,刺入了他的身体。</p>
|
||||
<p>"啊啊啊!"</p>
|
||||
<p>卡尔发出痛苦的吼叫,他的血魔化开始崩溃。身上的符文一个个碎裂,血色的光芒逐渐消散。</p>
|
||||
<p>"不可能...我...我被赫尔德大人赐予了力量...怎么会..."</p>
|
||||
<p>林克走到他面前,光剑指着他。</p>
|
||||
<p>"你的力量,是建立在仇恨之上的。"林克说,"而我,是为了守护而战。这就是我们的区别。"</p>
|
||||
<p>卡尔看着他,血色的眼睛逐渐恢复了原来的颜色。</p>
|
||||
<p>"守护...吗..."</p>
|
||||
<p>他苦笑一声:"我曾经也有想要守护的人...但赫尔德大人...夺走了她..."</p>
|
||||
<p>他的身体开始崩溃,血色的能量从体内涌出。</p>
|
||||
<p>"我...是个失败品..."他看向林克,"小心...赫尔德大人...还有更强的棋子..."</p>
|
||||
<p>说完,他的身体炸裂开来,化作了无数血色的光点,消散在空气中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束了。</p>
|
||||
<p>林克站在原地,看着卡尔消失的地方。</p>
|
||||
<p>"铁血卡尔...原来你也只是一个受害者。"</p>
|
||||
<p>他收起细雪之舞,转身离开。</p>
|
||||
<p>身后,平原上布满了战斗的痕迹。破碎的岩石、深深的沟壑、以及那些尚未消散的血色能量...</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到中央公园,艾丽丝和尼梅尔迎了上来。</p>
|
||||
<p>"林克,你没事吧?"艾丽丝关切地问。</p>
|
||||
<p>"没事。"林克摇头,"卡尔已经死了。"</p>
|
||||
<p>尼梅尔松了口气:"太好了!那个家伙太可怕了..."</p>
|
||||
<p>林克看向艾丽丝,心中涌起复杂的情绪。</p>
|
||||
<p>灵魂之源...在她的体内。</p>
|
||||
<p>"艾丽丝。"他开口。</p>
|
||||
<p>"嗯?"</p>
|
||||
<p>"接下来,我们去寂静城。"他说,"我要去找卢克。"</p>
|
||||
<p>艾丽丝点头:"好。我也一起去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天,三人离开中央公园,前往寂静城。</p>
|
||||
<p>林克回想着米歇尔的话:时间之钥、空间之心、灵魂之源。</p>
|
||||
<p>这三样东西,是阻止赫尔德的关键。</p>
|
||||
<p>而灵魂之源...就在艾丽丝体内。</p>
|
||||
<p>他暗暗发誓,一定要找到方法帮她融合,而不是让她牺牲。</p>
|
||||
<p>"等着我,赫尔德。我会阻止你的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-139.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-141.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-110.html" class="sidebar-chapter ">第110章:无法地带</a>
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter current">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(140)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,966 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>寂静城再访 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 141</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城,林克曾经拯救过的地方。</p>
|
||||
<p>当三人踏入这座城市时,熟悉的感觉涌上心头。高耸的建筑、神秘的能量、以及那个坐在古老能量核心旁边的老人。</p>
|
||||
<p>卢克。</p>
|
||||
<p>海伯伦星的王,第八使徒,制造者。</p>
|
||||
<p>他依然坐在那个位置,仿佛从未移动过。浑浊的眼睛看向林克,露出一丝欣慰的微笑。</p>
|
||||
<p>"年轻人,你回来了。"</p>
|
||||
<p>"卢克爷爷。"林克走上前,"我有事想请您帮忙。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>卢克听完林克的叙述,陷入沉思。</p>
|
||||
<p>"时间之钥..."他喃喃自语,"米歇尔告诉你,那是阻止赫尔德的关键之一?"</p>
|
||||
<p>"是的。"林克点头,"他说时间之钥在您这里。"</p>
|
||||
<p>卢克沉默了片刻,然后叹了口气:"米歇尔...还是那么喜欢多管闲事。"</p>
|
||||
<p>他站起身,走向城市深处:"时间之钥确实在我这里。但它不是一件简单的物品,而是一种力量。只有通过试炼的人,才能获得它。"</p>
|
||||
<p>"我愿意接受试炼。"林克说。</p>
|
||||
<p>"不急。"卢克摆了摆手,"你刚刚经历了一场大战,需要休息。明天再进行试炼。"</p>
|
||||
<p>他看向艾丽丝和尼梅尔:"你们也累了,先在这里休息一晚。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,寂静城的能量核心散发着柔和的光芒。</p>
|
||||
<p>林克独自站在城墙上,看着魔界扭曲的天空。</p>
|
||||
<p>"时间之钥、空间之心、灵魂之源..."</p>
|
||||
<p>他喃喃自语,思考着接下来的计划。</p>
|
||||
<p>灵魂之源在艾丽丝体内,这是最棘手的问题。米歇尔说,如果强行取出,艾丽丝可能会死。</p>
|
||||
<p>"我一定要找到其他方法..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克..."</p>
|
||||
<p>一个轻柔的声音从身后传来。</p>
|
||||
<p>林克转身,看到艾丽丝站在那里。紫色的长发在微风中轻轻飘动,她的眼神带着一丝忧虑。</p>
|
||||
<p>"艾丽丝?怎么了?"</p>
|
||||
<p>艾丽丝走到他身边,和他并肩站着。</p>
|
||||
<p>"我能问你一个问题吗?"她说。</p>
|
||||
<p>"当然。"</p>
|
||||
<p>艾丽丝犹豫了一下,然后开口:"在寂静岭,米歇尔和你说什么了?"</p>
|
||||
<p>林克心中一紧。他没有告诉艾丽丝关于灵魂之源的事,但他没想到她会主动问。</p>
|
||||
<p>"没什么...只是一些建议。"</p>
|
||||
<p>艾丽丝看着他,紫色的眼睛里带着复杂的光芒:"林克,我知道你在隐瞒什么。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"从寂静岭回来后,你看我的眼神就变得很奇怪。"艾丽丝轻声说,"像是在担心什么...又像是在犹豫什么。"</p>
|
||||
<p>她低下头:"是因为我体内有什么东西吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>他没想到艾丽丝这么敏感。她曾经是赫尔德的傀儡,对很多事情都有直觉。</p>
|
||||
<p>"艾丽丝..."</p>
|
||||
<p>"告诉我真相。"艾丽丝抬起头,眼中带着坚定,"不管是什么,我都有权知道。"</p>
|
||||
<p>林克深吸一口气,决定告诉她。</p>
|
||||
<p>"米歇尔说...你的体内有'灵魂之源'的一部分。"</p>
|
||||
<p>"灵魂之源?"</p>
|
||||
<p>"是赫尔德用来控制你的工具,也是创新世纪的重要组成部分。"林克说,"如果取出它,你可能会死。"</p>
|
||||
<p>艾丽丝的脸色变得苍白。</p>
|
||||
<p>"我...我体内有这样的东西?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握住她的手:"但米歇尔也说了另一个方法。如果你能让自己的灵魂足够强大,就可以与灵魂之源融合。那样你不仅能活下来,还能获得一部分使徒的力量。"</p>
|
||||
<p>"融合..."艾丽丝喃喃自语。</p>
|
||||
<p>她看向林克,眼中闪过一丝脆弱:"林克,我怕...我怕自己做不到..."</p>
|
||||
<p>林克将她拥入怀中:"你不需要一个人做到。我会帮你。"</p>
|
||||
<p>"林克..."</p>
|
||||
<p>"我答应你,不管发生什么,我都不会让你死。"林克在她耳边轻声说,"你是我的人,我会守护你。"</p>
|
||||
<p>艾丽丝的眼泪滑落,她紧紧抱住林克:"谢谢你...谢谢你..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人在城墙上相拥,月光洒在他们身上。</p>
|
||||
<p>艾丽丝抬起头,看着林克的眼睛:"林克...今晚...陪着我好吗?"</p>
|
||||
<p>林克看着她含泪的眼睛,点了点头。</p>
|
||||
<p>他低下头,轻轻吻住她的唇。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人来到林克的房间。</p>
|
||||
<p>艾丽丝主动解开了自己的长袍,露出白皙的肌肤。林克将她抱起,轻轻放在床上。</p>
|
||||
<p>"艾丽丝..."</p>
|
||||
<p>"林克,我爱你。"艾丽丝轻声说,"不管未来会发生什么,我只想记住这一刻。"</p>
|
||||
<p>林克俯下身,吻住她的唇。两人的身体交织在一起,在这个寂静的夜晚,彼此给予温暖和力量。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>月光透过窗户洒进房间,照在两人的身上。</p>
|
||||
<p>林克温柔地亲吻着艾丽丝的额头、脸颊、嘴唇。他的动作很轻,生怕伤害到她。</p>
|
||||
<p>艾丽丝紧紧抱着他,感受着他的体温和心跳。每一次触碰,都让她感到安心。</p>
|
||||
<p>"林克...林克..."</p>
|
||||
<p>她一遍遍念着他的名字,仿佛这是世界上最美好的词语。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>不知过了多久,两人终于累了。</p>
|
||||
<p>艾丽丝蜷缩在林克怀里,脸上带着满足的笑容。</p>
|
||||
<p>"林克..."她轻声说,"我感觉...体内的力量好像变强了一些。"</p>
|
||||
<p>"什么?"林克有些惊讶。</p>
|
||||
<p>"灵魂之源...好像在和我融合。"艾丽丝闭上眼睛,"也许是因为...我对你敞开了心扉。"</p>
|
||||
<p>林克愣了一下,然后露出微笑。</p>
|
||||
<p>"那就继续融合吧。"他搂紧她,"我会一直陪着你。"</p>
|
||||
<p>"嗯..."艾丽丝靠在他胸口,很快沉入了梦乡。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,林克来到能量核心前。</p>
|
||||
<p>卢克已经在等他了。</p>
|
||||
<p>"准备好了吗?"老人问。</p>
|
||||
<p>"准备好了。"林克点头。</p>
|
||||
<p>卢克看着他,浑浊的眼睛里闪过一丝欣慰:"昨晚,艾丽丝的灵魂波动变得更强了。你做得很好。"</p>
|
||||
<p>林克脸微微一红:"只是...陪着她。"</p>
|
||||
<p>卢克笑了笑:"灵魂之源会在她敞开心扉时逐渐融合。你做得很好。"</p>
|
||||
<p>他转身,走向城市深处:"现在,开始试炼吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-140.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-142.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-111.html" class="sidebar-chapter ">第111章:暗黑圣战</a>
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter current">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(141)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,976 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>时间之钥 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 142</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>寂静城深处,一扇古老的大门矗立在林克面前。</p>
|
||||
<p>门上刻满了复杂的符文,散发着淡淡的金色光芒。卢克站在门边,浑浊的眼睛看着林克。</p>
|
||||
<p>"这扇门后面,是'时间回廊'。"卢克说,"在那里,时间是不稳定的。你会遇到过去的敌人、过去的自己...甚至可能的未来。"</p>
|
||||
<p>"只有战胜这一切,才能获得时间之钥。"</p>
|
||||
<p>林克握紧细雪之舞:"我明白了。"</p>
|
||||
<p>"还有一件事。"卢克提醒道,"在时间回廊中,你不能使用所有的力量。你的体力、魔力都会被压制。唯一的依靠,是你的意志和剑术。"</p>
|
||||
<p>林克点头:"我不会让卢克爷爷失望。"</p>
|
||||
<p>他推开大门,踏入时间回廊。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>时间回廊是一个奇异的空间。</p>
|
||||
<p>四周是流动的光影,仿佛无数画面在眼前闪过。林克看到自己的过去——从洛兰出发、遇见赛丽亚、打败希洛克...一幕幕如同幻灯片。</p>
|
||||
<p>"这是...我的记忆?"</p>
|
||||
<p>"没错。"一个声音响起,"时间回廊记录着一切。"</p>
|
||||
<p>林克看向前方,那里站着一个身影。</p>
|
||||
<p>银色的铠甲,红色的头发,手中握着一把巨剑。</p>
|
||||
<p>"巴恩...?!"</p>
|
||||
<p>巴恩·巴休特,曾经在天帷巨兽遇到的对手。那时候,林克还只是一个初出茅庐的剑士。</p>
|
||||
<p>"好久不见,林克。"巴恩微笑道,"在时间回廊里,我以你记忆中的样子存在。"</p>
|
||||
<p>他举起巨剑:"来吧,让我看看你进步了多少!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗开始。</p>
|
||||
<p>林克挥剑迎上,但他发现自己的力量被压制了。原本可以轻松使出的技能,现在却需要消耗更多的体力。</p>
|
||||
<p>"这就是时间回廊的限制..."</p>
|
||||
<p>他咬紧牙关,与巴恩交战。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>两剑碰撞,林克被震退了几步。虽然他的实力已经远超当年的巴恩,但在压制状态下,这场战斗变得艰难。</p>
|
||||
<p>"你的剑术确实进步了。"巴恩说,"但还不够。"</p>
|
||||
<p>他挥动巨剑,一道剑气斩出。林克侧身闪避,同时反击。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>光剑刺向巴恩,但被巨剑挡下。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗持续了很长时间。</p>
|
||||
<p>林克的体力在快速消耗,但他没有放弃。他回想着卡西利亚斯的教导——剑是灵魂的延伸。</p>
|
||||
<p>"在压制状态下,我不能依赖力量...只能依赖剑术本身。"</p>
|
||||
<p>他闭上眼睛,感受周围的气息。</p>
|
||||
<p>巴恩的攻击模式、剑气轨迹、破绽位置...一切都在他脑海中清晰起来。</p>
|
||||
<p>"找到了。"</p>
|
||||
<p>他睁开眼睛,迎上巴恩的攻击。</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>他将巴恩击飞,然后连续攻击。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>闪电般的四连斩,巴恩被击倒在地。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>巴恩的身影逐渐消散,化作光点融入时间回廊。</p>
|
||||
<p>"不错。"一个声音响起,"你通过了第一关。"</p>
|
||||
<p>林克喘着气,看向前方。</p>
|
||||
<p>那里又出现了新的身影。</p>
|
||||
<p>光剑、金色铠甲、冷静的眼神...</p>
|
||||
<p>"这是...我?"</p>
|
||||
<p>"这是可能的未来。"那个身影开口,"如果你继续成长,就会成为我。"</p>
|
||||
<p>"未来的我?"</p>
|
||||
<p>"是的。"未来的林克举起光剑,"战胜我,证明你有资格获得时间之钥。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>与自己战斗,是最困难的事。</p>
|
||||
<p>未来的林克知道林克所有的招式、所有习惯。每一次攻击都被预判,每一次闪避都被跟踪。</p>
|
||||
<p>"可恶..."</p>
|
||||
<p>林克被压制得无法还手。他的体力已经接近极限,而未来的自己似乎永远不会疲倦。</p>
|
||||
<p>"放弃吧。"未来的林克说,"你现在还太弱了。"</p>
|
||||
<p>"不..."</p>
|
||||
<p>林克咬牙站起来,"我不会放弃。"</p>
|
||||
<p>"为什么?你明知道赢不了。"</p>
|
||||
<p>"因为...我有要守护的人。"</p>
|
||||
<p>林克握紧细雪之舞,眼中闪过坚定的光芒。</p>
|
||||
<p>"赛丽亚、艾丽丝、敏泰、帕丽丝...还有所有我在乎的人。为了她们,我不能在这里倒下!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他冲向未来的自己,不顾一切地挥剑。</p>
|
||||
<p>每一次攻击都被挡下,但他没有停止。他在寻找——寻找一个破绽。</p>
|
||||
<p>终于,他发现了。</p>
|
||||
<p>未来的自己,虽然强大,但缺少一样东西——对现在的林克来说最重要的东西。</p>
|
||||
<p>"你太完美了。"林克说,"完美得...没有感情。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"我的剑,不是为了胜利,而是为了守护。"林克的眼神变得坚定,"而你...已经忘记了这一点。"</p>
|
||||
<p>他挥剑斩出,这次不是冰冷的剑气,而是带着温暖的光芒。</p>
|
||||
<p>"极·鬼剑术(斩铁式)!"</p>
|
||||
<p>剑光穿透了未来的自己,他缓缓消散。</p>
|
||||
<p>"看来...你找到了自己的路。"未来的林克微笑道,"去吧,获得你应得的力量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>时间回廊开始崩塌。</p>
|
||||
<p>无数光点汇聚在林克面前,形成一把金色的钥匙。</p>
|
||||
<p>那就是时间之钥。</p>
|
||||
<p>林克伸出手,握住了它。</p>
|
||||
<p>瞬间,一股温暖的力量涌入他的体内。他感觉到时间在他周围流动,过去、现在、未来...一切都变得清晰。</p>
|
||||
<p>"这就是...时间之钥的力量。"</p>
|
||||
<p>他闭上眼睛,感受着这股力量。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克睁开眼睛时,他发现自己回到了寂静城。</p>
|
||||
<p>卢克站在他面前,露出欣慰的笑容。</p>
|
||||
<p>"恭喜你,年轻人。你通过了试炼。"</p>
|
||||
<p>"谢谢卢克爷爷。"</p>
|
||||
<p>"时间之钥已经和你融为一体。"卢克说,"现在,你可以短暂地操控时间——让时间变慢、回溯几秒、甚至预知未来。"</p>
|
||||
<p>"但记住,这股力量消耗极大。用一次,你就会虚弱很长时间。"</p>
|
||||
<p>林克点头:"我会谨慎使用的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝和尼梅尔跑过来。</p>
|
||||
<p>"林克,你没事吧?"艾丽丝关切地问。</p>
|
||||
<p>"没事。"林克微笑道,"而且...我获得了时间之钥。"</p>
|
||||
<p>艾丽丝松了口气:"太好了。"</p>
|
||||
<p>卢克看着林克:"你现在有了时间之钥。接下来,你要面对的是最困难的部分——空间之心和灵魂之源。"</p>
|
||||
<p>"空间之心在赫尔德手中,灵魂之源在艾丽丝体内。"</p>
|
||||
<p>林克点头:"我知道。"</p>
|
||||
<p>他看向艾丽丝,心中暗暗下定决心。</p>
|
||||
<p>"不管多困难,我都会找到方法。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-141.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-143.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-112.html" class="sidebar-chapter ">第112章:昔日悲鸣</a>
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter current">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(142)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,971 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>翡翠梦魇 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 143</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>中央公园,莎莎的情报屋。</p>
|
||||
<p>"翡翠梦魇?"莎莎看着林克,"你们确定要去那里?"</p>
|
||||
<p>"是的。"林克点头,"听说那里可能有空间之心的线索。"</p>
|
||||
<p>莎莎叹了口气:"确实有这个传闻。但翡翠梦魇是一个非常危险的地方。"</p>
|
||||
<p>她拿出一本古旧的书籍,翻开一页:"翡翠梦魇原本是魔界的一片精灵森林,名叫'翡翠之森'。那里生活着魔界最后的精灵族。"</p>
|
||||
<p>"后来呢?"</p>
|
||||
<p>"赫尔德需要精灵族的力量来推动创新世纪,于是她诅咒了整片森林。"莎莎说,"精灵族被转化为梦魇生物,守护着森林的中心。据说,其中有一个特别强大的存在——翡翠守护者希尔薇。"</p>
|
||||
<p>"希尔薇..."林克记下这个名字。</p>
|
||||
<p>"她原本是精灵族的公主,被诅咒后成为了森林的守护者。任何进入森林的人,都会被她攻击。"</p>
|
||||
<p>莎莎合上书:"你们要去,必须做好觉悟。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>离开情报屋后,艾丽丝看向林克:"林克,你确定要去吗?那个希尔薇...听起来很可怜。"</p>
|
||||
<p>"我知道。"林克说,"但如果她真的守护着空间之心的线索,我们必须去。"</p>
|
||||
<p>尼梅尔握着他的手:"我陪你去。"</p>
|
||||
<p>艾丽丝也点了点头:"我也去。也许...我可以帮她解除诅咒。"</p>
|
||||
<p>林克看着艾丽丝:"你能做到?"</p>
|
||||
<p>"我不确定。"艾丽丝说,"但我体内有灵魂之源,那是赫尔德的力量。也许可以用它来对抗赫尔德的诅咒。"</p>
|
||||
<p>林克露出一丝欣慰的笑容:"那就试试。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天清晨,三人前往翡翠梦魇。</p>
|
||||
<p>翡翠梦魇位于中央公园的东南方向,是一片被黑暗笼罩的区域。从远处看,那里的树木都是扭曲的,叶子呈现出诡异的绿色光芒。</p>
|
||||
<p>"这里的气息...好压抑。"尼梅尔皱眉。</p>
|
||||
<p>林克握紧细雪之舞,踏入森林。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一进入森林,周围的景象就变了。</p>
|
||||
<p>天空中弥漫着绿色的雾气,树木发出诡异的呻吟声。地面上长满了带刺的藤蔓,不时地蠕动着,仿佛有生命一般。</p>
|
||||
<p>"小心!"艾丽丝大喊。</p>
|
||||
<p>几根藤蔓突然从地面窜出,朝三人袭来。林克挥剑斩断它们,但更多的藤蔓涌了过来。</p>
|
||||
<p>"这些藤蔓...是受诅咒的植物。"艾丽丝说,"它们被赫尔德的力量控制了。"</p>
|
||||
<p>林克连续挥剑,将藤蔓全部斩断:"走吧,继续前进。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人深入森林,遇到了越来越多的敌人。</p>
|
||||
<p>扭曲的树精、变异的野兽、幽灵般的精灵...每一个都被诅咒侵蚀,失去了理智。</p>
|
||||
<p>林克的剑斩断它们,艾丽丝的魔法焚烧它们,尼梅尔的短剑刺穿它们。</p>
|
||||
<p>"这些生物...曾经都是精灵族吗?"尼梅尔看着地上的尸体,有些悲伤。</p>
|
||||
<p>"是的。"艾丽丝轻声说,"它们被赫尔德诅咒,变成了现在这个样子。"</p>
|
||||
<p>林克沉默了片刻:"如果能解除诅咒,也许它们能恢复。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约一个时辰,三人来到了一片开阔地。</p>
|
||||
<p>中央是一棵巨大的古树,树干足有数十米粗,树冠遮天蔽日。树上刻满了诡异的符文,散发着绿色的光芒。</p>
|
||||
<p>"这是...世界树的残骸?"艾丽丝惊讶。</p>
|
||||
<p>在古树前方,站着一个身影。</p>
|
||||
<p>那是一个身穿绿色长裙的女子,长发如同翡翠般闪耀。她的眼睛是深邃的绿色,却没有任何感情。她手中握着一把由藤蔓编织而成的弓,背上背着一箭囊。</p>
|
||||
<p>"希尔薇..."林克认出了她。</p>
|
||||
<p>希尔薇看向三人,声音冰冷:"入侵者...你们来送死吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"希尔薇,我不想和你战斗。"林克说,"我来是为了寻找空间之心的线索。"</p>
|
||||
<p>"空间之心?"希尔薇冷笑,"那是赫尔德大人的东西。你们这些蝼蚁,也妄想得到?"</p>
|
||||
<p>她举起弓,一支箭矢凭空出现:"死在这里吧!"</p>
|
||||
<p>箭矢射出,带着绿色的光芒。林克侧身闪避,箭矢击中他身后的树木,树干瞬间枯萎。</p>
|
||||
<p>"这箭矢...有诅咒的力量。"艾丽丝说。</p>
|
||||
<p>希尔薇再次拉弓,这次射出了三支箭:"翡翠之雨!"</p>
|
||||
<p>无数箭矢从空中落下,如同绿色的暴雨。林克举起光剑,挡下射向自己的箭矢。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他腾空而起,朝希尔薇冲去。但希尔薇的身影突然消失,出现在几十米外的位置。</p>
|
||||
<p>"想抓住我?"希尔薇冷笑,"我是森林的守护者,在这片森林里,我可以自由移动。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗变得非常艰难。</p>
|
||||
<p>希尔薇不仅擅长远程攻击,还能利用森林的力量瞬移。每当林克靠近,她就会消失,出现在另一个位置,然后射出致命的箭矢。</p>
|
||||
<p>"这家伙...太狡猾了。"</p>
|
||||
<p>林克咬牙,再次尝试追击。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他的身影化作闪电,连续四次斩击。但希尔薇提前消失了,剑气只斩断了空气。</p>
|
||||
<p>"在我身后!"艾丽丝大喊。</p>
|
||||
<p>林克转身,看到希尔薇已经出现在艾丽丝和尼梅尔附近,箭矢正对着她们。</p>
|
||||
<p>"可恶!"</p>
|
||||
<p>林克使用瞬影斩,瞬间出现在希尔薇面前,挡住了她的箭矢。</p>
|
||||
<p>"什么?"希尔薇惊讶,"你能这么快移动?"</p>
|
||||
<p>"我不允许你伤害她们。"林克的眼神坚定。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希尔薇看着林克,眼中闪过一丝复杂的情绪。</p>
|
||||
<p>"你...为了保护她们,不惜冲到我面前?"</p>
|
||||
<p>"当然。"林克说,"她们是我重要的人。"</p>
|
||||
<p>希尔薇沉默了。那一瞬间,她眼中的冰冷似乎动摇了。</p>
|
||||
<p>"重要的人..."</p>
|
||||
<p>她喃喃自语,然后捂住头,痛苦地喊道:"不...不要想起...赫尔德大人的命令...我不能..."</p>
|
||||
<p>她的身上爆发出绿色的光芒,诅咒的力量在体内翻涌。</p>
|
||||
<p>"希尔薇!"艾丽丝冲上前,"她在被诅咒反噬!"</p>
|
||||
<p>林克看着痛苦挣扎的希尔薇,心中做出决定。</p>
|
||||
<p>"艾丽丝,你能帮她吗?"</p>
|
||||
<p>"我试试。"艾丽丝举起法杖,紫色的光芒凝聚,"灵魂之源的力量...请帮我压制这个诅咒!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>紫色的光芒笼罩希尔薇。</p>
|
||||
<p>艾丽丝将灵魂之源的力量引导出来,与希尔薇体内的诅咒对抗。</p>
|
||||
<p>"啊——!"希尔薇发出痛苦的吼叫。</p>
|
||||
<p>她的身体在绿色和紫色之间交替,诅咒的力量与灵魂之源激烈碰撞。</p>
|
||||
<p>林克紧张地看着这一幕。如果艾丽丝成功了,希尔薇就能解除诅咒;如果失败了,艾丽丝自己可能会受伤。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>终于,绿色的光芒开始消退。</p>
|
||||
<p>希尔薇身上的诅咒符文逐渐消失,她的眼睛恢复了清澈的绿色。她瘫倒在地,喘着粗气。</p>
|
||||
<p>"成功了..."艾丽丝虚弱地说,也差点倒下。</p>
|
||||
<p>林克连忙扶住艾丽丝,然后看向希尔薇。</p>
|
||||
<p>希尔薇抬起头,看着林克,眼中带着复杂的情绪。</p>
|
||||
<p>"你...为什么要帮我?"</p>
|
||||
<p>"因为你不应该被诅咒控制。"林克说,"你应该是自由的。"</p>
|
||||
<p>希尔薇愣住了,眼泪从她眼中滑落。</p>
|
||||
<p>"自由...我已经很久没有感受过了..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-142.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-144.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-113.html" class="sidebar-chapter ">第113章:凛冬</a>
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter current">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(143)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,960 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>诅咒的守护者 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 144</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>希尔薇坐在古树下,讲述着她的过去。</p>
|
||||
<p>"三百年前,翡翠之森是魔界最美的森林。"她说,"我的族人生活在这里,与自然和谐共处。"</p>
|
||||
<p>"那时候,我是精灵族的公主,被族人爱护着。"</p>
|
||||
<p>她的眼中闪过悲伤:"但赫尔德来了。她说需要精灵族的力量来推动一个伟大的计划,要求我们服从她。"</p>
|
||||
<p>"我们拒绝了。"希尔薇说,"精灵族不会成为任何人的工具。"</p>
|
||||
<p>"于是她诅咒了整片森林。"艾丽丝轻声说。</p>
|
||||
<p>"是的。"希尔薇点头,"她用空间魔法封锁了森林,然后用诅咒腐蚀了所有精灵。我的族人...一个接一个地变成了梦魇生物。"</p>
|
||||
<p>她低下头:"我试图保护他们,但赫尔德的力量太强了。最后,我也被诅咒了。"</p>
|
||||
<p>"她告诉我,如果我想解除诅咒,就必须守护这片森林,直到她需要的时候。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克听着希尔薇的叙述,心中涌起怒火。</p>
|
||||
<p>赫尔德...她为了自己的计划,牺牲了整个精灵族。</p>
|
||||
<p>"希尔薇,你恨赫尔德吗?"他问。</p>
|
||||
<p>希尔薇沉默了片刻:"恨?我曾经恨过。但诅咒让我失去了仇恨,也失去了所有的感情。"</p>
|
||||
<p>她看向林克:"但现在...诅咒被压制了,我感觉到了...久违的温暖。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"艾丽丝,你的力量能完全解除诅咒吗?"林克问。</p>
|
||||
<p>艾丽丝摇头:"我只压制了表面层的诅咒。诅咒的核心...还在希尔薇体内。"</p>
|
||||
<p>"核心?"</p>
|
||||
<p>"是的。"艾丽丝说,"赫尔德的诅咒是一种'空间诅咒',它将希尔薇的灵魂和空间魔法绑定在一起。如果要完全解除,需要切断这种绑定。"</p>
|
||||
<p>希尔薇看着艾丽丝:"你能做到吗?"</p>
|
||||
<p>"我不确定。"艾丽丝说,"但如果林克愿意用时间之钥的力量帮我,也许可以。"</p>
|
||||
<p>林克看向希尔薇:"你愿意尝试吗?"</p>
|
||||
<p>希尔薇犹豫了片刻,然后点头:"我愿意。我不想再被诅咒控制了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>解除诅咒的仪式在古树下进行。</p>
|
||||
<p>艾丽丝站在希尔薇面前,双手放在她的额头上。紫色的光芒从艾丽丝体内涌出,进入希尔薇的身体。</p>
|
||||
<p>林克站在一旁,准备使用时间之钥的力量。</p>
|
||||
<p>"时间之钥,让时间在我周围缓慢流动。"他在心中默念。</p>
|
||||
<p>金色的光芒从林克体内散发,笼罩了整个仪式区域。时间变得缓慢,艾丽丝和希尔薇的动作仿佛被放慢了数倍。</p>
|
||||
<p>"就是现在!"艾丽丝大喊,"林克,用你的剑斩断诅咒的锁链!"</p>
|
||||
<p>林克举起细雪之舞,剑身上凝聚着金色的光芒。</p>
|
||||
<p>他挥剑斩下,剑光穿透了希尔薇的身体——不是伤害她,而是斩断了她灵魂中的诅咒锁链。</p>
|
||||
<p>"破!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>绿色的光芒从希尔薇体内爆发出来,那是诅咒被剥离的象征。</p>
|
||||
<p>希尔薇发出痛苦的吼叫,但她没有退缩。她咬紧牙关,承受着这一切。</p>
|
||||
<p>艾丽丝继续引导力量,将诅咒一点一点地从希尔薇体内抽离。</p>
|
||||
<p>终于,最后一道绿色的锁链被斩断。</p>
|
||||
<p>希尔薇的身体被光芒笼罩,当光芒散去时,她的身上不再有任何诅咒的痕迹。</p>
|
||||
<p>她的绿色长发变得更加明亮,眼睛恢复了清澈,身上散发出一股自然的气息。</p>
|
||||
<p>"诅咒...解除了?"她难以置信地看着自己的手。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"成功了!"尼梅尔欢呼。</p>
|
||||
<p>艾丽丝虚弱地倒下,林克连忙扶住她。</p>
|
||||
<p>"辛苦了。"他轻声说。</p>
|
||||
<p>艾丽丝笑了笑:"没事...只是消耗了一些力量。"</p>
|
||||
<p>希尔薇站起身,走向林克。她的眼神充满了感激和复杂的情绪。</p>
|
||||
<p>"谢谢你...林克。"她说,"你给了我自由。"</p>
|
||||
<p>"不用谢。"林克说,"是你自己战胜了诅咒。"</p>
|
||||
<p>希尔薇摇头:"如果没有你们,我永远无法摆脱赫尔德的控制。"</p>
|
||||
<p>她看向艾丽丝:"还有你...你用自己的力量帮我解除诅咒。这份恩情,我永远不会忘记。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,古树突然发出一道光芒。</p>
|
||||
<p>一个虚幻的影像从树干中浮现——那是赫尔德的身影。</p>
|
||||
<p>"希尔薇,看来你背叛了我。"赫尔德的声音冰冷。</p>
|
||||
<p>希尔薇的脸色变得苍白:"赫尔德..."</p>
|
||||
<p>"既然你不再是翡翠梦魇的守护者,那这片森林也没有存在的必要了。"</p>
|
||||
<p>赫尔德挥手,森林中所有的诅咒符文开始发光,整片森林即将崩塌。</p>
|
||||
<p>"她要摧毁森林!"艾丽丝惊呼。</p>
|
||||
<p>林克握紧细雪之舞:"希尔薇,这片森林还能救吗?"</p>
|
||||
<p>希尔薇看向古树:"如果能唤醒世界树的残存意志,也许可以阻止崩塌。"</p>
|
||||
<p>"怎么做?"</p>
|
||||
<p>"需要精灵族的血脉注入古树。"希尔薇说,"我是最后的精灵...让我来。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希尔薇走向古树,将手放在树干上。</p>
|
||||
<p>绿色的光芒从她体内涌出,进入古树。</p>
|
||||
<p>"世界树啊,请保护你的孩子。"</p>
|
||||
<p>古树开始震动,绿色的光芒从树干中散发出来,与赫尔德的力量对抗。</p>
|
||||
<p>"不行...我的力量不够。"希尔薇咬牙。</p>
|
||||
<p>林克走上前,将自己的手也放在树干上:"我帮你。"</p>
|
||||
<p>艾丽丝和尼梅尔也走了过来,将手放在古树上。</p>
|
||||
<p>四个人的力量同时注入古树,绿色的光芒越来越强。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>终于,赫尔德的力量被压制了。</p>
|
||||
<p>森林停止了崩塌,古树重新焕发出生机。</p>
|
||||
<p>赫尔德的影像冷哼一声:"有意思...看来你们比我想象的更难对付。"</p>
|
||||
<p>她看向林克:"年轻人,我们还会再见面的。"</p>
|
||||
<p>然后,影像消失了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希尔薇瘫坐在地上,喘着粗气。</p>
|
||||
<p>"成功了吗..."</p>
|
||||
<p>她看向四周,森林已经恢复了平静。那些曾经被诅咒的植物,现在也变得正常了。</p>
|
||||
<p>"谢谢你,林克。"她说,"你不仅解除了我的诅咒,还拯救了我的家园。"</p>
|
||||
<p>林克伸出手:"希尔薇,你接下来打算怎么办?"</p>
|
||||
<p>希尔薇看着他,眼中闪过一丝迷茫:"我不知道...我已经三百年没有自由了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十四章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-143.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-145.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-114.html" class="sidebar-chapter ">第114章:迷之觉悟</a>
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter current">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(144)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,952 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>精灵的誓言 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 145</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>夜幕降临,翡翠之森恢复了宁静。</p>
|
||||
<p>四人坐在古树下,享受着难得的平静时光。</p>
|
||||
<p>希尔薇看着天空中的紫色月亮,眼中满是感慨。</p>
|
||||
<p>"三百年了...我终于可以安静地看月亮了。"</p>
|
||||
<p>尼梅尔凑过来:"希尔薇姐姐,你真的三百岁了吗?看起来好年轻!"</p>
|
||||
<p>希尔薇笑了笑:"精灵族的寿命很长,三百年对我们来说只是成年。"</p>
|
||||
<p>她看向林克:"林克,我想问你一个问题。"</p>
|
||||
<p>"什么?"</p>
|
||||
<p>"你为什么要帮助我?"希尔薇认真地说,"我们素不相识,你却愿意冒险帮我解除诅咒。"</p>
|
||||
<p>林克思考了片刻:"因为你需要帮助。而且...赫尔德做的事情是错误的。"</p>
|
||||
<p>"仅此而已?"</p>
|
||||
<p>林克沉默了一下,然后说:"我看到你眼中的痛苦,那不是敌人应该有的眼神。我知道,你不是自愿成为守护者的。"</p>
|
||||
<p>希尔薇的眼眶微微泛红:"你...看出来了?"</p>
|
||||
<p>"是的。"林克说,"你被诅咒束缚,无法选择自己的命运。我不喜欢看到这种情况。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希尔薇低下头,沉默了很久。</p>
|
||||
<p>然后她抬起头,看向林克:"林克,我决定了。"</p>
|
||||
<p>"决定什么?"</p>
|
||||
<p>"我要跟你走。"希尔薇坚定地说,"你给了我自由,我要追随你。"</p>
|
||||
<p>艾丽丝和尼梅尔对视一眼,脸上露出微笑。</p>
|
||||
<p>林克有些意外:"追随我?"</p>
|
||||
<p>"是的。"希尔薇点头,"我没有地方可去,也不想一个人留在这里。你的目标是阻止赫尔德,而她也是我的仇人。"</p>
|
||||
<p>她看向林克:"请让我加入你的旅程。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着希尔薇认真的眼神,点了点头:"好。但我必须告诉你,我的旅程很危险。"</p>
|
||||
<p>"我不怕危险。"希尔薇说,"我已经在诅咒中生活了三百年,没有什么能比那更可怕。"</p>
|
||||
<p>她犹豫了一下,然后继续说:"而且...我对你的感觉,不仅仅是感激。"</p>
|
||||
<p>林克愣了一下:"什么意思?"</p>
|
||||
<p>希尔薇站起身,走到林克面前。</p>
|
||||
<p>"林克,你是第一个愿意为我冒险的人。"她说,"在我被诅咒的三百年里,没有人尝试救我。只有你。"</p>
|
||||
<p>"从你用剑斩断诅咒锁链的那一刻起,我就知道...我的心已经属于你了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝在一旁轻声说:"希尔薇,你知道林克已经有很多人了吗?"</p>
|
||||
<p>"我知道。"希尔薇点头,"在森林里,我看到了你们的互动。那个叫赛丽亚的女孩...还有其他很多人。"</p>
|
||||
<p>她看向林克:"但我不在乎。我只想陪在你身边。"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>他知道希尔薇的感情是真实的。三百年的孤独,让这份感情变得更加珍贵。</p>
|
||||
<p>"希尔薇..."他伸出手,轻轻抚摸她的脸颊,"你确定吗?"</p>
|
||||
<p>"确定。"希尔薇的眼中闪着坚定的光芒,"请接纳我。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克将希尔薇拥入怀中,低下头吻住了她的唇。</p>
|
||||
<p>希尔薇的眼睛微微睁大,然后慢慢闭上,沉醉在这个吻中。</p>
|
||||
<p>三百年的孤独,在这一刻终于得到了慰藉。</p>
|
||||
<p>艾丽丝和尼梅尔在一旁静静看着,脸上带着祝福的笑容。</p>
|
||||
<p>"希尔薇姐姐终于找到归宿了。"尼梅尔小声说。</p>
|
||||
<p>"是啊。"艾丽丝点头,"她受的苦够多了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>月光下,林克和希尔薇在古树旁相拥。</p>
|
||||
<p>希尔薇靠在林克怀里,脸上带着满足的笑容。</p>
|
||||
<p>"林克,我想告诉你...我的真名。"</p>
|
||||
<p>"真名?"</p>
|
||||
<p>"是的。"希尔薇说,"精灵族有传统,只有对最重要的人,才会说出真名。"</p>
|
||||
<p>她轻声说:"我的真名是希尔薇娅·翡翠之泪。"</p>
|
||||
<p>"希尔薇娅..."林克重复着这个名字。</p>
|
||||
<p>"从今以后,我就是你的人了。"希尔薇抬起头,看着林克的眼睛,"请照顾我...一辈子。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人在月光下度过了一个美好的夜晚。</p>
|
||||
<p>希尔薇将自己完全交给了林克,三百年来的孤独和痛苦,都在这个夜晚化为了温暖。</p>
|
||||
<p>第二天清晨,四人离开翡翠之森。</p>
|
||||
<p>希尔薇回头看了最后一眼,然后转身跟随林克,踏上新的旅程。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到中央公园,莎莎看到希尔薇,惊讶地说:"你解除了希尔薇的诅咒?这可是很多人都尝试过但失败的事情!"</p>
|
||||
<p>"运气好。"林克说。</p>
|
||||
<p>莎莎摇了摇头:"不是运气,是实力。林克,你的名声在魔界越来越响了。"</p>
|
||||
<p>她拿出一张纸条:"对了,有新的消息。"</p>
|
||||
<p>"什么消息?"</p>
|
||||
<p>"魔界大战即将开始。"莎莎说,"赫尔德召集了所有使徒和强者,准备进行最后的仪式。"</p>
|
||||
<p>林克的脸色变得严肃:"最后的仪式?"</p>
|
||||
<p>"是的。"莎莎点头,"创新世纪的启动仪式。地点在'深渊之眼'——地轨中心的最深处。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧细雪之舞。</p>
|
||||
<p>"时间到了。"</p>
|
||||
<p>他看向艾丽丝、尼梅尔和希尔薇:"我们准备好了吗?"</p>
|
||||
<p>艾丽丝点头:"我的灵魂之源融合得差不多了。"</p>
|
||||
<p>尼梅尔握着短剑:"我会保护林克!"</p>
|
||||
<p>希尔薇举起弓:"我会跟赫尔德算账的。"</p>
|
||||
<p>林克看向天空:"那就出发吧。去结束这一切。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十五章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(翡翠梦魇篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-144.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-146.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-115.html" class="sidebar-chapter ">第115章:番外·艾丽丝的抉择</a>
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter current">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(145)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,960 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>深渊之眼 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 146</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>地轨中心,深渊之眼入口。</p>
|
||||
<p>四人站在一扇巨大的黑色大门前。门上刻满了诡异的符文,散发着令人窒息的压迫感。从门缝中渗出的黑暗气息,仿佛能吞噬一切光明。</p>
|
||||
<p>"这就是深渊之眼..."艾丽丝轻声说,"地轨中心的最深处,赫尔德举行创新世纪仪式的地方。"</p>
|
||||
<p>希尔薇握紧弓箭:"我能感受到里面有一股恐怖的力量。"</p>
|
||||
<p>尼梅尔紧张地握着短剑:"林克,我们真的要进去吗?"</p>
|
||||
<p>林克看着大门,眼中闪过坚定:"是的。我们必须阻止赫尔德。"</p>
|
||||
<p>他推开大门,踏入黑暗之中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深渊之眼内部是一个巨大的圆形空间。</p>
|
||||
<p>四周是深不见底的深渊,只有一条狭窄的道路通向中央。天空中漂浮着无数紫色的能量球,散发着诡异的光芒。空气中弥漫着古老而压抑的气息,让人呼吸困难。</p>
|
||||
<p>"这里的空间...完全扭曲了。"艾丽丝皱眉,"普通冒险家进来,会立刻迷失方向。"</p>
|
||||
<p>林克握紧细雪之舞:"跟紧我,不要走散。"</p>
|
||||
<p>四人沿着狭窄的道路前进。每一步都需要小心翼翼,因为道路两旁就是无尽的深渊。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约十分钟,前方出现了动静。</p>
|
||||
<p>几个身穿黑色铠甲的身影从黑暗中浮现。他们手持长剑,眼睛燃烧着紫色的火焰。</p>
|
||||
<p>"深渊守卫。"希尔薇认出了他们,"赫尔德最忠诚的士兵,被改造过,没有感情,只会执行命令。"</p>
|
||||
<p>"入侵者。"领头的守卫发出低沉的声音,"执行清除程序。"</p>
|
||||
<p>六个深渊守卫同时拔剑,朝四人冲来。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>林克迎上第一个守卫,光剑划出一道冰蓝色的弧线。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>剑尖刺穿了守卫的胸甲,但他没有倒下,反而继续挥剑攻击。</p>
|
||||
<p>"这些家伙...不怕痛?"林克皱眉。</p>
|
||||
<p>"他们已经被改造了,没有痛觉。"希尔薇拉弓射箭,精准地命中一个守卫的头盔缝隙,"要攻击要害!"</p>
|
||||
<p>艾丽丝举起法杖:"元素爆破!"</p>
|
||||
<p>火球、冰锥、雷电同时轰向敌人。尼梅尔也挥舞着短剑,配合林克攻击。</p>
|
||||
<p>虽然深渊守卫不知疼痛,但在四人的配合下,还是一个个倒下了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>继续前进,敌人越来越多。</p>
|
||||
<p>深渊守卫、虚空行者、暗影刺客...各种被赫尔德改造的生物涌向四人。</p>
|
||||
<p>林克的剑不断挥舞,艾丽丝的魔法不断释放,希尔薇的箭矢精准命中,尼梅尔的短剑灵活刺击。</p>
|
||||
<p>"前面有一个更强的敌人!"希尔薇警告道。</p>
|
||||
<p>林克看向前方,那里站着一个巨大的身影——身高足有三米,全身覆盖着黑色的铠甲,手中握着一把巨剑。</p>
|
||||
<p>"深渊领主..."艾丽丝的脸色变得凝重,"深渊之眼的精英守卫。"</p>
|
||||
<p>深渊领主发出一声咆哮,声音震得整个空间都在颤抖。</p>
|
||||
<p>"入侵者...死!"</p>
|
||||
<p>他挥动巨剑,一道黑色的剑气横扫而出,范围足有十几米。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"散开!"林克大喊。</p>
|
||||
<p>四人迅速分散,剑气击中道路,地面崩裂,碎石落入深渊。</p>
|
||||
<p>"这家伙...攻击范围太大了!"尼梅尔惊呼。</p>
|
||||
<p>林克冷静地观察深渊领主的动作。他的攻击虽然威力大,但速度很慢,有预判的空间。</p>
|
||||
<p>"希尔薇,用箭压制他!艾丽丝,用魔法限制他的行动!"</p>
|
||||
<p>希尔薇连续射出三支箭,命中深渊领主的关节部位。艾丽丝也释放出冰霜魔法,在他脚下形成冰层,减缓他的移动速度。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>林克的身影化作闪电,连续四次斩击,全部命中深渊领主的胸口。</p>
|
||||
<p>深渊领主发出痛苦的吼叫,但依然挥剑反击。</p>
|
||||
<p>林克侧身闪避,然后再次攻击。</p>
|
||||
<p>"极·神剑术(瞬影斩)!"</p>
|
||||
<p>他瞬移到深渊领主身后,光剑刺入他的背部。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>深渊领主终于倒下了。</p>
|
||||
<p>他的身体化作黑色的烟雾消散,留下一把黑色的钥匙。</p>
|
||||
<p>"这是..."林克捡起钥匙。</p>
|
||||
<p>"深渊钥匙。"艾丽丝说,"应该是通向更深处的大门钥匙。"</p>
|
||||
<p>林克点头,将钥匙收起:"走吧,继续前进。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人继续深入深渊之眼。</p>
|
||||
<p>越往里走,压迫感越强。空气中弥漫着使徒级别的力量气息,让人感到窒息。</p>
|
||||
<p>终于,他们来到了一扇巨大的门前。</p>
|
||||
<p>门上刻着一只巨大的眼睛图案,周围环绕着无数符文。</p>
|
||||
<p>"这就是...创新世纪仪式的入口。"艾丽丝轻声说。</p>
|
||||
<p>林克拿出深渊钥匙,插入门上的锁孔。</p>
|
||||
<p>"咔嚓。"</p>
|
||||
<p>大门缓缓打开,一股恐怖的气息从里面涌出。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>门后是一个巨大的圆形广场。</p>
|
||||
<p>广场中央有一个高台,上面刻满了复杂的魔法阵。高台周围站着几十个身穿黑袍的人,正在进行某种仪式。</p>
|
||||
<p>而高台的中央,站着一个身穿白色长裙的女人——赫尔德。</p>
|
||||
<p>她的银色长发在魔法阵的光芒中飘动,紫色的眼睛闭着,仿佛在进行某种冥想。</p>
|
||||
<p>在赫尔德的上方,悬浮着一个巨大的紫色能量球,那是收集了使徒力量的结晶。</p>
|
||||
<p>"创新世纪的能量核心..."艾丽丝喃喃自语。</p>
|
||||
<p>林克握紧细雪之舞:"我们来了,赫尔德。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>赫尔德睁开眼睛,看向林克。</p>
|
||||
<p>"你来了。"她的声音平静,仿佛早已预料到,"我就知道你会来。"</p>
|
||||
<p>"停止你的计划。"林克说,"创新世纪只会带来更多的痛苦。"</p>
|
||||
<p>赫尔德微微摇头:"你还是不明白。创新世纪会消除所有的痛苦,创造一个完美的世界。"</p>
|
||||
<p>"用牺牲换来的完美,不是真正的完美。"</p>
|
||||
<p>赫尔德看着林克,眼中闪过一丝复杂的情绪:"也许你是对的。也许我是错的。但...我已经没有退路了。"</p>
|
||||
<p>她抬起手,魔法阵开始旋转:"让开,否则...我会消灭你们。"</p>
|
||||
<p>林克举剑:"我不会让开。"</p>
|
||||
<p>两人的目光在空中交汇,火药味弥漫整个广场。</p>
|
||||
<p>战斗,一触即发。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十六章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-145.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-147.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-116.html" class="sidebar-chapter ">第116章:番外·后宫的日常</a>
|
||||
<a href="chapter-117.html" class="sidebar-chapter ">第117章:番外·与赛丽亚的约会</a>
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter current">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(146)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,983 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>战后余晖 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 148</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>林克睁开眼睛,看到一片熟悉的天花板。</p>
|
||||
<p>"他醒了!"</p>
|
||||
<p>尼梅尔的声音在耳边响起,随即是一张担心的脸出现在视野中。</p>
|
||||
<p>"林克,你终于醒了!你昏迷了三天!"</p>
|
||||
<p>三天?林克回忆起最后的战斗。他用尽了所有力量逆转创新世纪仪式,然后就失去了意识。</p>
|
||||
<p>"艾丽丝姐姐和希尔薇姐姐这几天一直在照顾你。"尼梅尔说。</p>
|
||||
<p>林克试图坐起来,但身体还很虚弱。艾丽丝和希尔薇走进房间,看到他醒来,脸上都露出欣慰的笑容。</p>
|
||||
<p>"林克,你没事就好。"艾丽丝走到床边,握住他的手,"你吓死我了。"</p>
|
||||
<p>希尔薇也走过来:"你用时间回溯过度消耗了体力,能活下来已经是奇迹。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我们现在在哪里?"林克问。</p>
|
||||
<p>"魔界营地。"艾丽丝说,"凯蒂姐姐派人把我们接回来的。"</p>
|
||||
<p>林克点了点头,试图下床。但双腿还有些发软,他不得不重新坐下。</p>
|
||||
<p>"你还不能乱动。"艾丽丝按住他,"医生说你需要至少一周的休息。"</p>
|
||||
<p>"我没那么脆弱。"林克苦笑。</p>
|
||||
<p>但看着艾丽丝担心的眼神,他还是乖乖地躺回了床上。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>几天后,林克终于恢复了行动能力。</p>
|
||||
<p>他走出房间,看到魔界营地已经恢复了往日的平静。居民们在街道上忙碌,脸上带着久违的笑容。</p>
|
||||
<p>"赫尔德消失后,整个魔界都松了一口气。"凯蒂走过来,"她的爪牙们纷纷逃离,被她控制的生物也逐渐恢复了理智。"</p>
|
||||
<p>"那就好。"林克说。</p>
|
||||
<p>凯蒂看着他,眼中带着感激:"林克,谢谢你。你拯救了魔界。"</p>
|
||||
<p>"我只是做了该做的事。"</p>
|
||||
<p>凯蒂笑了笑:"你总是这么谦虚。不过,有几件事我想告诉你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>凯蒂带林克来到她的住所,拿出一封信。</p>
|
||||
<p>"这是莎莎送来的。她说有重要的消息。"</p>
|
||||
<p>林克打开信,上面写着:</p>
|
||||
<p>"林克:</p>
|
||||
<p>赫尔德的事件解决了,但魔界还没有完全恢复和平。</p>
|
||||
<p>最近,有传闻说泰波尔斯地区出现了异常的能量波动。据说,第三使徒普雷正在那里等待什么。</p>
|
||||
<p>如果你想继续变强,或者想知道更多关于这个世界的真相,也许你应该去泰波尔斯看看。</p>
|
||||
<p>——莎莎"</p>
|
||||
<p>林克放下信,陷入沉思。</p>
|
||||
<p>"泰波尔斯...普雷..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你打算去吗?"艾丽丝走过来,看到了信的内容。</p>
|
||||
<p>"也许吧。"林克说,"但现在,我想先回阿拉德大陆。"</p>
|
||||
<p>"回去?"</p>
|
||||
<p>"是的。"林克点头,"我已经很久没见到赛丽亚她们了。赫尔德的事情结束后,我想回去看看她们。"</p>
|
||||
<p>艾丽丝露出微笑:"我也想见见她们。"</p>
|
||||
<p>尼梅尔和希尔薇也走了过来。</p>
|
||||
<p>"我也想去阿拉德大陆!"尼梅尔说,"听说那里很漂亮!"</p>
|
||||
<p>希尔薇点头:"我跟你去。我已经决定追随你了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>几天后,四人离开魔界营地,前往寂静城。</p>
|
||||
<p>卢克听说林克成功阻止了创新世纪,非常欣慰。</p>
|
||||
<p>"年轻人,你做得很好。"他说,"赫尔德的计划失败了,世界恢复了和平。"</p>
|
||||
<p>"谢谢卢克爷爷的帮忙。"林克说,"时间之钥帮了我大忙。"</p>
|
||||
<p>卢克笑了笑:"时间之钥已经和你融为一体了。它是你的力量,不需要谢我。"</p>
|
||||
<p>他看向林克身后的艾丽丝、尼梅尔和希尔薇:"你收获了不错的伙伴。好好珍惜她们。"</p>
|
||||
<p>"我会的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>卢克开启了通往阿拉德大陆的传送门。</p>
|
||||
<p>金色的光芒笼罩四人,他们的身影开始变得模糊。</p>
|
||||
<p>"年轻人,世界还很大。"卢克的声音在耳边回荡,"如果有一天你想继续探索,泰波尔斯...或者更远的地方...都在等着你。"</p>
|
||||
<p>光芒闪烁,四人消失在传送门中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克再次睁开眼睛时,他看到了熟悉的天空——不是魔界扭曲的紫色天空,而是阿拉德大陆清澈的蓝色天空。</p>
|
||||
<p>阳光明媚,微风轻拂,空气中弥漫着青草的香气。</p>
|
||||
<p>"这里是...阿拉德大陆!"尼梅尔睁大眼睛,"好美!"</p>
|
||||
<p>希尔薇也露出惊讶的表情:"这里的天空...和魔界完全不同。"</p>
|
||||
<p>艾丽丝深吸一口气:"终于回来了..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人走在前往赛丽亚旅馆的路上。</p>
|
||||
<p>沿途的风景让尼梅尔和希尔薇惊叹不已。她们从未见过如此和平的世界——没有扭曲的空间,没有压抑的气息,只有宁静和美好。</p>
|
||||
<p>"林克,这就是你出生的世界?"希尔薇问。</p>
|
||||
<p>"是的。"林克点头,"虽然也有危险,但比魔界和平得多。"</p>
|
||||
<p>很快,他们看到了熟悉的建筑——赛丽亚旅馆。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克推开门,走进旅馆。</p>
|
||||
<p>"欢迎光临..."</p>
|
||||
<p>熟悉的声音响起,赛丽亚从柜台后抬起头。当她看到林克时,眼睛瞬间睁大。</p>
|
||||
<p>"林克?!"</p>
|
||||
<p>她冲过来,扑进林克怀里:"你回来了!我好担心你!"</p>
|
||||
<p>林克抱住她:"我回来了,赛丽亚。"</p>
|
||||
<p>敏泰、帕丽丝、莎兰、奥菲利亚...其他后宫们也纷纷出现,围在林克身边。</p>
|
||||
<p>"林克哥哥!"</p>
|
||||
<p>"你终于回来了!"</p>
|
||||
<p>"魔界那边怎么样了?"</p>
|
||||
<p>林克看着她们,心中涌起温暖的感觉。</p>
|
||||
<p>"我回来了。"他笑着说,"一切都结束了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>夜晚,赛丽亚旅馆举行了盛大的庆祝宴会。</p>
|
||||
<p>林克坐在中央,周围是他的后宫们。艾丽丝、尼梅尔和希尔薇被介绍给大家,很快就融入了这个大家庭。</p>
|
||||
<p>"林克哥哥,你好厉害!"敏泰崇拜地看着他,"你打败了赫尔德!"</p>
|
||||
<p>"是大家一起努力的结果。"林克说。</p>
|
||||
<p>帕丽丝笑着搂住他的脖子:"不管怎么说,你平安回来了,这就够了。"</p>
|
||||
<p>赛丽亚端着酒杯走过来:"林克,欢迎回家。"</p>
|
||||
<p>林克接过酒杯,与所有人碰杯:"谢谢大家。我回来了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>宴会结束后,林克独自站在旅馆的阳台上,看着星空。</p>
|
||||
<p>"在想什么?"</p>
|
||||
<p>艾丽丝走过来,站在他身边。</p>
|
||||
<p>"在想接下来的事。"林克说,"莎莎信里提到的泰波尔斯...还有普雷。"</p>
|
||||
<p>"你想去?"</p>
|
||||
<p>"也许。"林克说,"但不是现在。我想先休息一段时间,陪陪大家。"</p>
|
||||
<p>艾丽丝点头:"我陪着你。"</p>
|
||||
<p>两人靠在一起,看着天上的星星。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,天空中突然闪过一道奇异的光芒。</p>
|
||||
<p>一个紫色的光点划过天际,消失在远方。</p>
|
||||
<p>"那是..."林克皱眉。</p>
|
||||
<p>艾丽丝的脸色也变了:"那是...泰波尔斯的方向。"</p>
|
||||
<p>林克握紧拳头。他感觉到,新的冒险即将开始。</p>
|
||||
<p>但现在,他想好好休息,享受这段难得的和平时光。</p>
|
||||
<p>"不管发生什么..."他喃喃自语,"我都会保护这个世界。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十八章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(魔界篇 完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(泰波尔斯篇 预告)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-147.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-149.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-118.html" class="sidebar-chapter ">第118章:番外·与奥菲利亚的重逢</a>
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter current">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(148)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,963 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>泰波尔斯的召唤 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 149</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>赛丽亚旅馆,阳光明媚的早晨。</p>
|
||||
<p>林克坐在旅馆的院子里,享受着难得的平静时光。自从魔界篇结束后,他已经休息了整整一周。</p>
|
||||
<p>"林克,茶泡好了。"赛丽亚端着茶盘走过来,脸上带着温柔的微笑。</p>
|
||||
<p>"谢谢。"林克接过茶杯,感受着茶香。</p>
|
||||
<p>敏泰在一旁修剪着花草,帕丽丝正在和莎兰讨论魔法,莫纳亨安静地坐在角落里看书...每个人都享受着这份平静。</p>
|
||||
<p>"这样的日子真好。"艾丽丝走到林克身边坐下,"在魔界的时候,我从未想过能这样平静地生活。"</p>
|
||||
<p>"以后会一直这样的。"林克握住她的手。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,天空中突然传来一声巨响。</p>
|
||||
<p>所有人抬头看去,只见天空中出现了一道巨大的裂缝。裂缝散发着紫色的光芒,能量波动不断从中涌出。</p>
|
||||
<p>"那是...什么?"敏泰惊呼。</p>
|
||||
<p>林克站起身,皱眉看着天空中的裂缝。他能感受到从裂缝中传来的气息——那是使徒级别的力量。</p>
|
||||
<p>"有一个使徒...在求救?"艾丽丝惊讶地说,"我能感受到...一个强大的存在正在发出求救信号。"</p>
|
||||
<p>"求救?"赛丽亚担心地说,"林克,你要去吗?"</p>
|
||||
<p>林克沉默了片刻,然后点了点头:"如果有人需要帮助,我不能坐视不管。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一只紫色的鸟儿从裂缝中飞出,落在林克肩上。</p>
|
||||
<p>那是一只美丽的鸟,羽毛散发着神秘的光芒。它的嘴里叼着一封信。</p>
|
||||
<p>林克取下信,打开阅读:</p>
|
||||
<p>"来自阿拉德大陆的勇者:</p>
|
||||
<p>我是泰波尔斯的守护者,天空族的信使。</p>
|
||||
<p>第三使徒普雷大人正在与黑暗面伊西斯战斗,但形势危急。伊西斯的力量越来越强,普雷大人即将被吞噬。</p>
|
||||
<p>如果普雷大人堕落,整个泰波尔斯都将陷入黑暗,甚至波及阿拉德大陆。</p>
|
||||
<p>请务必前来相助。</p>
|
||||
<p>——天空族·艾拉"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"普雷...第三使徒。"林克喃喃自语。</p>
|
||||
<p>在米歇尔的使徒会晤上,他曾见过普雷的身影。那是一个笼罩在黑暗中的巨大存在,散发着天空之王的气息。</p>
|
||||
<p>"伊西斯是普雷的黑暗面?"艾丽丝问。</p>
|
||||
<p>"是的。"林克说,"米歇尔告诉过我,普雷是天空之王,但他有一个黑暗面叫伊西斯。两个存在一直处于战斗中。"</p>
|
||||
<p>"如果伊西斯获胜..."</p>
|
||||
<p>"那将是一个灾难。"林克握紧拳头,"我必须去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克,我陪你去。"艾丽丝站起身。</p>
|
||||
<p>"我也去!"尼梅尔跑过来。</p>
|
||||
<p>希尔薇也走过来:"我跟你一起。"</p>
|
||||
<p>林克看着她们,点了点头:"好。"</p>
|
||||
<p>他看向其他后宫们:"你们留在阿拉德大陆,如果有其他危险,帮忙照看一下。"</p>
|
||||
<p>赛丽亚走过来,轻轻吻了林克的脸颊:"一定要平安回来。"</p>
|
||||
<p>"我会的。"林克拥抱了她,"等我回来。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"去泰波尔斯的路...我不太清楚。"艾丽丝说。</p>
|
||||
<p>"那只鸟应该知道。"林克看向肩上的紫色鸟儿。</p>
|
||||
<p>鸟儿发出一声鸣叫,飞向天空中的裂缝。</p>
|
||||
<p>"跟紧它。"林克说。</p>
|
||||
<p>三人跟着鸟儿,朝着裂缝飞去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>穿过裂缝,眼前的景象完全变了。</p>
|
||||
<p>这里是一片漂浮在天空中的大陆,无数岛屿悬浮在云海之上。建筑风格奇异,充满了天空族的特色。天空中飞翔着各种鸟类,有些体型巨大,可以作为坐骑。</p>
|
||||
<p>"这就是泰波尔斯..."尼梅尔睁大眼睛,"好美!"</p>
|
||||
<p>希尔薇也露出惊讶的表情:"这里的能量...和魔界完全不同。充满了天空的气息。"</p>
|
||||
<p>鸟儿在前方带路,三人跟着它飞向中央的一座巨大建筑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>建筑前,已经有几个人在等着他们。</p>
|
||||
<p>领头的是一个身穿白色长袍的女子,她有着银色的长发和淡蓝色的眼睛,身上散发着神圣的气息。她的背后有一对洁白的翅膀——那是天空族的标志。</p>
|
||||
<p>"欢迎来到泰波尔斯。"她说,"我是艾拉,天空族的信使。感谢你们回应我们的召唤。"</p>
|
||||
<p>"我是林克。"林克说,"你说的普雷大人的情况...怎么样了?"</p>
|
||||
<p>艾拉的表情变得凝重:"不太乐观。伊西斯的力量越来越强,普雷大人已经被逼入了绝境。"</p>
|
||||
<p>她看向林克:"请跟我来,我带你去见普雷大人。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉带着三人穿过街道,朝着泰波尔斯的中心走去。</p>
|
||||
<p>沿途,林克看到许多天空族的居民。他们都有翅膀,或大或小,颜色各异。每个人的脸上都带着担忧的表情。</p>
|
||||
<p>"伊西斯是从哪里来的?"林克问。</p>
|
||||
<p>"他是普雷大人的黑暗面。"艾拉解释道,"很久以前,普雷大人在探索宇宙时,接触了一个被诅咒的空间。那个空间的黑暗力量侵入了他的身体,形成了伊西斯。"</p>
|
||||
<p>"从那以后,普雷大人就一直与伊西斯战斗。他们的力量此消彼长,一直处于平衡状态。"</p>
|
||||
<p>"但最近...伊西斯突然变强了。"艾拉的声音带着忧虑,"我们不知道原因,但普雷大人正在逐渐落入下风。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>很快,他们来到了一座巨大的神殿前。</p>
|
||||
<p>神殿散发着强烈的光芒,那是普雷的力量。但光芒中夹杂着黑色的气息,那是伊西斯的力量。</p>
|
||||
<p>"普雷大人就在里面。"艾拉说,"但你们要小心,伊西斯的力量非常强大。如果你们被他的黑暗侵蚀,也会变成他的傀儡。"</p>
|
||||
<p>林克点头:"我明白了。"</p>
|
||||
<p>他看向艾丽丝、尼梅尔和希尔薇:"你们留在外面,如果情况不对,随时支援。"</p>
|
||||
<p>"林克,小心。"艾丽丝握住他的手。</p>
|
||||
<p>林克深吸一口气,踏入神殿。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>神殿内部是一个巨大的空间。</p>
|
||||
<p>中央有两个人影在激战——一个散发着金色的光芒,另一个笼罩在黑暗中。</p>
|
||||
<p>金色光芒的是普雷,他有着巨大的翅膀,身上穿着天空之王的铠甲,手中握着一把光芒四射的长枪。</p>
|
||||
<p>黑暗中的是伊西斯,他的身形更加扭曲,翅膀是黑色的,身上散发着令人窒息的黑暗气息。</p>
|
||||
<p>两人的力量不断碰撞,整个神殿都在震动。</p>
|
||||
<p>"林克..."普雷注意到林克的到来,声音虚弱但威严,"你来了...阿拉德的勇者..."</p>
|
||||
<p>"普雷大人!"林克大喊。</p>
|
||||
<p>但就在这时,伊西斯发出一声冷笑:"又一个送死的..."</p>
|
||||
<p>他挥动黑色的翅膀,一道黑暗能量朝林克袭来。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克举起细雪之舞,挡住了黑暗能量。</p>
|
||||
<p>但那股力量太强了,他被震退了好几步。</p>
|
||||
<p>"这就是...使徒的黑暗面..."</p>
|
||||
<p>林克握紧光剑,眼神坚定。</p>
|
||||
<p>"普雷大人,我来帮你!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百四十九章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-148.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-150.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-119.html" class="sidebar-chapter ">第119章:番外·与敏泰的雪山之行</a>
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter current">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(149)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,959 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>天空之城 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 150</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>林克冲向伊西斯,细雪之舞划出一道冰蓝色的弧线。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>剑尖直取伊西斯的胸口,但被一道黑色的屏障挡住了。</p>
|
||||
<p>"太弱了。"伊西斯冷笑,"你就是那个打败赫尔德的人类?也不过如此。"</p>
|
||||
<p>他挥手,一道黑暗能量将林克击飞出去。</p>
|
||||
<p>林克在空中调整姿态,稳稳落地。他的胸口隐隐作痛,刚才的攻击虽然被挡下,但冲击力还是很强。</p>
|
||||
<p>"普雷大人,我们一起攻击!"</p>
|
||||
<p>普雷点头,金色长枪光芒大盛。</p>
|
||||
<p>"天空之枪!"</p>
|
||||
<p>他掷出长枪,枪身化作一道金色的流星,直冲伊西斯。同时,林克也从侧面发起攻击。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的长枪和冰蓝色的剑光同时袭向伊西斯。</p>
|
||||
<p>伊西斯的表情终于变得凝重。他张开黑色翅膀,形成一个巨大的护盾。</p>
|
||||
<p>"轰!"</p>
|
||||
<p>两股力量在护盾上爆发,整个神殿都在震动。</p>
|
||||
<p>但护盾没有破裂。</p>
|
||||
<p>"没用的。"伊西斯冷笑,"我是普雷的黑暗面,拥有和他同等的力量。而现在的普雷...已经被我压制了。"</p>
|
||||
<p>他反手一击,黑色的能量波横扫而出。</p>
|
||||
<p>普雷被击中,金色的铠甲出现了裂痕。林克也被余波击中,吐出一口鲜血。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"撤退!"普雷大喊。</p>
|
||||
<p>他抓住林克,展开翅膀飞出神殿。</p>
|
||||
<p>伊西斯没有追击,只是站在原地冷笑:"跑吧...你们逃不掉的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>神殿外,艾丽丝、尼梅尔和希尔薇紧张地等待着。</p>
|
||||
<p>当普雷带着林克飞出来时,她们立刻围了上去。</p>
|
||||
<p>"林克!"艾丽丝扶住他,"你受伤了!"</p>
|
||||
<p>"我没事。"林克擦去嘴角的血迹,"只是被震伤了。"</p>
|
||||
<p>普雷落在地上,金色的光芒黯淡了许多。他的脸色苍白,显然受了不轻的伤。</p>
|
||||
<p>艾拉走过来:"普雷大人,您的伤势..."</p>
|
||||
<p>"不要紧。"普雷摆了摆手,"伊西斯的力量越来越强了。如果不尽快阻止他,整个泰波尔斯都会陷入黑暗。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷被带到一处安静的宫殿休息。</p>
|
||||
<p>林克坐在他对面,艾丽丝、尼梅尔、希尔薇和艾拉也围在一旁。</p>
|
||||
<p>"普雷大人,伊西斯到底是什么?"林克问,"为什么他会突然变强?"</p>
|
||||
<p>普雷叹了口气:"伊西斯是我的黑暗面。很久以前,我在探索宇宙时,误入了一个被诅咒的空间。那个空间的黑暗力量侵入了我的身体,形成了他。"</p>
|
||||
<p>"从那以后,我就一直与他战斗。我们的力量此消彼长,一直处于平衡状态。"</p>
|
||||
<p>他看向林克:"但最近...他吸收了一些外来的黑暗力量。那些力量让他的实力大增,打破了我们之间的平衡。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"外来的黑暗力量?"艾丽丝皱眉,"是从哪里来的?"</p>
|
||||
<p>"我不知道。"普雷摇头,"但我能感受到,那股力量来自一个古老的源头...也许是某个被封印的存在。"</p>
|
||||
<p>林克思考了片刻:"有什么方法可以击败他吗?"</p>
|
||||
<p>普雷沉默了一会儿:"有两种方法。第一种是杀死我,伊西斯也会随之消失。但那样的话,泰波尔斯将失去守护者,整个天空之城都会崩溃。"</p>
|
||||
<p>"第二种呢?"</p>
|
||||
<p>"净化他。"普雷说,"用神圣的力量将他与我的身体分离,然后净化他的黑暗。那样的话,我将恢复完整,伊西斯也将消失。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"净化需要什么?"林克问。</p>
|
||||
<p>"天空之泪。"普雷说,"那是泰波尔斯最神圣的宝物,拥有净化一切黑暗的力量。"</p>
|
||||
<p>艾拉插话道:"天空之泪在泰波尔斯深处的'天空神殿'中,由天空圣兽守护。但要到达那里,需要通过四道试炼。"</p>
|
||||
<p>"四道试炼?"</p>
|
||||
<p>"是的。"艾拉点头,"风暴试炼、雷霆试炼、光芒试炼、暗影试炼。每一道试炼都有强大的守护者,只有通过所有试炼,才能获得天空之泪。"</p>
|
||||
<p>林克站起身:"我明白了。我会通过试炼,取得天空之泪。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷看着林克,眼中闪过一丝感激:"年轻人,谢谢你。但我必须警告你,试炼非常危险。即使是天空族的精英,也很少有人能全部通过。"</p>
|
||||
<p>"我会尽全力的。"林克说。</p>
|
||||
<p>艾丽丝站起身:"林克,我陪你去。"</p>
|
||||
<p>"我也去!"尼梅尔说。</p>
|
||||
<p>希尔薇点头:"我也一起。"</p>
|
||||
<p>林克看着她们,露出微笑:"好。我们一起去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉带四人前往试炼的入口。</p>
|
||||
<p>那是一座漂浮在云海上的巨大塔楼,塔身散发着金色的光芒。塔门前站着两个天空族的战士,他们看到艾拉,立刻行礼。</p>
|
||||
<p>"艾拉大人。"</p>
|
||||
<p>"这位是来自阿拉德大陆的勇者林克,他要挑战四道试炼。"艾拉说。</p>
|
||||
<p>战士们看向林克,眼中闪过一丝惊讶,但很快恢复平静。</p>
|
||||
<p>"请进。"他们打开塔门。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克踏入塔内,艾丽丝、尼梅尔和希尔薇紧随其后。</p>
|
||||
<p>塔内是一个巨大的空间,中央有一个传送阵。</p>
|
||||
<p>"第一道试炼是风暴试炼。"艾拉的声音从身后传来,"你们将面对风暴之主。祝你们好运。"</p>
|
||||
<p>林克点头,踏上传送阵。</p>
|
||||
<p>光芒闪烁,四人的身影消失在塔内。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克再次睁开眼睛时,发现自己站在一片狂风之中。</p>
|
||||
<p>这里是一个巨大的竞技场,四周是高耸的墙壁。天空中乌云密布,雷声轰鸣,狂风呼啸。</p>
|
||||
<p>在竞技场的中央,站着一个巨大的身影。</p>
|
||||
<p>那是一个人身鹰翼的怪物,翅膀展开足有十几米宽。他的眼睛燃烧着青色的火焰,手中握着一把由风构成的长矛。</p>
|
||||
<p>"挑战者..."风暴之主发出沙哑的声音,"我是风暴试炼的守护者。想要通过试炼,就要打败我。"</p>
|
||||
<p>他举起长矛,狂风更加猛烈:"来吧,让我看看你的实力!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧细雪之舞,眼神坚定。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑的光芒更盛,他冲向风暴之主。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>他进入流心状态,身形变得模糊。狂风在他周围呼啸,但无法阻挡他的前进。</p>
|
||||
<p>"来吧!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-149.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-151.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-120.html" class="sidebar-chapter ">第120章:番外·与莎兰的魔法时光</a>
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter current">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(150)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,965 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>风暴试炼 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 151</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>风暴之主挥动长矛,一道巨大的风刃横扫而出。</p>
|
||||
<p>"风暴斩!"</p>
|
||||
<p>风刃带着撕裂一切的威力,朝四人袭来。林克举剑格挡,但风刃的力量太强,他被震退了好几步。</p>
|
||||
<p>"这家伙...不简单。"林克稳住身形。</p>
|
||||
<p>艾丽丝举起法杖:"元素护盾!"</p>
|
||||
<p>紫色的护盾挡在四人面前,减轻了风刃的冲击。</p>
|
||||
<p>希尔薇拉弓射箭,三支箭矢同时飞向风暴之主。但狂风将箭矢吹偏,没有命中目标。</p>
|
||||
<p>"在我的领域里,风听从我的命令!"风暴之主狂笑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"尼梅尔,你从侧面攻击!希尔薇,掩护!艾丽丝,用魔法支援!"林克迅速制定战术。</p>
|
||||
<p>三人点头,分散开来。</p>
|
||||
<p>林克正面冲向风暴之主,光剑划出一道道剑气。风暴之主挥动长矛,将剑气全部击散。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>林克腾空而起,从空中劈下。同时,尼梅尔从侧面冲来,短剑刺向风暴之主的翅膀。</p>
|
||||
<p>"铛!"</p>
|
||||
<p>长矛挡住了林克的攻击,但尼梅尔的突袭成功了——短剑刺入了风暴之主的翅膀根部。</p>
|
||||
<p>"啊!"风暴之主发出痛苦的吼叫。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希尔薇抓住机会,连续射出五支箭。艾丽丝也释放出火球和冰锥。</p>
|
||||
<p>风暴之主被多人攻击,陷入被动。他挥动翅膀,掀起一阵狂风,将所有人吹开。</p>
|
||||
<p>"风暴领域!"</p>
|
||||
<p>竞技场上空形成了一个巨大的风眼,无数风刃在其中旋转。整个空间变成了风暴的海洋。</p>
|
||||
<p>"小心!这些风刃会撕裂一切!"艾丽丝大喊。</p>
|
||||
<p>林克咬牙,运转体内的力量。</p>
|
||||
<p>"极·鬼剑术(暴风式)!"</p>
|
||||
<p>他召唤出二十四把光剑,形成剑阵,挡住周围的风刃。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你的剑术不错。"风暴之主看着林克,"但在我的风暴中,你永远无法获胜!"</p>
|
||||
<p>他举起长矛,整个身体化作一道龙卷风,朝林克冲来。</p>
|
||||
<p>"风暴冲锋!"</p>
|
||||
<p>林克握紧细雪之舞,眼中闪过坚定。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他的身影化作闪电,迎向风暴之主的冲锋。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两股力量在空中碰撞,爆发出刺眼的光芒。</p>
|
||||
<p>风暴与剑气交织,整个竞技场都在震动。</p>
|
||||
<p>"你...竟然能和我抗衡?"风暴之主惊讶。</p>
|
||||
<p>林克没有回答,继续挥剑。他的每一击都带着坚定的意志,不断突破风暴之主的防御。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>"破军升龙击!"</p>
|
||||
<p>连续的攻击让风暴之主不断后退。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,艾丽丝发现了风暴之主的弱点。</p>
|
||||
<p>"林克!他的翅膀根部是他的弱点!那里没有风元素保护!"</p>
|
||||
<p>林克立刻明白了。他使用瞬影斩,瞬间出现在风暴之主身后。</p>
|
||||
<p>"极·神剑术(瞬影斩)!"</p>
|
||||
<p>光剑刺向风暴之主的翅膀根部。风暴之主想要闪避,但希尔薇的箭矢同时射来,限制了他的行动。</p>
|
||||
<p>"啊!"</p>
|
||||
<p>剑锋刺入翅膀根部,风暴之主发出痛苦的吼叫。他的力量开始衰弱,风暴领域也随之消散。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克没有给敌人喘息的机会。他再次挥剑,连续攻击。</p>
|
||||
<p>"万剑归宗!"</p>
|
||||
<p>无数光剑从空中落下,全部命中风暴之主。</p>
|
||||
<p>风暴之主终于倒下了。他的身体化作无数光点,消散在空气中。</p>
|
||||
<p>"恭喜你...通过了第一道试炼。"</p>
|
||||
<p>他的声音在竞技场中回荡,然后完全消失。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>竞技场的墙壁打开,出现了一个新的传送阵。</p>
|
||||
<p>林克喘着气,收回细雪之舞。</p>
|
||||
<p>"成功了..."尼梅尔欢呼。</p>
|
||||
<p>艾丽丝走过来:"林克,你没事吧?"</p>
|
||||
<p>"我没事。"林克摇头,"只是消耗了一些体力。"</p>
|
||||
<p>希尔薇看向传送阵:"第二道试炼应该是雷霆试炼。"</p>
|
||||
<p>林克点头:"走吧。"</p>
|
||||
<p>四人踏上传送阵,光芒闪烁,他们进入了第二道试炼。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>新的试炼场是一个被雷电笼罩的山峰。</p>
|
||||
<p>天空中乌云密布,无数闪电在云层中闪烁。空气中弥漫着电荷的味道,让人感到麻木。</p>
|
||||
<p>在山峰的顶端,站着一个身披雷甲的巨人。他手持一把雷电巨锤,眼睛燃烧着紫色的电光。</p>
|
||||
<p>"雷霆之主..."艾丽丝认出了他。</p>
|
||||
<p>雷霆之主举起巨锤,一声雷鸣响彻云霄。</p>
|
||||
<p>"挑战者...准备好迎接雷霆的审判了吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧细雪之舞,眼神坚定。</p>
|
||||
<p>"来吧。"</p>
|
||||
<p>雷霆之主挥动巨锤,一道粗大的闪电劈向林克。</p>
|
||||
<p>"雷霆审判!"</p>
|
||||
<p>林克迅速闪避,闪电击中地面,留下一个焦黑的坑洞。</p>
|
||||
<p>"这家伙...攻击力比风暴之主更强!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗再次爆发。</p>
|
||||
<p>雷霆之主的攻击极其凶猛,每一锤都能引发雷电风暴。林克不得不不断闪避,同时寻找反击的机会。</p>
|
||||
<p>艾丽丝用魔法护盾保护大家,希尔薇用箭矢牵制敌人,尼梅尔则寻找机会偷袭。</p>
|
||||
<p>四人的配合越来越默契,雷霆之主也逐渐落入下风。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"雷霆风暴!"</p>
|
||||
<p>雷霆之主释放出最强的攻击,无数闪电从天而降,笼罩整个山峰。</p>
|
||||
<p>林克举起细雪之舞,将所有力量集中在剑上。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>剑光与闪电碰撞,爆发出耀眼的光芒。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>经过激烈的战斗,雷霆之主终于被击败。</p>
|
||||
<p>他的身体化作光点消散,林克四人通过了第二道试炼。</p>
|
||||
<p>"还有两道..."林克喘着气,"继续!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-150.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-152.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-121.html" class="sidebar-chapter ">第121章:番外·与帕丽丝的格斗训练</a>
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter current">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(151)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,942 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>光芒与暗影 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 152</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>光芒试炼的场地是一片纯白的空间。</p>
|
||||
<p>这里没有天空和地面,只有无尽的光芒。在光芒的中心,站着一个全身发光的身影。</p>
|
||||
<p>光芒之主,一个没有具体形态的存在,只有轮廓和光芒。</p>
|
||||
<p>"挑战者...在我的光芒中,一切黑暗都将被净化。"</p>
|
||||
<p>他的声音如同圣歌,让人感到平静。但同时,一股强大的光芒力量笼罩了整个空间。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"这道光芒...能灼伤灵魂。"艾丽丝皱眉,"要小心。"</p>
|
||||
<p>林克握紧细雪之舞,但发现自己的剑光在这片光芒中变得黯淡。</p>
|
||||
<p>"这里...我的冰属性被压制了。"</p>
|
||||
<p>光芒之主开口:"在我的领域,黑暗和寒冷都将被驱散。你若想通过试炼,就要证明你心中的光芒。"</p>
|
||||
<p>"心中的光芒?"林克疑惑。</p>
|
||||
<p>"是的。"光芒之主说,"力量不仅仅是破坏,更是守护。当你的心充满光明,你就不会惧怕我的试炼。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克闭上眼睛,感受着周围的光芒。</p>
|
||||
<p>他想起了赛丽亚、艾丽丝、敏泰...所有他在乎的人。他想起了自己一路走来的旅程,每一次战斗,每一次成长。</p>
|
||||
<p>"我的剑...是为了守护。"</p>
|
||||
<p>他睁开眼睛,细雪之舞再次发出光芒。这次,是温暖的金色光芒。</p>
|
||||
<p>"这就是...我心中的光芒。"</p>
|
||||
<p>光芒之主看着他,似乎在点头。</p>
|
||||
<p>"你通过了光芒试炼。"</p>
|
||||
<p>整个空间开始消散,四人的身影被传送到了下一个试炼场。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>暗影试炼的场地是一片无尽的黑暗。</p>
|
||||
<p>这里没有光,只有深邃的黑暗。在黑暗中,无数红色的眼睛在闪烁。</p>
|
||||
<p>"欢迎来到暗影试炼。"</p>
|
||||
<p>一个低沉的声音响起,暗影之主从黑暗中浮现。他是一个完全由暗影构成的存在,没有固定形态,只有轮廓。</p>
|
||||
<p>"在我的黑暗中,一切光芒都将被吞噬。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克感到一股压迫感。这里的黑暗不仅是物理上的,更是精神上的。</p>
|
||||
<p>"不要被黑暗迷惑!"艾丽丝大喊,"保持清醒!"</p>
|
||||
<p>但黑暗开始侵蚀他们的心智。林克看到了一些幻象——过去的敌人、失败的记忆、失去的痛苦...</p>
|
||||
<p>"这是...幻术?"</p>
|
||||
<p>"是的。"暗影之主的声音在黑暗中回荡,"我会让你看到最深的恐惧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克闭上眼睛,抵抗着幻象的侵蚀。</p>
|
||||
<p>他想起了自己的信念——守护那些重要的人。</p>
|
||||
<p>"我不会被恐惧支配。"</p>
|
||||
<p>他睁开眼睛,金色光芒再次从剑上散发出来。黑暗被光芒驱散,幻象也随之消失。</p>
|
||||
<p>"时间之钥的力量..."</p>
|
||||
<p>金色的光芒照亮了黑暗,暗影之主的形态开始动摇。</p>
|
||||
<p>"你的光芒...竟然能穿透我的黑暗?"</p>
|
||||
<p>林克没有回答,挥剑斩向暗影之主。</p>
|
||||
<p>"极·神剑术(破空斩)!"</p>
|
||||
<p>剑光划破黑暗,暗影之主发出痛苦的吼叫。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>在四人合力攻击下,暗影之主终于被击败。</p>
|
||||
<p>"恭喜你们...通过了所有试炼。"</p>
|
||||
<p>他的声音逐渐消散,整个黑暗空间开始崩塌。</p>
|
||||
<p>当光芒再次出现时,林克发现自己站在一座宏伟的神殿前。</p>
|
||||
<p>天空神殿,这里存放着天空之泪。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>神殿的大门缓缓打开,一股神圣的气息扑面而来。</p>
|
||||
<p>林克四人踏入神殿,看到了中央祭台上悬浮着一颗晶莹的泪滴。</p>
|
||||
<p>那就是天空之泪,散发着温暖的光芒。</p>
|
||||
<p>艾拉不知何时出现在神殿中:"你们通过了所有试炼,有资格获得天空之泪。"</p>
|
||||
<p>她看向林克:"但这颗泪滴只能由最纯粹的人触碰。林克,你要亲自去取。"</p>
|
||||
<p>林克点头,走向祭台。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他伸出手,触碰天空之泪。</p>
|
||||
<p>瞬间,一股温暖的力量涌入他的体内。他感到自己的灵魂被净化,所有的疲惫都消失了。</p>
|
||||
<p>同时,他也看到了一些画面——普雷和伊西斯的战斗、天空族的历史、泰波尔斯的未来...</p>
|
||||
<p>"这是...天空之泪的记忆。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当林克收回手时,天空之泪已经融入了他的身体。</p>
|
||||
<p>"天空之泪现在与你同在。"艾拉说,"你可以用它来净化伊西斯。"</p>
|
||||
<p>林克点头:"我们回去吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人通过传送阵返回了泰波尔斯城。</p>
|
||||
<p>普雷正在宫殿中休息,看到林克带着天空之泪归来,眼中露出欣慰。</p>
|
||||
<p>"你成功了..."他说,"现在,是时候结束这一切了。"</p>
|
||||
<p>林克点头:"普雷大人,准备好了吗?"</p>
|
||||
<p>普雷站起身,金色的光芒再次散发:"我已经等了很久了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-151.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-153.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-122.html" class="sidebar-chapter ">第122章:番外·与莫纳亨的念动力</a>
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter current">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(152)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,992 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>天空之战(上) - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 153</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>泰波尔斯的天空神殿,散发着不祥的黑色气息。</p>
|
||||
<p>林克站在神殿入口,感受着里面涌出的压迫感。艾丽丝在他身旁,法杖上凝聚着元素力量。普雷则站在最前方,金色的铠甲在阳光下闪烁着坚定的光芒。</p>
|
||||
<p>"林克,你确定要和我一起进去吗?"普雷问道,"伊西斯的力量非常可怕,即使有天空之泪,也不能保证一定能成功。"</p>
|
||||
<p>林克握紧细雪之舞:"我已经决定了。普雷大人,我会和你一起面对伊西斯。"</p>
|
||||
<p>普雷看着林克坚定的眼神,嘴角露出一丝微笑:"谢谢你,年轻人。有你这样的盟友,是我和泰波尔斯的幸运。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉站在神殿外,目送三人进入。</p>
|
||||
<p>"林克...一定要平安回来。"她轻声说,眼中闪过复杂的情绪。</p>
|
||||
<p>这段时间的相处,让她对林克产生了好感。这个来自阿拉德大陆的年轻人,不仅实力强大,而且心地善良。他愿意冒着生命危险帮助陌生的天空族,这种无私让她深受感动。</p>
|
||||
<p>但此刻,她只能在心中祈祷。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人踏入神殿,黑暗的气息扑面而来。</p>
|
||||
<p>神殿内部已经被伊西斯的力量完全侵蚀。墙壁上布满了黑色的符文,地面裂开着暗紫色的缝隙,从中渗出令人作呕的能量。</p>
|
||||
<p>"你们又来了..."</p>
|
||||
<p>伊西斯的声音从黑暗深处传来,带着嘲讽和傲慢。</p>
|
||||
<p>"我就知道你们不会放弃。但我没想到,你们竟然真的找到了天空之泪。"</p>
|
||||
<p>伊西斯的身影从黑暗中浮现,他的身形比之前更加巨大,黑色的翅膀遮天蔽日。他的眼睛燃烧着暗紫色的火焰,散发出令人窒息的压迫感。</p>
|
||||
<p>"可惜,天空之泪救不了你们。在我的领域里,光明的力量会被完全压制!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷举起长枪:"伊西斯,你的统治到此为止了!"</p>
|
||||
<p>他率先发起攻击,金色的长枪化作流星,直取伊西斯的心脏。</p>
|
||||
<p>"天空之枪!"</p>
|
||||
<p>但伊西斯只是轻轻挥手,一道黑色的屏障挡住了长枪。</p>
|
||||
<p>"太弱了,普雷。你已经被我压制了,这些攻击对我来说毫无意义。"</p>
|
||||
<p>他反手一击,黑暗能量将普雷震退。</p>
|
||||
<p>普雷吐出一口鲜血,但他没有退缩。他稳住身形,再次举起长枪。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克,艾丽丝,我们一起攻击!"</p>
|
||||
<p>林克点头,冲向伊西斯。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>他进入流心状态,身影变得模糊。光剑上凝聚着天空之泪的金色光芒,划出一道道闪耀的剑气。</p>
|
||||
<p>艾丽丝也举起法杖,释放出最强的元素魔法。</p>
|
||||
<p>"元素风暴!"</p>
|
||||
<p>无数火球、冰锥、雷电、风刃同时涌向伊西斯。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三方攻击同时袭来,伊西斯的表情终于变得严肃。</p>
|
||||
<p>"天空之泪的力量...确实有些麻烦。"</p>
|
||||
<p>他展开黑色翅膀,形成一个巨大的护盾。金色的剑气、元素魔法、普雷的长枪同时击中护盾,爆发出刺眼的光芒。</p>
|
||||
<p>"轰——!"</p>
|
||||
<p>整个神殿都在震动,墙壁上的符文开始崩裂。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伊西斯的护盾出现了裂痕,但并没有破碎。</p>
|
||||
<p>"不错,你们的配合很默契。"伊西斯冷笑,"但还不够!"</p>
|
||||
<p>他挥手,无数黑暗能量从四面八方涌来,形成一把把黑色的剑,朝三人射去。</p>
|
||||
<p>"黑暗剑雨!"</p>
|
||||
<p>林克举起细雪之舞,连续挥剑,将袭来的黑暗剑全部斩断。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他的身影化作闪电,冲破黑暗剑雨,直取伊西斯。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伊西斯没想到林克能突破他的攻击,眼神微微一变。</p>
|
||||
<p>林克的光剑已经到了他面前,剑尖上凝聚着天空之泪的金色光芒。</p>
|
||||
<p>"极·神剑术(瞬影斩)!"</p>
|
||||
<p>剑锋刺入了伊西斯的护盾,金色光芒在黑暗中绽放。</p>
|
||||
<p>"什么?!"伊西斯震惊。</p>
|
||||
<p>他的护盾被天空之泪的力量撕裂,剑尖刺入了他的肩膀。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"啊!"伊西斯发出痛苦的吼叫。</p>
|
||||
<p>这是他第一次被真正伤到。天空之泪的光明力量在他体内燃烧,让他感到剧烈的疼痛。</p>
|
||||
<p>"不可能...你竟然能伤到我?!"</p>
|
||||
<p>他疯狂地挥动翅膀,黑暗能量爆发,将林克震飞出去。</p>
|
||||
<p>林克在空中调整姿态,稳稳落地。他的嘴角有一丝血迹,但眼神依然坚定。</p>
|
||||
<p>"伊西斯,你的黑暗...不是无敌的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷看到这一幕,眼中闪过希望。</p>
|
||||
<p>"林克说得对!伊西斯,你吸收的外来黑暗力量,在天空之泪面前毫无意义!"</p>
|
||||
<p>他再次举起长枪,金色的光芒比之前更加耀眼。</p>
|
||||
<p>"这一次,我会彻底击败你!"</p>
|
||||
<p>伊西斯的表情变得阴沉。他看着林克,又看向普雷,眼中闪过一丝恐惧。</p>
|
||||
<p>"该死...天空之泪的力量...比我想象的更强..."</p>
|
||||
<p>他后退了几步,似乎在积蓄力量。</p>
|
||||
<p>"既然如此...那就让你们见识一下,真正的黑暗力量!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伊西斯张开翅膀,整个神殿陷入了彻底的黑暗。</p>
|
||||
<p>所有光明都被吞噬,林克三人陷入了黑暗之中。</p>
|
||||
<p>"黑暗领域!"</p>
|
||||
<p>伊西斯的声音在黑暗中回荡:"在我的领域里,你们将永远找不到方向!"</p>
|
||||
<p>林克握紧细雪之舞,金色光芒在黑暗中显得格外耀眼。</p>
|
||||
<p>"艾丽丝,普雷大人,跟紧我!"</p>
|
||||
<p>艾丽丝的法杖也散发出紫色的光芒,普雷的长枪则发出金色的光辉。</p>
|
||||
<p>三道光芒在黑暗中汇聚,照亮了彼此。</p>
|
||||
<p>"不管多么黑暗,我们都不会放弃!"林克大声说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,黑暗中出现了无数双红色的眼睛。</p>
|
||||
<p>那是伊西斯创造的暗影仆从,它们从黑暗中涌出,朝三人扑来。</p>
|
||||
<p>"来吧!"林克挥剑,"万剑归宗!"</p>
|
||||
<p>无数光剑从空中落下,将暗影仆从一个个击倒。</p>
|
||||
<p>但暗影仆从的数量太多了,击倒一批,又有更多的涌来。</p>
|
||||
<p>"这样下去不是办法!"艾丽丝说,"伊西斯在消耗我们的体力!"</p>
|
||||
<p>普雷点头:"必须找到伊西斯的本体,直接攻击他!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克闭上眼睛,用时间之钥的力量感知周围的气息。</p>
|
||||
<p>时间在他周围缓慢流动,黑暗领域中的能量变化变得清晰。</p>
|
||||
<p>"在那边!"他睁开眼睛,指向黑暗深处的一个方向,"伊西斯的本体在那里!"</p>
|
||||
<p>普雷和艾丽丝立刻明白了他的意思。</p>
|
||||
<p>"我们一起攻击那个方向!"</p>
|
||||
<p>三人同时释放出最强的攻击,朝林克指的方向轰去。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"天空之枪!"</p>
|
||||
<p>"元素风暴!"</p>
|
||||
<p>"极·神剑术(破空斩)!"</p>
|
||||
<p>三股力量汇聚在一起,穿透了黑暗,直取伊西斯的本体。</p>
|
||||
<p>"不!"伊西斯惊呼,"你们怎么找到我的?!"</p>
|
||||
<p>他想要闪避,但三股力量的速度太快了。</p>
|
||||
<p>"轰——!"</p>
|
||||
<p>攻击命中了伊西斯,整个黑暗领域开始崩塌。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>光芒重新照进神殿,伊西斯的身影从黑暗中显现。</p>
|
||||
<p>他的身上有明显的伤痕,黑色翅膀被撕裂了一半,身上多处被金色光芒灼伤。</p>
|
||||
<p>"你们...竟然伤我到这种程度..."</p>
|
||||
<p>他的声音充满了愤怒和不可置信。</p>
|
||||
<p>林克三人也喘着粗气,这场战斗让他们消耗了大量体力。但看到伊西斯受伤,他们知道胜利在望。</p>
|
||||
<p>"伊西斯,结束了。"普雷说,"你已经没有退路了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>但就在这时,伊西斯突然露出诡异的笑容。</p>
|
||||
<p>"结束?不,普雷...真正的战斗才刚刚开始。"</p>
|
||||
<p>他的身体开始膨胀,黑暗能量疯狂涌出。</p>
|
||||
<p>"既然我要毁灭,那就拉着你们一起!"</p>
|
||||
<p>"黑暗自爆!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克的瞳孔瞬间收缩。</p>
|
||||
<p>"不好!他要自爆!"</p>
|
||||
<p>普雷大喊:"快退!"</p>
|
||||
<p>但黑暗能量已经爆发,整个神殿都被吞噬在黑暗之中...</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十三章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-152.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-154.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-123.html" class="sidebar-chapter ">第123章:番外·与泽丁的天界巡逻</a>
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter current">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(153)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,959 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>天空之战(中) - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 154</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>黑暗瞬间吞噬了一切。</p>
|
||||
<p>林克感到自己仿佛置身于无尽的虚空之中,周围没有任何光亮,只有令人窒息的黑暗。他的身体被黑暗侵蚀,感到一阵阵剧痛。</p>
|
||||
<p>"这就是...黑暗自爆的力量..."</p>
|
||||
<p>他想要运转力量抵抗,但体内的能量被黑暗压制,无法动弹。</p>
|
||||
<p>就在他即将被黑暗完全吞噬时,体内的天空之泪突然发出光芒。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的光芒从林克体内爆发,照亮了周围的黑暗。</p>
|
||||
<p>"天空之泪...保护我!"</p>
|
||||
<p>林克感受到一股温暖的力量包裹着自己,黑暗的侵蚀被挡在外面。他睁开眼睛,看到艾丽丝和普雷也被黑暗包裹着。</p>
|
||||
<p>"艾丽丝!普雷大人!"</p>
|
||||
<p>他冲向艾丽丝,将天空之泪的力量延伸到她身上。金色的光芒将两人都保护起来。</p>
|
||||
<p>"林克..."艾丽丝虚弱地睁开眼睛,"谢谢...你救了我..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克又冲向普雷,将他也纳入保护范围。</p>
|
||||
<p>普雷看着林克,眼中露出欣慰:"年轻人,你真的拥有天空之泪的力量...泰波尔斯有救了。"</p>
|
||||
<p>"普雷大人,我们该怎么办?伊西斯的自爆还在继续!"</p>
|
||||
<p>普雷看向四周的黑暗,眼神变得坚定:"只有用天空之泪的力量,彻底净化伊西斯。林克,你的体内有天空之泪,你必须引导它的力量,将伊西斯从我的身体中分离出来。"</p>
|
||||
<p>"分离?"</p>
|
||||
<p>"是的。"普雷点头,"伊西斯虽然是一个独立的存在,但他和我有着本质的联系。只要将他从我的身体中剥离,他就会失去力量来源,最终消散。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克明白了。伊西斯是普雷的黑暗面,他们之间的联系是伊西斯力量的来源。如果切断这种联系,伊西斯就无法维持存在。</p>
|
||||
<p>"我会尽全力的。"</p>
|
||||
<p>他闭上眼睛,开始引导天空之泪的力量。金色的光芒从他体内涌出,越来越强烈。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>在神殿外,艾拉焦急地看着神殿的方向。</p>
|
||||
<p>黑暗的能量不断从神殿中涌出,整个天空之城都在震动。</p>
|
||||
<p>"林克...普雷大人...一定要平安..."</p>
|
||||
<p>尼梅尔和希尔薇也站在她身边,脸上满是担忧。</p>
|
||||
<p>"林克不会有事的!"尼梅尔说,但她的声音也在颤抖。</p>
|
||||
<p>希尔薇握紧弓箭:"我们只能相信他了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>神殿内,林克努力引导着天空之泪的力量。</p>
|
||||
<p>但他发现,这并不容易。天空之泪的力量虽然强大,但需要正确的引导才能发挥作用。</p>
|
||||
<p>"林克,不要抗拒天空之泪的力量。"普雷说,"让它与你的意志融合,成为你的一部分。"</p>
|
||||
<p>林克深吸一口气,放松身体,让天空之泪的力量自由流动。</p>
|
||||
<p>金色光芒越来越强,最终形成了一个巨大的光柱,刺破了黑暗。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伊西斯的声音从黑暗深处传来:"不可能...你怎么能控制天空之泪的力量?!"</p>
|
||||
<p>林克睁开眼睛,看着黑暗中的伊西斯:"因为我的心中没有黑暗。"</p>
|
||||
<p>他举起细雪之舞,金色的剑光划破黑暗:"天空之泪,净化一切!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的光柱朝伊西斯涌去,黑暗开始被净化。</p>
|
||||
<p>伊西斯发出痛苦的吼叫:"不...不要!我的力量...我的黑暗..."</p>
|
||||
<p>他的身体开始崩解,黑色的能量不断从体内涌出,被金色光芒吞噬。</p>
|
||||
<p>"不!我不会让你得逞!"</p>
|
||||
<p>伊西斯拼命反抗,他凝聚最后的黑暗力量,朝林克发动最后一击。</p>
|
||||
<p>"黑暗终结!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克迎向伊西斯的攻击,光剑和黑暗在空中碰撞。</p>
|
||||
<p>"轰——!"</p>
|
||||
<p>两股力量在空中爆发,整个神殿再次震动。</p>
|
||||
<p>林克感到一股巨大的压力,伊西斯的最后反击非常猛烈。但他没有退缩,天空之泪的力量源源不断地涌入他的身体。</p>
|
||||
<p>"伊西斯,你的时代结束了!"</p>
|
||||
<p>他挥剑,金色光芒完全压倒了黑暗。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伊西斯被金色光芒击中,身体开始崩溃。</p>
|
||||
<p>"不...我...我不会...消失..."</p>
|
||||
<p>他的声音越来越弱,身体化作了无数黑色的光点。</p>
|
||||
<p>"普雷...我们...还会再见..."</p>
|
||||
<p>最后,伊西斯完全消散了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>黑暗终于散去,光芒重新照进神殿。</p>
|
||||
<p>林克喘着粗气,跪倒在地。他的体力已经几乎耗尽,但眼神中充满了胜利的喜悦。</p>
|
||||
<p>艾丽丝跑过来扶住他:"林克,你做到了!"</p>
|
||||
<p>普雷也走到林克身边,脸上露出感激的笑容:"谢谢你,年轻人。你拯救了泰波尔斯,也拯救了我。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克想要站起来,但身体太过虚弱,又差点倒下。</p>
|
||||
<p>艾丽丝连忙扶住他:"林克,你消耗太多了,需要休息。"</p>
|
||||
<p>"我没事..."林克勉强笑了笑,"只是有点累。"</p>
|
||||
<p>普雷伸出手,金色的光芒笼罩林克:"让我帮你恢复。"</p>
|
||||
<p>温暖的力量进入林克体内,他的疲劳开始消散。</p>
|
||||
<p>"谢谢普雷大人。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三人走出神殿,外面的天空已经恢复了平静。</p>
|
||||
<p>艾拉看到他们出来,立刻跑了过来:"林克!普雷大人!你们成功了!"</p>
|
||||
<p>她的眼中闪烁着泪光,脸上满是欣喜。</p>
|
||||
<p>尼梅尔和希尔薇也冲了过来,围着林克。</p>
|
||||
<p>"林克,你没事吧?"尼梅尔担心地问。</p>
|
||||
<p>"我没事。"林克微笑道,"伊西斯已经被净化了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷站在众人面前,金色的翅膀完全展开,散发出神圣的光芒。</p>
|
||||
<p>"感谢大家的帮助。"他说,"伊西斯已经消失,泰波尔斯重新恢复了和平。"</p>
|
||||
<p>他看向林克:"尤其是林克,如果没有你的天空之泪,我无法战胜伊西斯。你是我和泰波尔斯的恩人。"</p>
|
||||
<p>林克摇头:"我只是做了该做的事。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉走到林克面前,眼中带着复杂的情感。</p>
|
||||
<p>"林克...谢谢你。"</p>
|
||||
<p>她的声音有些颤抖:"你不仅救了普雷大人,也救了整个泰波尔斯。你是我们的英雄。"</p>
|
||||
<p>林克看着她,露出微笑:"不用这么客气。"</p>
|
||||
<p>但艾拉的眼中,不仅仅是感激。这段时间的相处,她对林克产生了特别的感情。</p>
|
||||
<p>她低下头,脸颊微微泛红:"林克,我有话想对你说..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十四章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-153.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-155.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-124.html" class="sidebar-chapter ">第124章:番外·与马琳的骑士之道</a>
|
||||
<a href="chapter-125.html" class="sidebar-chapter ">第125章:番外·与皇女的皇家约会</a>
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter current">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(154)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,981 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>格兰之森异象 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 156</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>清晨的阳光洒在赛丽亚旅馆的院子里。</p>
|
||||
<p>林克早早起床,站在院子里练习剑术。光剑划出一道道优美的弧线,每一招都精准而流畅。</p>
|
||||
<p>自从泰波尔斯之战后,他感觉自己的剑道又有了新的领悟。天空之泪的力量与他体内的灵魂之源、时间之钥产生了某种共鸣,让他的实力更进一步。</p>
|
||||
<p>"林克,早安。"</p>
|
||||
<p>艾拉从旅馆里走出来,银色的长发在晨光中闪耀。她的身上穿着艾丽丝帮她挑选的长裙——那是一件淡蓝色的裙子,非常适合她。</p>
|
||||
<p>"早安,艾拉。"林克收起光剑,"睡得怎么样?"</p>
|
||||
<p>"很好。"艾拉微笑道,"阿拉德大陆的夜晚...和泰波尔斯完全不同。我看到了很多从未见过的星星。"</p>
|
||||
<p>她走到林克身边,看着他手中的光剑:"林克,你的剑术...真的好厉害。"</p>
|
||||
<p>"谢谢。"林克笑了笑,"要多练习才行。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我也要练习!"艾拉认真地说,"虽然我是天空族的信使,擅长的是飞行和侦察,但我也想学会战斗。这样就能帮到你了。"</p>
|
||||
<p>林克看着她坚定的眼神,点了点头:"好,我教你。"</p>
|
||||
<p>他将细雪之舞收起,拿出一把普通的长剑递给艾拉。</p>
|
||||
<p>"先从基础开始。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,赛丽亚从旅馆里跑出来。</p>
|
||||
<p>"林克!艾拉!早餐准备好了!"</p>
|
||||
<p>三人走进旅馆,餐厅里已经坐满了人。敏泰、帕丽丝、莎兰、奥菲利亚、莫纳亨、泽丁、马琳、艾丽婕、米娅、贝奇、艾泽拉、艾丽丝、尼梅尔、希尔薇...所有后宫都在。</p>
|
||||
<p>艾拉看着这么多人,有些紧张。</p>
|
||||
<p>"艾拉,来坐这里!"敏泰热情地招呼她。</p>
|
||||
<p>"谢谢..."艾拉坐在敏泰旁边。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐时,林克将昨晚看到的红色光芒告诉了大家。</p>
|
||||
<p>"格兰之森方向?"赛丽亚担心地说,"那里...是你旅程开始的地方。"</p>
|
||||
<p>"是的。"林克点头,"那里曾经是洛兰地区,是我第一次拿起剑的地方。"</p>
|
||||
<p>艾丽丝皱眉:"红色光芒...可能是某种邪恶力量的迹象。"</p>
|
||||
<p>"我打算去看看。"林克说。</p>
|
||||
<p>"我陪你去!"艾拉立刻说。</p>
|
||||
<p>"我也去!"艾丽丝站起身。</p>
|
||||
<p>"我也去!"尼梅尔和希尔薇同时说。</p>
|
||||
<p>林克看着她们,露出微笑:"好,我们一起去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>早餐后,林克带着艾拉、艾丽丝、尼梅尔、希尔薇四人出发。</p>
|
||||
<p>赛丽亚站在门口送行:"林克,小心。"</p>
|
||||
<p>"我会的。"林克拥抱了她,"等我回来。"</p>
|
||||
<p>其他后宫们也纷纷告别,目送五人离开。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>格兰之森,阿拉德大陆最古老的森林之一。</p>
|
||||
<p>林克走在熟悉的小路上,回忆起第一次来到这里的情景。那时候他还是一个刚从洛兰出发的年轻人,手中只有一把普通的铁剑,心中充满了对冒险的渴望。</p>
|
||||
<p>"这里...好安静。"艾拉环顾四周,"比泰波尔斯安静多了。"</p>
|
||||
<p>"这里曾经有哥布林和猫妖。"林克说,"但现在已经被清理干净了。"</p>
|
||||
<p>艾丽丝用法杖感知着周围的气息:"但我能感受到...有一股不寻常的力量在这里。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>五人深入森林,很快来到了一个开阔的区域。</p>
|
||||
<p>这里曾经是林克第一次战斗的地方,但现在,空气中弥漫着淡淡的红色雾气。地面上的草木枯萎,呈现出诡异的暗红色。</p>
|
||||
<p>"这就是...异象的源头?"尼梅尔惊讶地说。</p>
|
||||
<p>希尔薇拉弓警戒:"小心,有什么东西在靠近。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,地面突然裂开,几个身形扭曲的生物从地下钻了出来。</p>
|
||||
<p>它们看起来像是哥布林,但全身呈现出暗红色,眼睛燃烧着诡异的光芒。它们的动作僵硬而疯狂,发出令人不安的嘶吼声。</p>
|
||||
<p>"变异哥布林!"艾丽丝认出了它们,"被某种力量侵蚀了!"</p>
|
||||
<p>林克拔出细雪之舞:"保护艾拉,我来对付它们!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克冲向变异哥布林,光剑划出一道冰蓝色的弧线。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>剑尖刺穿了第一个哥布林,但它的反应很奇怪——没有痛苦的表情,反而继续疯狂攻击。</p>
|
||||
<p>"这些家伙...不怕死?"</p>
|
||||
<p>林克连续挥剑,将几个哥布林全部击倒。但更多的哥布林从地下钻出,数量越来越多。</p>
|
||||
<p>"太多了!"尼梅尔喊道。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝举起法杖:"元素爆破!"</p>
|
||||
<p>火球和冰锥横扫而出,将一群哥布林击飞。希尔薇也连续射箭,精准命中哥布林的头颅。</p>
|
||||
<p>艾拉虽然没有战斗经验,但也挥舞着长剑,努力保护自己。</p>
|
||||
<p>"这样下去不是办法!"艾丽丝说,"必须找到异象的源头!"</p>
|
||||
<p>林克看向森林深处,那里有一股更强烈的红色光芒。</p>
|
||||
<p>"在那边!"他指着森林深处,"我去看看!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克使用瞬影斩,瞬间出现在森林深处。</p>
|
||||
<p>那里有一个巨大的裂缝,红色的能量不断从中涌出。裂缝周围,刻满了诡异的符文,散发着令人不安的气息。</p>
|
||||
<p>"这是...空间裂缝?"林克皱眉。</p>
|
||||
<p>他想起艾丽丝体内的灵魂之源,想起赫尔德的创新世纪...这种空间裂缝,和赫尔德的力量有几分相似。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克!"艾丽丝等人追了上来。</p>
|
||||
<p>她看到裂缝,脸色一变:"这是...无形者的气息!"</p>
|
||||
<p>"无形者?"</p>
|
||||
<p>"是的。"艾丽丝严肃地说,"第四使徒希洛克,被称为'无形者'。她能附身他人,制造幻象,操纵精神。"</p>
|
||||
<p>她看向裂缝:"这个裂缝...可能是她复苏的征兆。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,裂缝中传出了一阵诡异的声音。</p>
|
||||
<p>"终于...有人来了..."</p>
|
||||
<p>一个女性的声音在空气中回荡,带着冷漠和傲慢。</p>
|
||||
<p>"我是希洛克...无形者...我已经等了很久了..."</p>
|
||||
<p>林克握紧细雪之舞,眼神坚定。</p>
|
||||
<p>"希洛克...又是一个使徒。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>裂缝中涌出更多的红色能量,几个更强大的怪物从裂缝中走出。</p>
|
||||
<p>它们不是普通的变异生物,而是被希洛克力量完全侵蚀的存在。</p>
|
||||
<p>"先撤退!"艾丽丝说,"我们还不清楚希洛克的力量有多强!"</p>
|
||||
<p>林克点头:"走!"</p>
|
||||
<p>五人迅速撤离,但林克心中已经明白——新的冒险,即将开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到赛丽亚旅馆,林克将情况告诉了大家。</p>
|
||||
<p>"希洛克...第四使徒。"艾丽丝说,"她是被赫尔德杀害的使徒之一。如果她复苏了,那意味着..."</p>
|
||||
<p>"赫尔德的计划失败了,但使徒们开始陆续苏醒。"林克接过话头。</p>
|
||||
<p>艾拉站在林克身边,轻轻握住他的手:"林克,不管发生什么,我都会陪着你。"</p>
|
||||
<p>林克看着她,露出微笑:"谢谢你,艾拉。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当晚,林克独自站在阳台上,看着夜空。</p>
|
||||
<p>"赫尔德、伊西斯、希洛克...使徒们一个个出现。"</p>
|
||||
<p>他想起米歇尔说过的话——使徒是世界的守护者,但赫尔德的计划打破了平衡。</p>
|
||||
<p>"也许...这就是新的命运。"</p>
|
||||
<p>艾丽丝走过来,站在他身边:"林克,你在担心什么?"</p>
|
||||
<p>"在想...这个世界到底怎么了。"林克说,"使徒、黑暗、异象...似乎永远不会结束。"</p>
|
||||
<p>艾丽丝靠在他肩上:"但我们会一直陪着你。你已经打败了赫尔德,净化了伊西斯...希洛克也不会是问题。"</p>
|
||||
<p>林克搂住她:"谢谢。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天,莎莎的信送到了。</p>
|
||||
<p>"林克:</p>
|
||||
<p>希洛克的复苏比我想象的更快。她的力量正在向阿拉德大陆蔓延,如果不尽快阻止,整个大陆都会被她的无形之力侵蚀。</p>
|
||||
<p>我查到一些线索——希洛克的本体可能在一个叫'魔界深处'的地方。那是赫尔德曾经囚禁她的地方。</p>
|
||||
<p>如果你想阻止她,可能需要回到魔界。</p>
|
||||
<p>——莎莎"</p>
|
||||
<p>林克放下信,眼神坚定。</p>
|
||||
<p>"看来...又要回魔界了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十六章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(希洛克篇 开启)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-155.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-157.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-126.html" class="sidebar-chapter ">第126章:番外·与米娅的工坊时光</a>
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter current">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(156)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,967 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>魔界深处 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 157</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>三天后,林克一行人站在寂静城的传送门前。</p>
|
||||
<p>这次前往魔界,林克决定带更多的人。除了艾拉、艾丽丝、尼梅尔、希尔薇外,他还邀请了赛丽亚、敏泰和帕丽丝一同前往。</p>
|
||||
<p>"希洛克不是普通的敌人。"林克在出发前对大家说,"她是第四使徒,擅长精神控制和幻象。我们需要所有人的力量。"</p>
|
||||
<p>赛丽亚握着他的手:"我会一直陪着你。"</p>
|
||||
<p>敏泰和帕丽丝也表示愿意同行。</p>
|
||||
<p>艾丽丝用法杖感知着传送门的能量:"魔界的气息...比之前更混乱了。希洛克的力量正在扩散。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>卢克站在传送门旁,苍老的眼睛看着林克。</p>
|
||||
<p>"年轻人,又要去魔界?"</p>
|
||||
<p>"是的,卢克爷爷。希洛克复苏了,我们需要去阻止她。"</p>
|
||||
<p>卢克沉默了片刻,然后叹了口气:"希洛克...她是第四使徒,曾经是最强大的使徒之一。赫尔德杀死她的时候,我以为一切都结束了。"</p>
|
||||
<p>他看向林克:"但看来,命运并非如此。你要小心,希洛克的能力非常诡异——她能附身他人,操纵精神,制造无法分辨的幻象。"</p>
|
||||
<p>"我会注意的。"林克说。</p>
|
||||
<p>卢克点了点头:"这个传送门会直接将你们送到魔界营地的附近。凯蒂应该已经收到消息了,她会在那里等你们。"</p>
|
||||
<p>"谢谢卢克爷爷。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>光芒闪烁,七人的身影消失在传送门中。</p>
|
||||
<p>当林克再次睁开眼睛时,熟悉的紫色天空映入眼帘。</p>
|
||||
<p>魔界,他又回来了。</p>
|
||||
<p>但这次,魔界的气息比之前更加压抑。空气中弥漫着一股无形的压力,让人感到不安。</p>
|
||||
<p>"这股气息..."艾丽丝皱眉,"比赫尔德在的时候还要压抑。希洛克的力量正在侵蚀整个魔界。"</p>
|
||||
<p>艾拉展开翅膀,飞到空中侦察:"前面有动静!很多人在朝这边来!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看向前方,看到一群人正朝他们走来。</p>
|
||||
<p>领头的是凯蒂,身后跟着魔界营地的冒险家们。</p>
|
||||
<p>"林克!"凯蒂快步走来,"你终于来了!情况比我们想象的更糟!"</p>
|
||||
<p>"发生什么了?"</p>
|
||||
<p>凯蒂的脸色凝重:"希洛克的力量正在快速扩散。被她侵蚀的生物越来越多,甚至有些冒险家都被她控制了。"</p>
|
||||
<p>她看向林克身后的众人:"你们来得正是时候。我们需要尽快行动。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>众人来到魔界营地。</p>
|
||||
<p>营地的情况比上次更糟。很多居民都被希洛克的力量影响,精神恍惚,行为异常。凯蒂用魔法勉强压制着这些影响,但效果越来越弱。</p>
|
||||
<p>"希洛克的本体在哪里?"林克问。</p>
|
||||
<p>"魔界深处。"凯蒂说,"那是赫尔德曾经囚禁她的地方。现在她从那里复苏,力量正在向外扩散。"</p>
|
||||
<p>她拿出一幅地图,指向地图中央的一个位置:"从这里到魔界深处,大约需要三天路程。但沿途都是被希洛克侵蚀的区域,非常危险。"</p>
|
||||
<p>林克看着地图,点了点头:"我们出发。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天,七人离开魔界营地,朝着魔界深处前进。</p>
|
||||
<p>沿途的景象让所有人感到不安。原本的紫色天空变得更加暗淡,空气中弥漫着无形的雾气。地面的植物呈现出诡异的红色,偶尔能看到被侵蚀的生物在远处徘徊。</p>
|
||||
<p>"这些生物..."敏泰皱眉,"它们的眼睛都是红色的。"</p>
|
||||
<p>"那是希洛克的标记。"艾丽丝说,"被她侵蚀的存在,眼睛都会变成红色。"</p>
|
||||
<p>希尔薇拉弓警戒:"小心,有东西在靠近!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>一群被侵蚀的怪物从迷雾中冲了出来。</p>
|
||||
<p>它们曾经是魔界的普通生物——狼、蝙蝠、史莱姆——但现在完全变了模样。全身呈现出暗红色,眼睛燃烧着诡异的光芒,行为疯狂而混乱。</p>
|
||||
<p>"战斗!"林克拔出细雪之舞。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>林克挥剑迎向第一个怪物,光剑划出一道冰蓝色的弧线。怪物的身体被斩开,但没有立刻死亡,反而继续疯狂攻击。</p>
|
||||
<p>"这些家伙...不怕死吗?"尼梅尔惊讶。</p>
|
||||
<p>"它们已经失去了理智。"艾丽丝说,"被希洛克完全控制了。"</p>
|
||||
<p>赛丽亚挥舞法杖,释放出治愈魔法,保护众人。帕丽丝则用爪刺和毒粉攻击敌人。敏泰使用冰系魔法,配合希尔薇的箭矢。</p>
|
||||
<p>艾拉虽然战斗经验不足,但也努力挥舞长剑,保护自己。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>经过一番激战,怪物们终于被全部消灭。</p>
|
||||
<p>林克收起光剑,看向远方:"还有三天的路程...这会很艰难。"</p>
|
||||
<p>凯蒂之前给他们准备的补给足够使用,但被侵蚀的区域越来越多,战斗会越来越频繁。</p>
|
||||
<p>"我们继续前进。"林克说,"不能让希洛克继续扩散她的力量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第三天,众人终于来到了魔界深处的入口。</p>
|
||||
<p>那是一个巨大的峡谷,峡谷深处散发着暗红色的光芒。峡谷的入口被诡异的符文封锁,似乎在阻止外人进入。</p>
|
||||
<p>"这就是魔界深处..."艾丽丝轻声说,"我能感受到里面有一股极其强大的力量。"</p>
|
||||
<p>林克握紧细雪之舞:"走吧。"</p>
|
||||
<p>他走向峡谷入口,但符文突然亮起,一道红色的屏障挡住了去路。</p>
|
||||
<p>"有结界!"帕丽丝说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,峡谷深处传来了一阵笑声。</p>
|
||||
<p>"呵呵...终于有人来了..."</p>
|
||||
<p>一个女性的身影从峡谷中浮现。她有着紫色的长发,身材高挑,穿着暗红色的长裙。她的眼睛是诡异的红色,散发着令人不安的气息。</p>
|
||||
<p>"希洛克!"艾丽丝认出了她。</p>
|
||||
<p>希洛克看着林克,嘴角带着微笑:"你就是那个打败赫尔德的人类?林克?"</p>
|
||||
<p>"是的。"林克握剑。</p>
|
||||
<p>希洛克轻笑:"有点意思。但你知道吗?赫尔德杀死我的时候,我也感受到了死亡...然后是漫长的黑暗..."</p>
|
||||
<p>她的表情变得阴沉:"我在黑暗中等待了很久...终于,有人打破了封印,让我得以复苏。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着她:"你打算做什么?"</p>
|
||||
<p>"做什么?"希洛克歪了歪头,"我只是想...活下去。"</p>
|
||||
<p>她展开双臂,无形的力量从她体内涌出:"但这个世界太挤了。使徒们互相残杀,赫尔德想要重造世界...我不想被消灭,所以我必须先消灭威胁。"</p>
|
||||
<p>她的眼睛锁定了林克:"你打败了赫尔德,你很强...所以你是我最大的威胁。"</p>
|
||||
<p>林克的眼神变得凌厉:"那就来试试吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希洛克微笑着摇了摇头:"不急,林克。我们还有很多时间。"</p>
|
||||
<p>她的身影开始变得透明:"我会慢慢...侵蚀你。让你看到最深的恐惧,让你失去最重要的人..."</p>
|
||||
<p>"然后,我会夺走你的身体。"</p>
|
||||
<p>她的身影完全消失了,只留下一句话在空气中回荡:</p>
|
||||
<p>"期待我们的下次见面,林克..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧剑柄,眼神凝重。</p>
|
||||
<p>艾丽丝走到他身边:"希洛克...她的力量比我想象的更强。"</p>
|
||||
<p>"她能制造幻象,也能附身他人。"艾丽丝说,"我们必须找到她的本体,在她完全复苏之前击败她。"</p>
|
||||
<p>林克看向峡谷深处的屏障:"这个结界...需要打破。"</p>
|
||||
<p>艾拉飞到屏障前,感受着上面的能量:"这是希洛克的力量...需要强大的光明能量才能打破。"</p>
|
||||
<p>林克想起了体内的天空之泪。</p>
|
||||
<p>"也许...我可以试试。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克伸出手,金色光芒从体内涌出,触碰到屏障。</p>
|
||||
<p>天空之泪的力量与希洛克的结界碰撞,爆发出刺眼的光芒。</p>
|
||||
<p>"轰——!"</p>
|
||||
<p>屏障开始崩裂,最终完全破碎。</p>
|
||||
<p>峡谷的入口打开了。</p>
|
||||
<p>"走吧。"林克说,"进去。"</p>
|
||||
<p>七人踏入峡谷,魔界深处,就在前方。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十七章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-156.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-158.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-127.html" class="sidebar-chapter ">第127章:番外·与贝奇的人造之心</a>
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter current">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(157)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,989 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>幻象迷宫 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 158</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>峡谷内部是一片奇异的空间。</p>
|
||||
<p>紫色的天空变成了深邃的黑色,无数光点在黑暗中闪烁,如同夜空中的星辰。地面是光滑如镜的水晶,倒映着每个人的身影。</p>
|
||||
<p>"这里...好奇怪。"敏泰皱眉,"我能感受到一股无形的力量在监视我们。"</p>
|
||||
<p>艾丽丝用法杖感知着周围:"希洛克的力量无处不在。她能制造幻象,让我们看到她想让们看到的东西。"</p>
|
||||
<p>"保持警惕。"林克说,"不要被任何幻象迷惑。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>七人继续深入峡谷。</p>
|
||||
<p>但走着走着,林克发现周围的景象开始变化。</p>
|
||||
<p>原本光滑的水晶地面出现了裂痕,裂痕中渗出暗红色的能量。空气中弥漫着诡异的雾气,能见度越来越低。</p>
|
||||
<p>"林克..."赛丽亚突然停下脚步。</p>
|
||||
<p>林克回头看她:"怎么了?"</p>
|
||||
<p>但当他转身时,发现赛丽亚的眼神变得空洞,仿佛失去了灵魂。</p>
|
||||
<p>"赛丽亚!"林克冲向她。</p>
|
||||
<p>但就在他触碰到赛丽亚的瞬间,她的身体化作了无数光点,消散在空气中。</p>
|
||||
<p>"不..."林克瞳孔收缩。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"这是幻象。"艾丽丝的声音从身后传来,"林克,不要被迷惑!"</p>
|
||||
<p>林克转身,发现艾丽丝、敏泰、帕丽丝、希尔薇、尼梅尔、艾拉...所有人都不见了。</p>
|
||||
<p>整个空间只剩下他一个人。</p>
|
||||
<p>"希洛克!"林克大喊。</p>
|
||||
<p>但只有回声在空旷的空间中回荡。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,周围的景象再次变化。</p>
|
||||
<p>林克发现自己回到了洛兰——他旅程开始的地方。</p>
|
||||
<p>但洛兰已经不是他记忆中的样子。村庄被火焰吞噬,村民们倒在血泊中,怪物在四处游荡。</p>
|
||||
<p>"这是...什么?"</p>
|
||||
<p>"这是你的恐惧。"</p>
|
||||
<p>希洛克的声音在空中回荡:"你害怕失去,害怕失败,害怕你珍视的一切被毁灭。"</p>
|
||||
<p>"我只是在帮你...看到你的恐惧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧细雪之舞,眼神变得坚定。</p>
|
||||
<p>"这不是真的。"</p>
|
||||
<p>他闭上眼睛,运转体内的力量。天空之泪的光芒在他体内闪耀,驱散了幻象的影响。</p>
|
||||
<p>当林克再次睁开眼睛时,发现自己站在一个巨大的迷宫中。</p>
|
||||
<p>迷宫的墙壁是由无数镜子组成的,每一面镜子都映照着不同的画面。</p>
|
||||
<p>"幻象迷宫..."林克喃喃自语。</p>
|
||||
<p>他看向其中一面镜子,镜中是赛丽亚被怪物杀死的画面。</p>
|
||||
<p>另一面镜子,是艾丽丝被黑暗吞噬。</p>
|
||||
<p>第三面镜子,是他所有的后宫都被杀害,只剩他一个人孤独地站在废墟中。</p>
|
||||
<p>"这些都是幻象..."林克咬紧牙关。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>但幻象越来越真实。</p>
|
||||
<p>林克看到一个身影从迷宫深处走来——那是他自己,但眼睛是红色的。</p>
|
||||
<p>"你是谁?"林克问。</p>
|
||||
<p>"我是你。"另一个林克说,"我是你心中的恐惧,是你害怕成为的样子。"</p>
|
||||
<p>他举起剑,指向林克:"你害怕失去所有人,害怕孤独,所以你拼命想要变强...但你知道,有些东西是永远无法守护的。"</p>
|
||||
<p>"闭嘴。"林克说。</p>
|
||||
<p>"我说错了吗?"另一个林克微笑,"赫尔德差点杀死你,伊西斯几乎摧毁泰波尔斯...现在希洛克又来了。你能守护多久?"</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>另一个林克继续说:"你的后宫们...她们跟着你,冒着生命危险。如果她们死了,你会怎么办?"</p>
|
||||
<p>林克握紧剑柄,回忆起一路走来的旅程。</p>
|
||||
<p>赛丽亚的温柔、艾丽丝的坚强、敏泰的可爱、帕丽丝的勇敢...每一个他爱的人,都愿意追随他,和他一起面对危险。</p>
|
||||
<p>"她们...是自己选择跟随我的。"</p>
|
||||
<p>林克抬起头,眼神变得坚定:"我不是一个人在战斗。她们相信我,我也相信她们。"</p>
|
||||
<p>"就算我害怕失去,我也不会停止前进。因为只有前进,才能守护她们!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>另一个林克露出惊讶的表情:"你能抵抗幻象?"</p>
|
||||
<p>林克举起细雪之舞:"因为我的心中,有比恐惧更重要的东西。"</p>
|
||||
<p>他冲向另一个林克,光剑划出一道金色的剑气。</p>
|
||||
<p>"极·神剑术(破空斩)!"</p>
|
||||
<p>另一个林克被剑气击中,身体开始崩解。</p>
|
||||
<p>"不...这不可能..."</p>
|
||||
<p>他的身体化作了无数光点,融入了周围的空间。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>迷宫开始崩塌。</p>
|
||||
<p>林克感觉到周围的空间在扭曲,然后,他重新站在了水晶地面上。</p>
|
||||
<p>艾丽丝、赛丽亚、敏泰、帕丽丝、希尔薇、尼梅尔、艾拉...所有人都在他身边。</p>
|
||||
<p>"林克!"赛丽亚扑进他怀里,"你没事吧?刚才我们都看到了幻象..."</p>
|
||||
<p>"我没事。"林克紧紧抱住她,"都是幻象。你们都在这里。"</p>
|
||||
<p>艾丽丝的脸色苍白:"希洛克...她的幻象太强了。我们每个人都看到了不同的恐惧。"</p>
|
||||
<p>敏泰眼中还带着泪光:"我看到...林克哥哥被杀死了..."</p>
|
||||
<p>帕丽丝握紧拳头:"我也是。我看到你死了,我无法保护你..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着众人,心中涌起复杂的情感。</p>
|
||||
<p>希洛克的幻象让每个人都经历了最深的恐惧。但她们都挺过来了。</p>
|
||||
<p>"大家都没事,这才是最重要的。"林克说,"希洛克想用恐惧击垮我们,但她失败了。"</p>
|
||||
<p>艾拉展开翅膀,感知着周围:"幻象迷宫已经消失了。我们可以继续前进。"</p>
|
||||
<p>林克点头:"走吧。希洛克一定在前面等着我们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>七人继续深入峡谷。</p>
|
||||
<p>幻象迷宫之后,地形变得更加复杂。水晶地面变成了扭曲的空间,有时候走一步会跨越很远的距离,有时候走很久却还在原地。</p>
|
||||
<p>"这里的空间被希洛克扭曲了。"艾丽丝说,"我们需要找到正确的路径。"</p>
|
||||
<p>林克运转时间之钥的力量,感知着空间的变化。</p>
|
||||
<p>"时间在这里也是扭曲的。"他说,"但我能感受到...那边的空间比较稳定。"</p>
|
||||
<p>他指向左前方的一条道路。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>众人沿着林克指示的道路前进,终于来到了一个巨大的空间。</p>
|
||||
<p>空间的中央,有一个巨大的祭坛。祭坛上刻满了符文,散发着红色的光芒。</p>
|
||||
<p>在祭坛的中央,希洛克正坐在一个由无形力量构成的王座上。</p>
|
||||
<p>她看到林克等人,露出微笑:"你们通过了幻象迷宫,有点意思。"</p>
|
||||
<p>林克握剑:"希洛克,你的幻象对我们没用。"</p>
|
||||
<p>希洛克轻笑:"幻象只是热身而已。现在...让我看看你们能否通过我的真正试炼。"</p>
|
||||
<p>她站起身,无形的剑出现在她手中:"让我看看,你是否有资格与我战斗。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗瞬间爆发。</p>
|
||||
<p>希洛克挥动无形的剑,一道暗红色的剑气横扫而出。林克举剑格挡,但剑气的力量太强,他被震退了好几步。</p>
|
||||
<p>"你的剑...还不错。"希洛克说,"但在我面前,还不够。"</p>
|
||||
<p>她再次挥剑,这次是连续的三道剑气。</p>
|
||||
<p>林克连续闪避,同时挥剑反击。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>光剑刺向希洛克,但她的身影突然消失,出现在林克身后。</p>
|
||||
<p>"太慢了。"</p>
|
||||
<p>她挥剑,林克被击中,吐出一口鲜血。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克!"赛丽亚惊呼。</p>
|
||||
<p>艾丽丝举起法杖:"元素风暴!"</p>
|
||||
<p>无数火球、冰锥、雷电涌向希洛克。但希洛克只是挥手,无形的力量将所有攻击全部挡下。</p>
|
||||
<p>"你们的攻击对我无效。"她说,"我是无形者,没有实体,你们的攻击无法触及我。"</p>
|
||||
<p>林克站起身,擦去嘴角的血迹。</p>
|
||||
<p>"没有实体?那我就要找到你的本体!"</p>
|
||||
<p>他运转天空之泪的力量,金色的光芒在剑上凝聚。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"天空之泪?"希洛克微微皱眉,"那是普雷的力量...你怎么会有?"</p>
|
||||
<p>林克没有回答,冲向希洛克。</p>
|
||||
<p>"万剑归宗!"</p>
|
||||
<p>无数光剑从空中落下,全部朝希洛克袭去。希洛克展开无形的力量,试图挡住攻击。</p>
|
||||
<p>但天空之泪的光芒穿透了她的防御,金色的剑光在她身上留下了伤痕。</p>
|
||||
<p>"什么?!"希洛克惊讶,"你能伤害我?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克的眼神坚定:"天空之泪能净化一切黑暗,包括你的无形之力!"</p>
|
||||
<p>希洛克的表情变得阴沉:"好...很好。看来我要认真对待你了。"</p>
|
||||
<p>她的气息突然暴涨,无形的力量在她周围凝聚,形成了一个巨大的影子。</p>
|
||||
<p>"无形化身!"</p>
|
||||
<p>战斗,才刚刚开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十八章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-157.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-159.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-128.html" class="sidebar-chapter ">第128章:番外·与艾泽拉的守护誓言</a>
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter current">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(158)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,966 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>无形之战 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 159</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>无形化身的出现,让整个空间的压力瞬间增加了数倍。</p>
|
||||
<p>希洛克的身影被一个巨大的黑色影子包裹,影子的轮廓模糊不定,时而是人形,时而是兽形,时而完全没有固定的形态。无数黑色的剑气从影子中延伸出来,如同蛛网一般覆盖了整个空间。</p>
|
||||
<p>"这是我的无形化身。"希洛克的声音从影子的深处传来,"在这个形态下,我没有任何实体限制,可以自由操控空间中的任何力量。"</p>
|
||||
<p>林克握紧细雪之舞,感受到前所未有的压力。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>无形化身首先发动攻击。</p>
|
||||
<p>无数黑色的剑气从四面八方朝林克袭来,速度快到几乎无法看清。林克挥剑格挡,连续的金属碰撞声响彻整个空间。</p>
|
||||
<p>"铛铛铛铛!"</p>
|
||||
<p>但剑气太多了,林克被击中了好几次,身上出现了多处伤痕。</p>
|
||||
<p>"林克!"赛丽亚释放出治愈魔法,金色的光芒覆盖林克的身体,伤口开始愈合。</p>
|
||||
<p>"谢谢。"林克稳定住身形,"我来吸引她的注意力,你们找机会攻击!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克再次冲向无形化身。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑的光芒更盛,剑身上凝聚着天空之泪的金色能量。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>林克进入流心状态,身影变得模糊,在无形化身的攻击中穿梭。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他化作闪电,连续四斩,每一剑都命中无形化身。金色的光芒在黑色影子上留下了深深的痕迹。</p>
|
||||
<p>"啊!"希洛克发出痛苦的吼叫。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝看到机会,举起法杖:"元素风暴!"</p>
|
||||
<p>火球、冰锥、雷电、风刃同时涌向无形化身。希尔薇也连续射出五支箭,每一支都缠绕着天空之泪的光芒。</p>
|
||||
<p>帕丽丝冲上前,用爪刺攻击无形化身的弱点。敏泰释放出冰系魔法,试图冻结影子的行动。</p>
|
||||
<p>尼梅尔和艾拉也加入了战斗,从不同方向进行攻击。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>无形化身被众人围攻,开始动摇。</p>
|
||||
<p>"可恶...你们这些蝼蚁!"希洛克愤怒地喊道。</p>
|
||||
<p>她挥手,无形的力量爆发,将所有人震飞出去。</p>
|
||||
<p>林克被震飞了几十米,撞在水晶墙壁上,吐出一口鲜血。其他人也被震飞,受了不同程度的伤。</p>
|
||||
<p>"你们以为这样就能打败我?"希洛克的声音充满了嘲讽,"我是第四使徒,无形者!在魔界深处,我就是无敌的存在!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克艰难地站起来,擦去嘴角的血迹。</p>
|
||||
<p>"无敌?我不相信有无敌的存在。"</p>
|
||||
<p>他回想起与赫尔德的战斗,当时他也以为自己会输。但他没有放弃,最终逆转了战局。</p>
|
||||
<p>"赫尔德曾经也是使徒,但我打败了她。你,也不会例外。"</p>
|
||||
<p>希洛克冷笑:"赫尔德?她只是自取灭亡。而我...我会亲手杀死你!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>无形化身再次发动攻击。</p>
|
||||
<p>这次,希洛克不再只是用剑气,而是操控整个空间。水晶地面开始崩裂,无数碎片化作利刃朝林克袭来。空间本身也在扭曲,让林克难以判断方向。</p>
|
||||
<p>"空间操控..."林克咬牙。</p>
|
||||
<p>他想起了时间之钥的力量。如果希洛克能操控空间,那他就用时间来对抗。</p>
|
||||
<p>"时间之钥...让时间变慢!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>金色的光芒从林克体内爆发,周围的时间开始变慢。</p>
|
||||
<p>飞来的水晶碎片、扭曲的空间、希洛克的攻击...一切都变得缓慢。</p>
|
||||
<p>林克在这缓慢的时间中,快速移动,避开所有攻击。</p>
|
||||
<p>"什么?!"希洛克惊讶,"你还能操控时间?!"</p>
|
||||
<p>林克没有回答,继续移动。他来到了无形化身的面前,举起细雪之舞。</p>
|
||||
<p>"极·神剑术(瞬影斩)!"</p>
|
||||
<p>他瞬移到无形化身身后,剑光贯穿了黑色的影子。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"啊啊啊!"希洛克发出痛苦的吼叫。</p>
|
||||
<p>金色的光芒在无形化身体内蔓延,天空之泪的力量正在净化她的黑暗。</p>
|
||||
<p>"不...不可能...你竟然能伤到我到这种程度..."</p>
|
||||
<p>林克没有给希洛克喘息的机会,继续攻击。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>无数剑光将无形化身完全覆盖,每一剑都带着天空之泪的净化力量。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>但就在这时,希洛克突然发出冷笑。</p>
|
||||
<p>"你以为...这样就能打败我?"</p>
|
||||
<p>无形化身突然崩解,化作无数黑色的光点,朝林克涌来。</p>
|
||||
<p>"小心!"艾丽丝大喊,"她想附身你!"</p>
|
||||
<p>林克想要躲避,但黑色的光点太快了,它们冲入了林克的身体。</p>
|
||||
<p>"不!"赛丽亚惊呼。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克感到一股冰冷的力量侵入他的身体。</p>
|
||||
<p>那是希洛克的意识,正在试图控制他的精神。</p>
|
||||
<p>"林克...把你的身体交给我..."希洛克的声音在他脑海中回荡,"我会让你看到...真正的力量..."</p>
|
||||
<p>林克咬紧牙关,抵抗着希洛克的侵蚀。</p>
|
||||
<p>"滚出我的身体!"</p>
|
||||
<p>他运转天空之泪、灵魂之源、时间之钥三股力量,金色的光芒在体内爆发,与希洛克的黑暗力量对抗。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"什么?你的体内有这么多力量?"希洛克惊讶,"灵魂之源...时间之钥...还有天空之泪...你是怎么做到的?"</p>
|
||||
<p>林克没有回答,继续将希洛克的力量往外推。</p>
|
||||
<p>"我说了...滚出我的身体!"</p>
|
||||
<p>金色的光芒越来越强,最终,希洛克的黑暗力量被完全驱逐出林克的身体。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>黑色的光点在空中重新凝聚,形成了希洛克的身影。但这次,她的气息比之前弱了很多。</p>
|
||||
<p>"你竟然能抵抗我的附身..."希洛克看着林克,眼中露出惊讶,"你到底是什么人?"</p>
|
||||
<p>林克喘着气,脸色苍白。刚才的对抗消耗了他大量的力量,但他没有倒下。</p>
|
||||
<p>"我是林克。阿拉德大陆的冒险家,她们的守护者。"</p>
|
||||
<p>他举起细雪之舞,剑指希洛克:"而且...我是打败你的人。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希洛克沉默了片刻,然后发出一阵笑声。</p>
|
||||
<p>"有趣...太有趣了..."</p>
|
||||
<p>她看着林克:"你确实很强,林克。比我想象的还要强。"</p>
|
||||
<p>"但你知道吗?"她的表情变得阴沉,"这还只是开始。我的力量...还没有完全复苏。"</p>
|
||||
<p>她的身影开始变得透明:"我会回来的,林克。当我们下次见面时,我会让你看到真正的无形者之力。"</p>
|
||||
<p>林克想要追击,但身体已经到了极限。他只能看着希洛克的身影完全消失。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束了。</p>
|
||||
<p>林克跪倒在地,几乎失去了意识。</p>
|
||||
<p>"林克!"赛丽亚冲过来扶住他,"你没事吧?"</p>
|
||||
<p>"我...没事..."林克虚弱地说,"希洛克...逃走了..."</p>
|
||||
<p>艾丽丝走过来:"她的力量确实很强,而且还没有完全复苏。如果她完全复苏,我们可能无法战胜她。"</p>
|
||||
<p>林克握紧拳头:"那就在她复苏之前,再次找到她。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>众人休息了一会儿,开始撤离魔界深处。</p>
|
||||
<p>这次虽然击退了希洛克,但她逃走了,而且威胁着整个魔界。</p>
|
||||
<p>"我们需要更多的力量。"林克说,"才能彻底击败她。"</p>
|
||||
<p>艾丽丝点头:"我听说,有一些古老的道具可以对抗无形者。也许我们可以去寻找。"</p>
|
||||
<p>林克看向远方:"那就去找。在希洛克完全复苏之前,我们必须做好准备。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百五十九章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-158.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-160.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-129.html" class="sidebar-chapter ">第129章:魔界的召唤</a>
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter current">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(159)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,962 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>无形者的秘密 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 160</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>返回寂静城后,林克直接倒下了。</p>
|
||||
<p>与希洛克的战斗消耗了他所有的力量。三股力量的同时运转——时间之钥、灵魂之源、天空之泪——让他的身体承受了巨大的负担。虽然击退了希洛克,但他自己也到了极限。</p>
|
||||
<p>赛丽亚一直守在林克身边,握着他的手。她的眼中满是担忧,但更多的是坚定。</p>
|
||||
<p>"林克一定会没事的。"她对其他人说,"他每次都能挺过来。"</p>
|
||||
<p>艾丽丝用法术检测着林克的身体状况:"他的生命力在快速恢复,但精神力消耗太大了。需要休息。"</p>
|
||||
<p>艾拉、敏泰、帕丽丝、希尔薇、尼梅尔也都守在旁边。每个人都担心地看着昏迷的林克。</p>
|
||||
<p>卢克站在一旁,浑浊的眼睛中闪过一丝复杂:"这个年轻人...竟然能同时操控三股力量。即使是我,也不敢这样做。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第一天,林克没有醒来。</p>
|
||||
<p>赛丽亚寸步不离地守着他,甚至没有睡觉。艾丽丝和其他人也轮流守夜,确保林克得到最好的照顾。</p>
|
||||
<p>第二天,林克还是没有醒来。</p>
|
||||
<p>艾拉开始研究天空族的古籍,希望能找到对付希洛克的方法。她知道,林克醒来后,第一件事就是寻找击败希洛克的方法。</p>
|
||||
<p>"我必须做好准备。"她对自己说。</p>
|
||||
<p>第三天清晨,林克终于醒了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>睁开眼睛的那一刻,林克看到赛丽亚趴在他床边睡着了。她的手还握着他的手,脸上带着疲惫。</p>
|
||||
<p>林克轻轻动了动手指,赛丽亚立刻醒了。</p>
|
||||
<p>"林克!你醒了!"她的眼中瞬间涌出了泪水,"你昏迷了三天...我好担心..."</p>
|
||||
<p>"我没事。"林克的声音有些沙哑,"抱歉,让你担心了。"</p>
|
||||
<p>赛丽亚摇了摇头,俯下身轻轻吻了林克的额头:"只要你平安就好。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>很快,其他人也都知道林克醒了,纷纷赶来探望。</p>
|
||||
<p>艾丽丝第一个进来,用法术再次检查林克的身体:"你的力量恢复了大半,但还需要休息。"</p>
|
||||
<p>"我知道。"林克试图坐起来,"希洛克...她逃走了?"</p>
|
||||
<p>艾丽丝点头,神色凝重:"是的。她重伤逃走,但我不确定她什么时候会恢复。"</p>
|
||||
<p>林克皱眉:"我们需要在她完全复苏之前,找到彻底击败她的方法。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉走过来,手中拿着一本古老的书籍:"林克,我在天空族的古籍中找到了一些关于希洛克的记载。"</p>
|
||||
<p>"什么记载?"林克问。</p>
|
||||
<p>艾拉打开书籍,书页泛黄,但文字依然清晰。</p>
|
||||
<p>"希洛克是第四使徒,被称为'无形者'。她的本体不是实体的存在,而是某种...概念。"</p>
|
||||
<p>"概念?"敏泰疑惑。</p>
|
||||
<p>"是的。"艾拉指着书中的一段文字,"她诞生于虚无和恐惧之中,是某种负面情绪的集合体。正因如此,她没有固定的实体,可以附身他人,制造幻象。"</p>
|
||||
<p>帕丽丝皱眉:"那要怎么才能打败一个概念?"</p>
|
||||
<p>艾拉翻到下一页:"书中提到,对付无形者,需要一种特殊的力量——光之结晶。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"光之结晶?"林克问。</p>
|
||||
<p>"是的。"艾拉说,"那是泰波尔斯的圣物,和天空之泪齐名。天空之泪是净化的力量,而光之结晶是封印的力量。"</p>
|
||||
<p>艾丽丝接过话头:"如果能得到光之结晶,我们就能封印希洛克,阻止她复苏。"</p>
|
||||
<p>林克思考了片刻:"光之结晶在哪里?"</p>
|
||||
<p>艾拉摇头:"这就是问题所在。光之结晶在上一次希洛克被击败时,被封印在'光之圣殿'中。那是泰波尔斯最神圣的地方,只有通过特殊的试炼才能进入。"</p>
|
||||
<p>"什么样的试炼?"</p>
|
||||
<p>"光之试炼。"艾拉说,"这是泰波尔斯最困难的试炼,据说从未有人通过。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>赛丽亚担忧地说:"从未有人通过?那怎么拿到光之结晶?"</p>
|
||||
<p>艾拉看向林克:"但林克拥有天空之泪,也许能通过。"</p>
|
||||
<p>林克沉默了片刻,然后点头:"我会去试试。"</p>
|
||||
<p>"林克,你刚醒,身体还很虚弱..."赛丽亚握住他的手。</p>
|
||||
<p>"我知道。"林克说,"但我不能等希洛克完全复苏。必须尽快行动。"</p>
|
||||
<p>他看向艾拉:"光之圣殿在泰波尔斯吗?"</p>
|
||||
<p>艾拉点头:"是的。我可以带你去。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,莎莎的信通过魔法传讯送达。</p>
|
||||
<p>艾丽丝接过信,念给林克听:</p>
|
||||
<p>"林克:</p>
|
||||
<p>希洛克的复苏比我想象的更快。她的力量正在向整个世界扩散,不仅仅是魔界。</p>
|
||||
<p>我在中央公园发现了一些被她侵蚀的冒险家,他们的精神被希洛克控制,变成了她的傀儡。如果不能尽快阻止她,整个阿拉德大陆都会被她的无形之力吞噬。</p>
|
||||
<p>附:有消息说,泰波尔斯的光之圣殿中,有对付无形者的圣物。如果你能得到它,也许能封印希洛克。</p>
|
||||
<p>——莎莎"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克放下信,看向众人。</p>
|
||||
<p>"看来,我们已经没有选择了。"</p>
|
||||
<p>他看向艾拉:"准备好回泰波尔斯了吗?"</p>
|
||||
<p>艾拉点头:"随时可以出发。"</p>
|
||||
<p>林克又看向其他人:"这次,我一个人去。你们留在这里,保护阿拉德大陆。"</p>
|
||||
<p>"不行!"赛丽亚说,"我不让你一个人去!"</p>
|
||||
<p>艾丽丝也站起来:"林克,你需要我们。希洛克不是普通的敌人。"</p>
|
||||
<p>敏泰也走过来:"林克哥哥,我也要去!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着她们坚定的眼神,叹了口气:"好。但只有你们几个。其他人留下。"</p>
|
||||
<p>最终,决定与林克一起去泰波尔斯的有:艾丽丝、艾拉、赛丽亚、敏泰。</p>
|
||||
<p>帕丽丝、希尔薇、尼梅尔留在阿拉德大陆,监视希洛克力量的扩散。</p>
|
||||
<p>"如果发现任何异常,立刻通知我。"林克对她们说。</p>
|
||||
<p>帕丽丝点头:"放心,我们会守好的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天,林克等人踏上前往泰波尔斯的旅程。</p>
|
||||
<p>通过寂静城的传送门,他们很快回到了那片漂浮在云海上的大陆。</p>
|
||||
<p>但这次,泰波尔斯的景象有了变化。天空中弥漫着淡淡的红色雾气,那是希洛克的力量正在侵蚀这里。</p>
|
||||
<p>艾拉展开翅膀,感知着周围的气息:"希洛克的力量...已经影响到泰波尔斯了。她的侵蚀速度比我想象的快。"</p>
|
||||
<p>林克握紧细雪之舞:"我们必须抓紧时间。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人朝光之圣殿的方向走去。</p>
|
||||
<p>沿途,他们遇到了一些被侵蚀的生物——它们曾经是泰波尔斯的普通动物,但现在眼睛变成了红色,行为疯狂。</p>
|
||||
<p>林克挥剑解决了几个,但更多的是避开战斗,快速前进。</p>
|
||||
<p>"这些生物...和魔界的一样。"敏泰说,"都是被希洛克控制的。"</p>
|
||||
<p>艾丽丝皱眉:"她的力量扩散得太快了。如果不能尽快封印她,整个世界都会被侵蚀。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约两个小时,光之圣殿终于出现在他们面前。</p>
|
||||
<p>那是一座完全由光芒构成的建筑,悬浮在云海之上,散发着神圣的气息。与上次见到的泰波尔斯建筑不同,这座圣殿更加纯粹,仿佛是由光本身凝聚而成。</p>
|
||||
<p>圣殿周围有一层金色的结界,阻止了希洛克力量的侵蚀。</p>
|
||||
<p>"这就是光之圣殿..."艾拉轻声说,"泰波尔斯最神圣的地方。"</p>
|
||||
<p>"光之结晶就在里面吗?"赛丽亚问。</p>
|
||||
<p>艾拉点头:"是的。但要进入,需要通过光之试炼。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克走到结界前,感受到里面散发出的强大力量。</p>
|
||||
<p>"我来打开结界。"</p>
|
||||
<p>他运转天空之泪的力量,金色的光芒从体内涌出,触碰到结界。</p>
|
||||
<p>天空之泪的力量与结界产生了共鸣,符文开始发光,结界上出现了一个入口。</p>
|
||||
<p>"走吧。"林克说。</p>
|
||||
<p>四人踏入光之圣殿,迎接他们的,是前所未有的试炼。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-159.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-161.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-130.html" class="sidebar-chapter ">第130章:魔界营地</a>
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter current">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(160)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,978 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>光之试炼 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 161</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>踏入光之圣殿,林克感受到一股神圣的力量将他包围。</p>
|
||||
<p>与外面的世界不同,圣殿内部一片纯白。没有墙壁,没有地面,没有天花板,只有无尽的光芒。在这种光芒中,林克几乎看不清自己的身体。</p>
|
||||
<p>"林克..."赛丽亚的声音从旁边传来。</p>
|
||||
<p>林克转头,发现赛丽亚、艾丽丝、敏泰、艾拉都不见了。他又是一个人。</p>
|
||||
<p>"又来了...又是分开的试炼。"他喃喃自语。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一个声音在光芒中响起:</p>
|
||||
<p>"欢迎来到光之圣殿,勇者。"</p>
|
||||
<p>那是一个温柔的女声,仿佛来自四面八方。</p>
|
||||
<p>"我是光之圣殿的守护者,光之意志。你来到这里,是为了获得光之结晶吗?"</p>
|
||||
<p>林克点头:"是的。我需要光之结晶来封印希洛克,阻止她的侵蚀。"</p>
|
||||
<p>光之意志沉默了片刻,然后说:"光之结晶不是普通的物品。它是泰波尔斯的神圣圣物,只给予真正值得的人。"</p>
|
||||
<p>"要获得它,你必须通过光之试炼。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我准备好了。"林克说。</p>
|
||||
<p>光之意志的声音再次响起:"光之试炼有三个阶段。第一,面对你的过去。第二,面对你的恐惧。第三,面对你的本心。"</p>
|
||||
<p>"只有通过这三个阶段,你才能获得光之结晶。"</p>
|
||||
<p>林克握紧细雪之舞:"开始吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>光芒开始变化,周围的景象逐渐形成。</p>
|
||||
<p>林克发现自己回到了洛兰——那个他旅程开始的地方。</p>
|
||||
<p>但这是过去的洛兰,他还只是一个普通的年轻人,手中握着铁剑,站在村口。</p>
|
||||
<p>"这是...我的过去?"</p>
|
||||
<p>"是的。"光之意志的声音说,"第一阶段的试炼,是面对你的过去。看着这一切,然后告诉我,你是否后悔。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着眼前的景象,回忆起当初离开洛兰时的情景。</p>
|
||||
<p>那时候的他,只是一个普通的冒险者,心中充满了对未知世界的好奇和向往。他不知道未来会遇到什么,不知道自己会经历多少战斗,不知道自己会爱上这么多人。</p>
|
||||
<p>他一步步走过洛兰的街道,看着熟悉的建筑,熟悉的面孔。</p>
|
||||
<p>然后,他看到了当初的自己——那个年轻的林克,站在村口,回望村庄,眼中满是不舍和期待。</p>
|
||||
<p>"你后悔吗?"光之意志问,"如果让你重新选择,你还会离开洛兰吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>他想起了一路上的经历——格兰之森的战斗、天空之城的冒险、天界的对决、魔界的激战...每一次都充满危险,每一次都可能有去无回。</p>
|
||||
<p>他也想起了那些他爱的人——赛丽亚、艾丽丝、敏泰、帕丽丝、莎兰、奥菲利亚、莫纳亨、泽丁、马琳、皇女艾丽婕、米娅、贝奇、艾泽拉、尼梅尔、希尔薇、艾拉...每一个都是他的牵挂,每一个都让他更加不舍。</p>
|
||||
<p>"我不后悔。"他最终说。</p>
|
||||
<p>"为什么?"光之意志问,"你经历了这么多危险,失去了这么多,你不后悔吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克摇了摇头:"我不后悔。因为我遇到的每一个人,经历的每一件事,都让我成为了现在的我。"</p>
|
||||
<p>他看向光之意志的方向:"如果我当初没有离开洛兰,我就不会遇到赛丽亚,不会遇到所有我爱的人。我也许会安全,但我不会幸福。"</p>
|
||||
<p>光芒开始变化,第一阶段的试炼通过了。</p>
|
||||
<p>"你的回答是真实的。"光之意志说,"第一阶段通过。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>景象再次变化。</p>
|
||||
<p>这次,林克来到了一个战场的残骸。到处都是尸体,空气中弥漫着血腥味。</p>
|
||||
<p>在战场的中央,他看到了自己的身体——冰冷地躺在地上,眼睛紧闭。</p>
|
||||
<p>而在他的尸体周围,是他爱的人的尸体——赛丽亚、艾丽丝、敏泰...所有人都倒下了。</p>
|
||||
<p>"这是你的恐惧。"光之意志的声音说,"你害怕失去她们,害怕无法保护她们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着这一幕,心中涌起巨大的痛苦。</p>
|
||||
<p>这是他最深的恐惧,是他每次战斗后都会担心的事情。如果有一天,他无法保护她们,她们就会...变成这样。</p>
|
||||
<p>"你害怕吗?"光之意志问。</p>
|
||||
<p>"我害怕。"林克承认,"我非常害怕。"</p>
|
||||
<p>"那你为什么还要继续战斗?为什么还要让她们跟着你冒险?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克沉默了。</p>
|
||||
<p>然后,他抬起头,眼中闪过坚定:"因为...她们选择了我。"</p>
|
||||
<p>他看向赛丽亚的尸体,轻声说:"我从来没有强迫她们跟随我。每一次,都是她们自己选择要和我在一起。"</p>
|
||||
<p>"她们知道危险,但她们还是选择了这条路。如果因为害怕,就阻止她们追求自己的选择,那才是对她们的背叛。"</p>
|
||||
<p>他转向光之意志的方向:"所以,我会继续战斗,继续变强。不是为了消除恐惧,而是为了在恐惧面前,依然能保护她们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>光芒再次变化,尸体消失了。</p>
|
||||
<p>"你的回答是真实的。"光之意志说,"第二阶段通过。"</p>
|
||||
<p>林克松了口气。两个阶段了,还剩最后一个。</p>
|
||||
<p>"第三阶段,面对你的本心。"光之意志说,"这个阶段,没有问题,没有选择。你只需要...看着。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>光芒彻底消散,林克发现自己站在一个空旷的空间中。</p>
|
||||
<p>在他的面前,出现了一个身影——那是他自己,但眼睛是红色的,身上散发着黑暗的气息。</p>
|
||||
<p>"这是...我?"</p>
|
||||
<p>"这是你内心深处的阴影。"光之意志说,"每个人都有的阴暗面。它包含了你的自私、你的欲望、你的仇恨..."</p>
|
||||
<p>"如果你能面对它,接受它,它就会消失。如果你被它吞噬...你就无法获得光之结晶。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>阴影林克看着林克,嘴角带着诡异的笑容:"你知道你为什么能通过前两个阶段吗?因为你...虚伪。"</p>
|
||||
<p>"你说你不后悔,但你在每个夜晚都会想,如果当初没有离开洛兰,你就不用承受这些痛苦。"</p>
|
||||
<p>"你说你不害怕,但你每次战斗后都会做噩梦,梦见她们死在你面前。"</p>
|
||||
<p>"你只是...在骗自己。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着阴影林克,没有说话。</p>
|
||||
<p>阴影林克继续说:"你还记得赫尔德吗?你杀了她。你以为你是为了正义,但其实...你只是想变强。你想证明自己是最强的冒险者,你想让所有人都认可你。"</p>
|
||||
<p>"你的后宫们...你爱她们,但你也享受被这么多女人爱着的感觉。你的爱,有多少是纯粹的?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧拳头,身体微微颤抖。</p>
|
||||
<p>阴影林克说得...没有错。</p>
|
||||
<p>他确实有过那些想法。他确实有过自私的欲望。他确实不是完美的。</p>
|
||||
<p>"也许...我不配获得光之结晶。"他低声说。</p>
|
||||
<p>"你说得对。我不是一个纯粹的人。我有私心,有欲望,有阴暗面。"</p>
|
||||
<p>他看向阴影林克:"如果光之结晶只给完美的人,那我确实不配。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在林克准备放弃的时候,阴影林克突然笑了。</p>
|
||||
<p>"放弃了吗?这样就放弃了吗?"</p>
|
||||
<p>林克愣了一下。</p>
|
||||
<p>阴影林克继续说:"你以为光之试炼是测试你是否完美?不...光之试炼测试的,是你是否能面对自己的不完美。"</p>
|
||||
<p>他的身体开始变化,逐渐变成了林克的样子,但眼神变得更加清澈。</p>
|
||||
<p>"每个人都是不完美的。英雄也好,圣人也罢,都有自己的阴暗面。"</p>
|
||||
<p>"真正的光芒,不是没有阴影,而是能在阴影面前,依然前行。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着眼前这个变化后的身影,突然明白了。</p>
|
||||
<p>"我接受我的阴暗面。"他说,"我有私心,有欲望,有恐惧...但这不影响我想保护她们的心。"</p>
|
||||
<p>"我也许不完美,但我会为了她们,变得更好。"</p>
|
||||
<p>身影微笑着点了点头,然后化作了无数光点,融入了林克的身体。</p>
|
||||
<p>林克感到一股温暖的力量在体内流转,那是...光之结晶。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"恭喜你,勇者。"光之意志的声音响起,"你通过了光之试炼,获得了光之结晶。"</p>
|
||||
<p>光芒再次充满整个空间,林克发现自己回到了圣殿的入口。</p>
|
||||
<p>赛丽亚、艾丽丝、敏泰、艾拉也都站在那里,她们也都通过了各自的试炼。</p>
|
||||
<p>"林克!"赛丽亚冲过来抱住他,"我看到了好多...好多可怕的画面..."</p>
|
||||
<p>"我没事。"林克紧紧抱住她,"都过去了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉走上前:"林克,你获得光之结晶了吗?"</p>
|
||||
<p>林克点头,伸出手。一颗金色的水晶出现在他掌心,散发着神圣的光芒。</p>
|
||||
<p>"这就是光之结晶。"艾拉说,"有了它,我们就能封印希洛克了。"</p>
|
||||
<p>艾丽丝看着光之结晶,神色凝重:"但希洛克已经恢复了不少力量。要封印她,我们需要找到她的本体。"</p>
|
||||
<p>林克收起光之结晶:"那就去找。在我们的力量耗尽之前,一定要封印她。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人离开光之圣殿,踏上了寻找希洛克本体的旅程。</p>
|
||||
<p>但她们不知道的是,在圣殿之外,一双红色的眼睛正在注视着她们。</p>
|
||||
<p>"光之结晶...果然被他拿到了。"希洛克的声音在空中回荡,"有趣...太有趣了..."</p>
|
||||
<p>"让我看看,你能否找到我的本体...在我完全复苏之前。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十一章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-160.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-162.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-131.html" class="sidebar-chapter ">第131章:凯蒂的指引</a>
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter current">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(161)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,967 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>希洛克的陷阱 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 162</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>离开光之圣殿后,林克等人开始在泰波尔斯寻找希洛克的本体。</p>
|
||||
<p>但很快,她们发现了一个问题——希洛克的侵蚀正在加速。</p>
|
||||
<p>原本只有边缘区域被侵蚀,现在连中心区域也开始出现红色的雾气。被侵蚀的生物越来越多,甚至开始出现被控制的天空族战士。</p>
|
||||
<p>"她的力量...比之前更强了。"艾拉展开翅膀,感知着周围的气息,"我感觉到了...她的力量在快速扩散。"</p>
|
||||
<p>艾丽丝皱眉:"她在吸收泰波尔斯的能量。如果我们不尽快找到她,整个泰波尔斯都会被她吞噬。"</p>
|
||||
<p>林克握紧细雪之舞:"我们能追踪她的位置吗?"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾拉闭上眼睛,用天空族的天赋感知着周围的能量流动。</p>
|
||||
<p>片刻后,她睁开眼睛:"找到了。她的力量源头...在泰波尔斯的中央区域,那里曾经是普雷大人的宫殿。"</p>
|
||||
<p>"普雷的宫殿?"林克疑惑。</p>
|
||||
<p>"是的。"艾拉点头,"那是泰波尔斯最核心的地方,能量最集中。希洛克选择那里作为她的基地,可以更快地吸收整个泰波尔斯的力量。"</p>
|
||||
<p>林克看向中央区域的方向:"那就去那里。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人朝中央区域前进。</p>
|
||||
<p>沿途的景象越来越诡异。天空完全变成了暗红色,地面的植物全部枯萎,空气中弥漫着令人窒息的压迫感。被侵蚀的生物成群结队地游荡,它们的眼睛都是红色的,行为疯狂。</p>
|
||||
<p>林克挥剑斩杀了几只挡路的生物,但更多的是源源不断地涌来。</p>
|
||||
<p>"太多了!"敏泰用冰系魔法阻挡着敌人。</p>
|
||||
<p>艾丽丝释放出元素风暴,将一大群被侵蚀的生物击飞。但她们很快就发现,这些生物杀不完,而且数量还在增加。</p>
|
||||
<p>"这样下去不行。"赛丽亚说,"我们需要快速穿过这里,不能被拖住。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克点头:"我来开路。"</p>
|
||||
<p>他运转天空之泪的力量,金色的光芒在剑上凝聚。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他化作闪电,连续斩破敌人的包围,为众人开辟出一条道路。</p>
|
||||
<p>四人快速穿过被侵蚀的区域,终于来到了中央区域的入口。</p>
|
||||
<p>但眼前的景象让所有人都愣住了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>中央区域已经被完全侵蚀。</p>
|
||||
<p>原本宏伟的建筑现在扭曲变形,墙上爬满了诡异的藤蔓。空气中弥漫着无形的力量,让人感到精神恍惚。</p>
|
||||
<p>最可怕的是,无数被侵蚀的天空族战士守在入口,它们的数量足有上百个。</p>
|
||||
<p>"这是...希洛克的军队。"艾拉的脸色苍白。</p>
|
||||
<p>那些战士曾经是泰波尔斯的守护者,但现在它们的眼睛都是红色的,被希洛克完全控制了。</p>
|
||||
<p>"我们要怎么进去?"敏泰问。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧光剑:"只能硬闯了。"</p>
|
||||
<p>他正要冲上去,但艾拉突然拉住他:"等等!"</p>
|
||||
<p>"怎么了?"</p>
|
||||
<p>艾拉指着那些被控制的战士:"它们曾经是我们天空族的同胞...你能不能...不要杀它们?"</p>
|
||||
<p>林克看向她,看到她眼中的恳求。</p>
|
||||
<p>他沉默了片刻,然后点头:"我会尽量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克冲向被控制的战士,但这次他没有用剑刃,而是用剑脊。</p>
|
||||
<p>他击昏了几个战士,但更多的战士涌上来。林克不得不后退。</p>
|
||||
<p>"太多了,而且不能杀它们..."他咬牙。</p>
|
||||
<p>艾丽丝举起法杖:"我来用睡眠魔法!"</p>
|
||||
<p>紫色的光芒覆盖了周围的战士,十几个战士陷入沉睡。但更多的战士还在涌来。</p>
|
||||
<p>赛丽亚也释放出治愈魔法,试图净化被侵蚀的战士,但效果很微弱。</p>
|
||||
<p>"希洛克的侵蚀太深了...普通的净化无法解除。"她说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在众人陷入困境时,一个声音从身后传来:</p>
|
||||
<p>"需要帮忙吗?"</p>
|
||||
<p>林克回头,看到普雷带着一队天空族的战士出现。</p>
|
||||
<p>"普雷大人!"艾拉惊喜地喊道。</p>
|
||||
<p>普雷看向林克:"我来拖住这些被控制的战士。你们进去,找到希洛克的本体。"</p>
|
||||
<p>林克点头:"谢谢普雷大人!"</p>
|
||||
<p>他转向众人:"走!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>四人冲过被控制的战士,进入中央区域的深处。</p>
|
||||
<p>普雷和他的战士们在外面与被侵蚀的战士战斗,为林克争取时间。</p>
|
||||
<p>"希望他能成功。"普雷看着林克消失的背影。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>中央区域的内部更加诡异。</p>
|
||||
<p>扭曲的建筑、弥漫的红色雾气、不时传来的诡异声音...一切都散发着希洛克的力量。</p>
|
||||
<p>林克等人小心翼翼地前进,时刻保持警惕。</p>
|
||||
<p>"她的本体就在前方。"艾拉说,"我能感受到了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>终于,她们来到了一座巨大的宫殿前。</p>
|
||||
<p>这座宫殿曾经是普雷的居所,但现在完全变了模样。墙壁上刻满了诡异的符文,门上悬浮着一个巨大的红色能量球。</p>
|
||||
<p>"这就是...希洛克的巢穴。"艾丽丝说。</p>
|
||||
<p>林克握紧细雪之舞和光之结晶:"准备好了吗?"</p>
|
||||
<p>众人点头。</p>
|
||||
<p>林克推开门,踏入宫殿。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>宫殿内部是一个巨大的大厅。</p>
|
||||
<p>大厅的中央,希洛克坐在一个由无形力量构成的宝座上。她的气息比之前更加强大,显然在林克获得光之结晶的这段时间里,她吸收了大量的能量。</p>
|
||||
<p>"你来了,林克。"希洛克看着他,嘴角带着微笑,"我等你很久了。"</p>
|
||||
<p>林克举起细雪之舞:"希洛克,你的侵蚀到此为止了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希洛克轻笑:"到此为止?"</p>
|
||||
<p>她站起身,展开无形的翅膀:"你以为获得了光之结晶,就能封印我?"</p>
|
||||
<p>她挥手,周围的空气开始扭曲。</p>
|
||||
<p>"从一开始,我就知道你会来这里。你以为光之圣殿的试炼是什么?"</p>
|
||||
<p>林克的瞳孔收缩:"什么意思?"</p>
|
||||
<p>希洛克的笑容更加诡异:"光之试炼...是我故意让你通过的。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"什么?!"艾丽丝惊讶。</p>
|
||||
<p>希洛克看向林克:"你以为光之结晶是什么神圣的物品?它只是一个容器...一个可以被我侵蚀的容器。"</p>
|
||||
<p>"当你获得光之结晶的时候,我就已经在里面注入了我的力量。"</p>
|
||||
<p>林克低头看向手中的光之结晶,发现金色的光芒中,确实夹杂着红色的光点。</p>
|
||||
<p>"你现在手中的光之结晶...已经被我污染了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克的脸色变得难看。</p>
|
||||
<p>他没想到,希洛克竟然早就设下了陷阱。光之试炼...竟然是她的计谋!</p>
|
||||
<p>"那又如何?"林克说,"即使光之结晶被污染,我依然可以打败你!"</p>
|
||||
<p>希洛克摇头:"不,你做不到。因为..."</p>
|
||||
<p>她的眼中闪过冷光:"当光之结晶被污染,你体内也有我的力量了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克感到体内突然涌起一股冰冷的力量。</p>
|
||||
<p>那是...希洛克的力量,正在他的体内扩散!</p>
|
||||
<p>"不..."林克握紧剑,试图抵抗。</p>
|
||||
<p>但希洛克的力量太强了,天空之泪、灵魂之源、时间之钥三股力量同时运转,才勉强压制住。</p>
|
||||
<p>"林克!"赛丽亚冲过来,"你没事吧?!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克的脸色苍白,额头冒出冷汗:"我...我能压制住..."</p>
|
||||
<p>希洛克看着他:"有点意思。三股力量同时运转,还能抵抗我的侵蚀。但你...能坚持多久?"</p>
|
||||
<p>她展开无形化身:"在你被完全控制之前,让我看看你的极限!"</p>
|
||||
<p>战斗,再次爆发。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十二章完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-161.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-163.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-132.html" class="sidebar-chapter ">第132章:营地危机</a>
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter current">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(162)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,992 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>无形之战 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 163</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>希洛克的无形化身再次展开,巨大的暗影笼罩了整个宫殿。</p>
|
||||
<p>林克感到体内的侵蚀越来越强。希洛克的力量在他的血液中流动,试图控制他的精神。但天空之泪、灵魂之源、时间之钥三股力量也在运转,将她的力量压制住。</p>
|
||||
<p>"你...到底是怎么做到的?"希洛克看着他,"普通人不可能同时承受三股力量,还能抵抗我的侵蚀。"</p>
|
||||
<p>林克没有回答,而是举剑冲向希洛克。</p>
|
||||
<p>"流心!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗比之前更加艰难。</p>
|
||||
<p>林克不仅要对付希洛克的无形化身,还要抵抗体内的侵蚀。每一次挥剑,他都要分出一部分力量来压制希洛克的力量。</p>
|
||||
<p>"你的剑...越来越慢了。"希洛克冷笑,"很快,你就会被我的力量完全控制。"</p>
|
||||
<p>她挥手,无形的剑气横扫而出。林克勉强挡下,但被震退了好几步。</p>
|
||||
<p>"林克!"赛丽亚想要帮忙,但被无形的力量挡在外面。</p>
|
||||
<p>"这是我和她之间的战斗。"林克喘着气,"你们...不要过来!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝、敏泰、艾拉站在结界外,焦急地看着林克。</p>
|
||||
<p>"我们帮不了他..."艾丽丝说,"这是精神层面的对抗。"</p>
|
||||
<p>艾拉咬着嘴唇:"林克体内的三股力量...如果他能将它们融合,也许能彻底压制希洛克的力量。"</p>
|
||||
<p>"融合?"艾丽丝看向她,"你的意思是..."</p>
|
||||
<p>"是的。"艾拉说,"天空之泪、灵魂之源、时间之钥,它们都是不同的力量,但本质上都是来自同一个源头——创世之力。"</p>
|
||||
<p>"如果林克能将它们融合,他就能获得创世之力的碎片,那是超越使徒的力量!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>宫殿内,林克的战斗越来越艰难。</p>
|
||||
<p>希洛克的无形化身似乎无穷无尽,无论他怎么攻击,都无法造成致命伤害。而他体内的侵蚀也越来越强,他的意识开始模糊。</p>
|
||||
<p>"放弃吧,林克。"希洛克的声音在他脑海中回荡,"把你的身体交给我,我会给你无尽的力量。"</p>
|
||||
<p>"不..."林克咬紧牙关,"我...不会..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,林克感受到了一股温暖的力量。</p>
|
||||
<p>那是...赛丽亚、艾丽丝、敏泰、艾拉...他的后宫们,正在用她们的方式支持他。</p>
|
||||
<p>赛丽亚的治愈魔法穿过结界,进入他的体内。艾丽丝用灵魂之源的共鸣,增强他的精神。敏泰和艾拉也在外面为他祈祷。</p>
|
||||
<p>"你们..."林克感到心中涌起一股力量。</p>
|
||||
<p>他明白了。</p>
|
||||
<p>他的力量不仅仅来自他自己,还来自那些爱他的人。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我不会输。"</p>
|
||||
<p>林克闭上眼睛,运转体内的三股力量。</p>
|
||||
<p>天空之泪的金色光芒、灵魂之源的紫色光芒、时间之钥的银色光芒...三股力量开始融合。</p>
|
||||
<p>"这是...什么?!"希洛克惊讶,"你在做什么?!"</p>
|
||||
<p>林克睁开眼睛,他的眼睛变成了三种颜色的混合——金、紫、银。</p>
|
||||
<p>"融合。"他说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三股力量在林克体内交汇,产生了一股前所未有的力量。</p>
|
||||
<p>那是创世之力的碎片——超越使徒的力量。</p>
|
||||
<p>林克感到自己的气息暴涨,体内的希洛克力量被瞬间驱逐。</p>
|
||||
<p>"不!不可能!"希洛克惊呼。</p>
|
||||
<p>林克举起细雪之舞,剑上的光芒变成了三色混合的剑气。</p>
|
||||
<p>"极·神剑术(万剑归宗)!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>无数三色剑气从空中落下,全部命中希洛克的无形化身。</p>
|
||||
<p>希洛克发出痛苦的吼叫,她的无形化身开始崩解。</p>
|
||||
<p>"你...你怎么可能拥有创世之力?!"她难以置信地看着林克,"那是不可能被凡人获得的!"</p>
|
||||
<p>林克没有回答,继续挥剑。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>连续的剑光将希洛克完全覆盖,每一剑都带着创世之力的碎片,净化着她的无形之力。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>希洛克的无形化身终于完全崩解,她的本体显露出来。</p>
|
||||
<p>那是一个美丽的女人,紫色的长发,但眼神中满是怨恨。</p>
|
||||
<p>"你以为...这样就能打败我?"她喘着气,"我是不死不灭的存在!"</p>
|
||||
<p>林克看向她:"你是不死不灭吗?还是...只是不愿面对死亡?"</p>
|
||||
<p>他举起光之结晶,虽然被污染,但他用创世之力净化了它。</p>
|
||||
<p>"光之结晶...净化!"</p>
|
||||
<p>金色的光芒从光之结晶中爆发,笼罩了希洛克。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"不!不要!"希洛克发出最后的吼叫。</p>
|
||||
<p>光之结晶的力量封印了她的无形之力,让她重新变成了实体。</p>
|
||||
<p>"你...你赢了..."</p>
|
||||
<p>她的身体开始消散,化作无数光点。</p>
|
||||
<p>"林克...记住...使徒的恩怨...不会结束..."</p>
|
||||
<p>她的身影完全消失了,只留下最后的声音。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗结束了。</p>
|
||||
<p>林克跪倒在地,体内的创世之力碎片消散,他恢复了正常。</p>
|
||||
<p>"林克!"赛丽亚冲过来扶住他。</p>
|
||||
<p>艾丽丝、敏泰、艾拉也跑过来,围在他身边。</p>
|
||||
<p>"你没事吧?"敏泰担心地问。</p>
|
||||
<p>林克虚弱地笑了笑:"我没事...希洛克...被封印了。"</p>
|
||||
<p>艾拉看着他:"你刚才...融合了三股力量。那是创世之力的碎片。"</p>
|
||||
<p>林克点头:"我感受到了...那股力量非常强大,但我也只能维持很短的时间。"</p>
|
||||
<p>艾丽丝说:"即使是这样,你也做到了前人无法做到的事。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷带着天空族的战士们赶过来。</p>
|
||||
<p>"希洛克被击败了?"他问。</p>
|
||||
<p>"是的。"林克站起身,"她被封印了。"</p>
|
||||
<p>普雷看向林克,眼中露出欣慰:"你做到了,年轻人。你不仅保护了泰波尔斯,也保护了整个世界。"</p>
|
||||
<p>林克摇头:"我只是做了我该做的事。"</p>
|
||||
<p>他看向众人:"谢谢大家的支持。如果没有你们,我无法战胜希洛克。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>普雷伸出手,一颗金色的光芒出现在他手中。</p>
|
||||
<p>"这是泰波尔斯的祝福。"他说,"作为感谢,我将这份力量赐予你。它将帮助你更好地控制体内的三股力量。"</p>
|
||||
<p>金色的光芒进入林克体内,他感到三股力量变得更加稳定。</p>
|
||||
<p>"谢谢普雷大人。"</p>
|
||||
<p>普雷点头:"去吧,回到你的世界。泰波尔斯会永远记住你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克等人离开了泰波尔斯,通过天空裂缝返回阿拉德大陆。</p>
|
||||
<p>当他们再次踏上熟悉的土地时,所有人都松了口气。</p>
|
||||
<p>"终于回来了..."敏泰说。</p>
|
||||
<p>艾拉展开翅膀,感受着阿拉德大陆的气息:"这里...和泰波尔斯完全不同。"</p>
|
||||
<p>林克看向远方:"走吧,回赛丽亚旅馆。其他人在等我们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>回到旅馆,帕丽丝、希尔薇、尼梅尔等人立刻围了上来。</p>
|
||||
<p>"林克!你们回来了!"帕丽丝说,"希洛克呢?"</p>
|
||||
<p>"被封印了。"林克回答,"她的威胁暂时解除了。"</p>
|
||||
<p>所有人欢呼起来。</p>
|
||||
<p>赛丽亚站在林克身边,握着他的手:"欢迎回家,林克。"</p>
|
||||
<p>林克微笑:"我回来了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>当晚,赛丽亚旅馆举行了盛大的庆祝宴会。</p>
|
||||
<p>十七位后宫围坐在林克身边,大家欢声笑语,庆祝这次胜利。</p>
|
||||
<p>林克看着她们,心中充满了感激和爱意。</p>
|
||||
<p>"谢谢你们...一直陪着我。"</p>
|
||||
<p>赛丽亚靠在他肩上:"我们会一直陪着你的,林克。"</p>
|
||||
<p>艾丽丝举起酒杯:"为了林克,为了我们的未来。"</p>
|
||||
<p>所有人举起酒杯:"为了未来!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>宴会结束后,林克独自站在阳台上,看着星空。</p>
|
||||
<p>希洛克被封印了,但使徒的恩怨没有结束。米歇尔曾经说过,使徒们互相残杀,这是命运。</p>
|
||||
<p>"也许...这就是阿拉德的命运。"</p>
|
||||
<p>艾丽丝走过来,站在他身边:"在想什么?"</p>
|
||||
<p>"在想...接下来会发生什么。"林克说,"希洛克说使徒的恩怨不会结束。"</p>
|
||||
<p>艾丽丝沉默了片刻:"也许不会结束。但只要我们在一起,就能面对一切。"</p>
|
||||
<p>林克转头看着她:"你说得对。"</p>
|
||||
<p>他将她拥入怀中:"不管未来如何,我都会保护你们。"</p>
|
||||
<p>艾丽丝靠在他胸口:"我们也会保护你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>第二天,林克收到了莎莎的信。</p>
|
||||
<p>"林克:</p>
|
||||
<p>恭喜你封印了希洛克。</p>
|
||||
<p>但我要告诉你一个消息——在我研究赫尔德的遗物时,发现了一些奇怪的记录。</p>
|
||||
<p>赫尔德的'创新世纪'计划,似乎还隐藏着更深的秘密。她为什么要重造世界?使徒们为什么互相残杀?</p>
|
||||
<p>我觉得...这一切背后,有一个更大的阴谋。</p>
|
||||
<p>等你准备好了,来中央公园找我。我有一些东西要给你看。</p>
|
||||
<p>——莎莎"</p>
|
||||
<p>林克放下信,眼神变得凝重。</p>
|
||||
<p>"更大的阴谋..."</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十三章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(希洛克篇 完)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-162.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-164.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-133.html" class="sidebar-chapter ">第133章:尼梅尔的心意</a>
|
||||
<a href="chapter-134.html" class="sidebar-chapter ">第134章:中央公园</a>
|
||||
<a href="chapter-135.html" class="sidebar-chapter ">第135章:剑圣的试炼</a>
|
||||
<a href="chapter-136.html" class="sidebar-chapter ">第136章:地轨中心</a>
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter current">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(163)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@ -1,978 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>黑色大地入口 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 167</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>西北方向,阿拉德大陆的边境地带。</p>
|
||||
<p>这里的景色逐渐变得荒凉。枯黄的草地、干涸的河床、被风蚀的岩石...一切都在诉说着这片土地的贫瘠。</p>
|
||||
<p>"就是这里吗?"敏泰问。</p>
|
||||
<p>林克拿出圣者之十字,十字架散发出微弱的光芒,指向远处的一个峡谷。</p>
|
||||
<p>"在那边。"</p>
|
||||
<p>四人向峡谷走去。</p>
|
||||
<p>越靠近峡谷,空气就越发压抑。天空中的云层变得灰暗,阳光被遮蔽,整个世界仿佛都失去了色彩。</p>
|
||||
<p>"我感觉到了..."艾拉展开翅膀,感知着周围的能量,"那里有很强的黑暗力量。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他们来到峡谷入口,看到前方的空间中有一道紫色的裂缝。</p>
|
||||
<p>那就是次元裂缝。</p>
|
||||
<p>裂缝周围,空气扭曲着,仿佛有什么东西想要从里面冲出来。偶尔,黑暗的雾气从裂缝中涌出,让周围的温度骤降。</p>
|
||||
<p>"这就是通往黑色大地的入口。"艾丽丝说,"被封印了数百年的异次元空间。"</p>
|
||||
<p>林克握紧圣者之十字,感受着从中传来的神圣力量。</p>
|
||||
<p>那股力量与他体内的创世之力产生共鸣,让他感到一丝温暖。</p>
|
||||
<p>"准备好了吗?"他问。</p>
|
||||
<p>艾丽丝点头:"随时。"</p>
|
||||
<p>敏泰握紧法杖:"我已经做好准备了。"</p>
|
||||
<p>艾拉展开翅膀:"让我们走吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克举起圣者之十字,十字架发出金色的光芒,与裂缝中的黑暗力量形成对抗。</p>
|
||||
<p>"开!"</p>
|
||||
<p>光芒扩大,将裂缝撑开。</p>
|
||||
<p>一股寒冷的气息从裂缝中涌出,让人打了个寒颤。</p>
|
||||
<p>林克第一个踏入裂缝,艾丽丝、敏泰和艾拉紧随其后。</p>
|
||||
<p>穿过裂缝的瞬间,林克感到一阵天旋地转。</p>
|
||||
<p>仿佛整个世界都在旋转,然后又突然停止。</p>
|
||||
<p>等视野恢复时,他发现自己站在一片完全不同的世界中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>天空是暗紫色的,没有太阳,只有微弱的光芒从地平线透出。</p>
|
||||
<p>地面是焦黑的岩石,裂缝中流淌着紫色的岩浆,散发着令人窒息的热气和硫磺味。</p>
|
||||
<p>空气中弥漫着硫磺和腐败的气息,让人想要作呕。</p>
|
||||
<p>"这里就是...黑色大地。"艾丽丝喃喃道。</p>
|
||||
<p>敏泰捂住鼻子:"好难闻的味道!像是腐烂的东西。"</p>
|
||||
<p>艾拉飞到半空中,观察着周围:"我能感觉到...到处都是黑暗的力量。它们在空气中流动,在地面下涌动。"</p>
|
||||
<p>林克拿出圣者之十字,十字架的光芒照亮了周围。</p>
|
||||
<p>"走吧。"他说,"我们要找到奥兹玛。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他们在黑色大地中行走,周围是一片荒凉。</p>
|
||||
<p>焦黑的岩石上刻满了奇怪的符文,紫色的雾气从地缝中升起,如同幽灵的触手。</p>
|
||||
<p>偶尔,他们能看到一些身影在远处游荡。</p>
|
||||
<p>那些身影形状各异,有的像人类,有的像野兽,但都有一个共同点——周身散发着黑暗的气息。</p>
|
||||
<p>"那些是伪装者吗?"敏泰问。</p>
|
||||
<p>"是的。"艾丽丝说,"被血之诅咒感染的人类,变成了恶魔。"</p>
|
||||
<p>林克看着那些身影,心中涌起一股悲伤。</p>
|
||||
<p>他们曾经也是普通人,有家人、有朋友、有生活...</p>
|
||||
<p>但现在,他们只是奥兹玛力量的傀儡。</p>
|
||||
<p>"我们要战斗吗?"艾拉问。</p>
|
||||
<p>林克摇头:"我们的目标是奥兹玛。尽量避开战斗,节省体力。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约十分钟,林克停下了脚步。</p>
|
||||
<p>"怎么了?"艾丽丝问。</p>
|
||||
<p>林克指向前方:"有人来了。"</p>
|
||||
<p>众人看去,只见几个身影正从远处的雾气中走出来。</p>
|
||||
<p>他们的动作僵硬,眼神空洞,周身散发着淡淡的紫色光芒。</p>
|
||||
<p>是伪装者。</p>
|
||||
<p>而且不止一个。</p>
|
||||
<p>"有五六个。"敏泰说。</p>
|
||||
<p>"准备战斗。"林克拔出光剑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>伪装者们发现了他们,发出低沉的嘶吼声,冲了过来。</p>
|
||||
<p>他们的速度比普通人快得多,动作虽然僵硬,却充满了攻击性。</p>
|
||||
<p>林克挥剑,一道剑气将最前面的伪装者斩飞。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑亮起蓝白色的光芒,林克冲入敌群。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>他进入流心状态,剑术变得更加流畅。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>艾丽丝举起法杖,施展魔法:"灵魂冲击!"</p>
|
||||
<p>紫色的光束从法杖中射出,击中一个伪装者,让它动作一滞。</p>
|
||||
<p>敏泰也加入了战斗,用班图族的冰系魔法牵制敌人:"冰霜陷阱!"</p>
|
||||
<p>冰霜在地面蔓延,让几个伪装者的脚步变慢。</p>
|
||||
<p>艾拉从空中攻击,用天空族的闪电之力击倒敌人:"雷霆一击!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗很快结束了。</p>
|
||||
<p>六个伪装者倒在地下,黑暗的力量从他们身上散去。</p>
|
||||
<p>林克走到一个伪装者身边,看到他的面容逐渐恢复了人类的样子。</p>
|
||||
<p>是一个中年男性,穿着破旧的皮甲,手里还握着一把生锈的剑。</p>
|
||||
<p>"他...他曾经是冒险家吗?"敏泰惊讶地问。</p>
|
||||
<p>"可能。"艾丽丝说,"很多冒险家都曾试图探索黑色大地,但很少有人能活着离开。"</p>
|
||||
<p>林克握紧圣者之十字。</p>
|
||||
<p>每一个伪装者背后,都有一个被毁灭的人生。</p>
|
||||
<p>奥兹玛的诅咒...太残酷了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"我们能救他们吗?"艾拉问。</p>
|
||||
<p>林克点头:"如果我能打败奥兹玛,也许诅咒就会解除。"</p>
|
||||
<p>他看向远方,那里还有更多的身影在游荡。</p>
|
||||
<p>"走吧,继续前进。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>继续深入,他们遇到了更多的伪装者。</p>
|
||||
<p>有的伪装者保留了人类的形态,只是眼神空洞、动作僵硬。</p>
|
||||
<p>有的伪装者已经完全变形,变成了怪物般的模样,长着尖利的爪子和扭曲的四肢。</p>
|
||||
<p>每一次战斗,林克都会用圣者之十字净化他们。</p>
|
||||
<p>净化后的伪装者会恢复人类的面容,然后静静地躺在地下。</p>
|
||||
<p>他们无法复活,但至少...他们解脱了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"林克。"艾丽丝走到他身边,"你还好吗?"</p>
|
||||
<p>"我没事。"林克说,"只是在想...如果我能早点来,也许能救更多人。"</p>
|
||||
<p>艾丽丝握住他的手:"你已经做得很好了。"</p>
|
||||
<p>林克看着她,露出微笑:"谢谢你,艾丽丝。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约一个小时,周围的景色开始变化。</p>
|
||||
<p>焦黑的岩石变成了更加扭曲的形态——有的像伸向天空的手臂,有的像扭曲的面孔,有的像被凝固的尖啸。</p>
|
||||
<p>紫色的雾气也变得更加浓重,能见度越来越低。</p>
|
||||
<p>"我们深入了。"艾拉说,"黑暗力量越来越强。"</p>
|
||||
<p>林克点头:"说明我们接近核心区域了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,前方出现了一个巨大的身影。</p>
|
||||
<p>那是一个穿着黑色铠甲的骑士,手持巨剑,挡在道路中央。</p>
|
||||
<p>他周身散发着强大的黑暗气息,远超之前遇到的伪装者。</p>
|
||||
<p>"那是..."敏泰瞪大了眼睛。</p>
|
||||
<p>"暗黑骑士。"艾丽丝说,"奥兹玛的护卫。"</p>
|
||||
<p>林克握紧光剑:"看来真正的挑战开始了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>骑士举起巨剑,指向林克等人。</p>
|
||||
<p>"外来者...你们不应该来这里。"</p>
|
||||
<p>他的声音低沉而沙哑,带着无尽的冷漠。</p>
|
||||
<p>林克上前一步:"我是林克。我要见奥兹玛。"</p>
|
||||
<p>"奥兹玛大人不是你们能见的。"骑士说,"回去,或者...死。"</p>
|
||||
<p>"我没有退路。"林克说,"让开。"</p>
|
||||
<p>骑士发出一声冷笑:"那就...死吧。"</p>
|
||||
<p>他挥动巨剑,向林克斩来。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十七章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(奥兹玛篇·第四章)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-166.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-168.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-137.html" class="sidebar-chapter ">第137章:魔剑士阿斯兰</a>
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter current">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(167)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,979 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>焦黑之地深入 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 168</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>骑士的巨剑带着毁灭性的力量斩下,林克用光剑格挡。</p>
|
||||
<p>当!</p>
|
||||
<p>两把武器碰撞,爆发出刺目的火花。</p>
|
||||
<p>林克感到手臂一阵发麻,这个骑士的力量比他想象的还要强。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>光剑亮起更强的光芒,林克开始反击。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他跃向空中,然后俯冲向骑士。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>光剑刺向骑士的铠甲,却被弹开了。</p>
|
||||
<p>"你的攻击太弱了。"骑士冷笑。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克后退几步,重新评估对手。</p>
|
||||
<p>这个骑士的防御力极强,普通攻击根本无法破防。</p>
|
||||
<p>"极·神剑术!"</p>
|
||||
<p>二十四把光剑在空中形成剑阵,向骑士飞去。</p>
|
||||
<p>骑士挥动巨剑,将大部分剑影击散,但还有几把剑穿透了他的防御,在他身上留下伤口。</p>
|
||||
<p>"呃...!"</p>
|
||||
<p>黑暗的力量从伤口中涌出,但很快又恢复了。</p>
|
||||
<p>"黑暗的力量会不断修复我的身体。"骑士说,"你不可能打败我。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧圣者之十字。</p>
|
||||
<p>"那就试试这个。"</p>
|
||||
<p>他举起十字架,金色的光芒扩散开来。</p>
|
||||
<p>"神圣审判!"</p>
|
||||
<p>一道光柱从天而降,笼罩了骑士。</p>
|
||||
<p>骑士发出痛苦的嘶吼,神圣的光芒克制着黑暗的力量。</p>
|
||||
<p>"这...这是什么力量?!"</p>
|
||||
<p>"圣者之十字。"林克说,"克制黑暗的神器。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>趁着骑士被神圣光芒压制的时机,林克发动了终结技。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p>他化为一道剑光,连续斩向骑士。每一次斩击都带着神圣的力量,削弱着骑士的防御。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>无数剑影在空中飞舞,覆盖了骑士全身。</p>
|
||||
<p>终于,骑士跪倒在地,巨剑脱手。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你...你是谁?"骑士艰难地问。</p>
|
||||
<p>"我是林克。"林克说,"我要去见奥兹玛。"</p>
|
||||
<p>骑士沉默了片刻,然后发出一声叹息:"你赢了。"</p>
|
||||
<p>他缓缓站起来,收起武器:"继续前进吧。但在前面...还有更强的敌人在等待。"</p>
|
||||
<p>说完,他让开了道路。</p>
|
||||
<p>林克看了他一眼,带着艾丽丝、敏泰和艾拉继续前进。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>穿过第一个骑士的防线,他们继续向黑色大地深处前进。</p>
|
||||
<p>周围的景色变得越来越扭曲。焦黑的岩石形成了诡异的形状——有的像伸向天空的手臂,有的像扭曲的面孔,有的像被凝固的尖啸。</p>
|
||||
<p>紫色的雾气也变得更加浓重,能见度越来越低。</p>
|
||||
<p>"这里的黑暗力量越来越强了。"艾拉说,"我能感觉到...有什么东西在前方等待。"</p>
|
||||
<p>林克拿出圣者之十字,十字架的光芒照亮了周围。</p>
|
||||
<p>"保持警惕。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他们沿着一条狭窄的道路前进,两侧是深不见底的裂谷。</p>
|
||||
<p>裂谷中流淌着紫色的岩浆,散发着令人窒息的热气和硫磺味。</p>
|
||||
<p>"这些裂谷...好像在呼吸。"敏泰惊讶地说。</p>
|
||||
<p>确实,裂谷中的岩浆在缓慢地起伏,仿佛整个大地都是活的。</p>
|
||||
<p>艾丽丝皱眉:"黑色大地是一个活着的异次元空间。奥兹玛的力量渗透在每一寸土地中。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约十分钟,前方出现了一片废墟。</p>
|
||||
<p>那是某种古老的建筑遗迹,已经完全被黑暗侵蚀。断壁残垣之间,隐约可以看到一些雕像的碎片。</p>
|
||||
<p>"这里曾经是...什么?"敏泰问。</p>
|
||||
<p>林克走近一块残破的石碑,上面的文字已经模糊不清。</p>
|
||||
<p>"可能是某个被奥兹玛毁灭的文明。"艾丽丝说,"在暗黑圣战之前,黑色大地也是有人居住的。"</p>
|
||||
<p>"但后来...奥兹玛的力量吞噬了一切。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他们穿过废墟,看到了一些奇怪的景象。</p>
|
||||
<p>有一些被黑暗侵蚀的雕像,保持着恐惧的表情。</p>
|
||||
<p>有一些残留的生活用品,说明这里曾经有人类生活。</p>
|
||||
<p>"好悲伤..."艾拉轻声说,"这些人...都在一瞬间被毁灭了。"</p>
|
||||
<p>林克握紧拳头。</p>
|
||||
<p>奥兹玛的诅咒,夺走了太多无辜的生命。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,前方的雾气中传来一阵低沉的嘶吼声。</p>
|
||||
<p>"有敌人!"艾丽丝警觉地说。</p>
|
||||
<p>林克看向雾气深处,看到了几个身影正在靠近。</p>
|
||||
<p>那些身影佝偻着身体,动作僵硬,周身散发着淡淡的紫色光芒。</p>
|
||||
<p>是伪装者。</p>
|
||||
<p>"这次数量更多。"林克说,"至少有十个。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>敏泰握紧法杖:"我们要战斗吗?"</p>
|
||||
<p>"没有其他路。"林克拔出光剑。</p>
|
||||
<p>伪装者们发现了他们,发出嘶吼声,冲了过来。</p>
|
||||
<p>"破极兵刃!"</p>
|
||||
<p>林克冲入敌群,光剑在他手中舞动,每一剑都带着神圣的力量。</p>
|
||||
<p>艾丽丝、敏泰和艾拉也加入了战斗。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗持续了大约十分钟。</p>
|
||||
<p>十个伪装者全部倒下,黑暗的力量从他们身上散去。</p>
|
||||
<p>林克走到一个伪装者身边,用圣者之十字净化他。</p>
|
||||
<p>那是一个年轻女性,穿着破旧的衣裙,面容恢复后带着恐惧的表情。</p>
|
||||
<p>"她可能是在逃跑的时候被感染的。"艾丽丝说。</p>
|
||||
<p>林克叹了口气。</p>
|
||||
<p>每一个伪装者,都是一场悲剧。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>继续前进,他们遇到了更多的敌人。</p>
|
||||
<p>有的是伪装者,保持着人类的形态但失去了理智。</p>
|
||||
<p>有的是变异生物,被黑暗力量彻底扭曲,变成了怪物。</p>
|
||||
<p>每一次战斗,林克都会用圣者之十字净化他们。</p>
|
||||
<p>他不想让他们继续在这种状态中挣扎。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>走了大约两个小时,周围的景色再次变化。</p>
|
||||
<p>焦黑的岩石变成了黑色的晶体,从地下生长出来,形成了一片黑色森林。</p>
|
||||
<p>这些晶体闪烁着诡异的光芒,仿佛在注视着闯入者。</p>
|
||||
<p>"黑暗结晶。"艾丽丝说,"奥兹玛力量的凝聚。"</p>
|
||||
<p>林克看向那些晶体,感受到了其中蕴含的恐怖力量。</p>
|
||||
<p>"我们接近核心区域了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,三个身影从黑暗中走出,挡在他们面前。</p>
|
||||
<p>三个穿着黑色铠甲的骑士,手持各自的武器,周身散发着强大的黑暗气息。</p>
|
||||
<p>"绝望之泰玛特。"手持镰刀的骑士说。</p>
|
||||
<p>"毁灭之贝利亚斯。"手持巨剑的骑士说。</p>
|
||||
<p>"恐怖之阿斯特罗斯。"手持双刀的骑士说。</p>
|
||||
<p>"我们是暗黑骑士团,奥兹玛大人的护卫。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧光剑:"让开。"</p>
|
||||
<p>泰玛特发出一声冷笑:"外来者,你们走得太远了。"</p>
|
||||
<p>贝利亚斯举起巨剑:"回去,或者死。"</p>
|
||||
<p>阿斯特罗斯的双刀闪烁着寒光:"我更希望你们选择死。"</p>
|
||||
<p>林克没有退缩,举起圣者之十字:"我没有退路。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三个骑士同时发动攻击。</p>
|
||||
<p>泰玛特的镰刀带着绝望的气息斩来。</p>
|
||||
<p>贝利亚斯的巨剑劈向林克的头顶。</p>
|
||||
<p>阿斯特罗斯化为一道残影,从背后偷袭。</p>
|
||||
<p>战斗,开始了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十八章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(奥兹玛篇·第五章)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-167.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-169.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-138.html" class="sidebar-chapter ">第138章:泪目之眼</a>
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter current">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(168)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@ -1,981 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>暗黑骑士团 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 169</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>三个骑士同时发动攻击,空气中充满了压抑的气息。</p>
|
||||
<p>泰玛特的镰刀带着绝望的气息斩来,那股力量仿佛能吞噬一切希望。</p>
|
||||
<p>贝利亚斯的巨剑劈向林克的头顶,力量足以粉碎岩石,让大地颤抖。</p>
|
||||
<p>阿斯特罗斯化为一道残影,绕到林克背后,双刀闪烁着寒光,直取他的要害。</p>
|
||||
<p>三面夹击,无处可逃。</p>
|
||||
<p>但林克没有后退,而是迎向攻击。</p>
|
||||
<p>"猛龙断空斩!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>他化为一道剑光,连续闪避三人的攻击,然后出现在他们身后。</p>
|
||||
<p>"拔刀斩!"</p>
|
||||
<p>一道巨大的剑气斩出,击中贝利亚斯的铠甲。</p>
|
||||
<p>当!</p>
|
||||
<p>剑气被弹开,贝利亚斯的铠甲完好无损,连一丝划痕都没有留下。</p>
|
||||
<p>"毁灭之铠甲..."林克意识到,"他的防御力极强,普通攻击根本无法破防。"</p>
|
||||
<p>泰玛特趁机发动攻击,镰刀再次挥来,带着吸取生命力的黑暗力量。</p>
|
||||
<p>林克格挡,但镰刀上的黑暗力量让他感到一阵虚弱,仿佛生命力在流逝。</p>
|
||||
<p>"绝望之镰...会吸取生命力。"泰玛特冷冷地说,"你会越来越虚弱,直到死亡。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克咬紧牙关,调动体内的创世之力碎片。</p>
|
||||
<p>金色的光芒从体内涌出,驱散了黑暗的力量,让他重新恢复了力量。</p>
|
||||
<p>"创世之力?"泰玛特惊讶地说,"你竟然拥有这种力量?"</p>
|
||||
<p>贝利亚斯举起巨剑,再次发动攻击:"那就更要杀掉你!"</p>
|
||||
<p>他的巨剑带着毁灭性的力量,仿佛能劈开天地。</p>
|
||||
<p>林克侧身闪避,但剑风还是擦过他的身体,在他手臂上留下一道伤口。</p>
|
||||
<p>"好强的力量!"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>阿斯特罗斯趁机从侧面攻击,双刀连续斩击,速度快得让人眼花缭乱。</p>
|
||||
<p>林克被迫防守,但她的攻击速度太快,他只能勉强招架。</p>
|
||||
<p>"流心!"</p>
|
||||
<p>林克进入流心状态,剑术变得更加流畅,终于能够跟上阿斯特罗斯的速度。</p>
|
||||
<p>"流心:跃!"</p>
|
||||
<p>他跃向空中,避开了她的攻击。</p>
|
||||
<p>"流心:刺!"</p>
|
||||
<p>他俯冲向阿斯特罗斯,光剑贯穿了她的肩膀。</p>
|
||||
<p>"呃!"</p>
|
||||
<p>阿斯特罗斯后退,捂住伤口。黑暗的力量开始从伤口中涌出,修复着她的身体。</p>
|
||||
<p>"你的速度...很快。"她说,"但还不够。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克看着三人,眉头紧锁。</p>
|
||||
<p>三个骑士的力量都很强,而且他们可以互相配合,形成完美的攻防体系。</p>
|
||||
<p>泰玛特的镰刀可以吸取生命力,让人虚弱。</p>
|
||||
<p>贝利亚斯的铠甲坚不可摧,普通攻击无法破防。</p>
|
||||
<p>阿斯特罗斯的速度极快,难以捕捉。</p>
|
||||
<p>如果这样下去,他会被消耗殆尽。</p>
|
||||
<p>"必须一个个击败。"林克心想。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"艾丽丝!"林克喊道,"帮我牵制他们!"</p>
|
||||
<p>"收到!"艾丽丝举起法杖,开始施展魔法。</p>
|
||||
<p>"灵魂风暴!"</p>
|
||||
<p>紫色的能量风暴在三个骑士之间卷起,将他们吹散。</p>
|
||||
<p>敏泰也加入了战斗,施放冰系魔法:"冰霜陷阱!"</p>
|
||||
<p>冰霜在地面蔓延,让三个骑士的脚步变慢。</p>
|
||||
<p>艾拉从空中发射闪电:"雷霆一击!"</p>
|
||||
<p>闪电击中贝利亚斯,让他动作一滞。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克抓住了机会。</p>
|
||||
<p>"极·神剑术!"</p>
|
||||
<p>二十四把光剑在周围形成剑阵,向三个骑士飞去。</p>
|
||||
<p>泰玛特挥动镰刀,将大部分剑影击散,但还有几把剑穿透了他的防御。</p>
|
||||
<p>贝利亚斯用巨剑格挡,剑阵在他身上留下几道伤口,黑暗的力量从伤口中涌出。</p>
|
||||
<p>阿斯特罗斯化为一道残影,躲避了大部分攻击,但还是有几把剑擦过她的身体。</p>
|
||||
<p>"他们...受伤了!"敏泰惊喜地说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克没有停下,继续发动攻击。</p>
|
||||
<p>"幻影剑舞!"</p>
|
||||
<p>无数剑影在空中飞舞,覆盖了三个骑士。</p>
|
||||
<p>他们被迫防守,无法组织有效的反击。</p>
|
||||
<p>林克的身影在剑影中穿梭,每一次斩击都带着神圣的力量,削弱着他们的防御。</p>
|
||||
<p>"神圣的力量...克制黑暗!"艾丽丝说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>战斗持续了将近一个小时。</p>
|
||||
<p>林克的身上增加了很多伤口,但他没有放弃。</p>
|
||||
<p>创世之力的碎片在他体内涌动,让他的力量源源不断。</p>
|
||||
<p>终于,三个骑士的力量开始减弱。</p>
|
||||
<p>他们的动作变慢了,攻击也不再那么凌厉。</p>
|
||||
<p>林克抓住了机会。</p>
|
||||
<p>"万剑归宗!"</p>
|
||||
<p>他发动了二觉终极技,无数剑气从天而降,覆盖了整个战场。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>三个骑士被迫分散防御,但剑气太密集,他们无法全部挡住。</p>
|
||||
<p>泰玛特的镰刀被击飞,他的身体上多了几道伤口,黑暗的力量从伤口中涌出。</p>
|
||||
<p>贝利亚斯的铠甲被击碎了一部分,露出了里面的黑色身躯。</p>
|
||||
<p>阿斯特罗斯的双刀脱手,她跪倒在地,气息微弱。</p>
|
||||
<p>"你...真的很强。"泰玛特喘息着说,"比我预想的还要强。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克收起光剑,看着三人。</p>
|
||||
<p>"我不杀你们。"他说,"让开。"</p>
|
||||
<p>泰玛特抬头看着他,眼中闪过复杂的情绪。</p>
|
||||
<p>"你赢了。"他说,"也许...你真的能见到奥兹玛大人。"</p>
|
||||
<p>他挥手,一道黑暗屏障消失了,露出通往深处的道路。</p>
|
||||
<p>"去吧。"贝利亚斯低声说,"奥兹玛大人在最深处等待。"</p>
|
||||
<p>阿斯特罗斯没有说话,只是默默地看着林克通过。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克点头,带着艾丽丝、敏泰和艾拉继续前进。</p>
|
||||
<p>艾丽丝走到他身边:"你为什么不杀他们?"</p>
|
||||
<p>"他们只是奥兹玛的护卫。"林克说,"而且...我能感受到他们内心的挣扎。"</p>
|
||||
<p>"他们被黑暗力量束缚,无法自拔。"</p>
|
||||
<p>艾丽丝点头:"你说得对。他们曾经也是战士,只是被奥兹玛的力量侵蚀了。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>身后的三个骑士依然跪在地下,目送他们离去。</p>
|
||||
<p>泰玛特看着林克的背影,喃喃道:"创世之力...也许他真的能拯救奥兹玛大人。"</p>
|
||||
<p>贝利亚斯叹了口气:"我们守护了这么多年,也许...就是等待这一天。"</p>
|
||||
<p>阿斯特罗斯的双刀重新出现在手中,但她没有追击。</p>
|
||||
<p>"希望他能成功。"她说,"如果奥兹玛大人能获得解脱...我们的使命也完成了。"</p>
|
||||
<p>泰玛特点头:"是啊。我们守护了数百年,等待的就是这个人。"</p>
|
||||
<p>贝利亚斯看着林克消失的方向:"走吧,我们也该休息了。"</p>
|
||||
<p>三人缓缓站起身,身影逐渐消失在黑暗中。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>穿过骑士团的防线后,周围的黑暗变得更加浓重。</p>
|
||||
<p>林克感受着周围的气息,那是比之前更强的黑暗力量。</p>
|
||||
<p>"我们接近核心了。"艾拉说,"我能感觉到...前方有强大的存在。"</p>
|
||||
<p>敏泰握紧法杖:"那就是奥兹玛吗?"</p>
|
||||
<p>林克点头:"是的。"</p>
|
||||
<p>他握紧圣者之十字,感受着从中传来的神圣力量。</p>
|
||||
<p>那股力量让他感到安心,也让他更加坚定。</p>
|
||||
<p>"走吧。"他说,"结束这一切。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>远处的黑暗中,一个巨大的身影正静静地等待。</p>
|
||||
<p>那个身影坐在由黑暗凝聚而成的王座上,周身被混沌的力量包裹。</p>
|
||||
<p>林克握紧圣者之十字,向前走去。</p>
|
||||
<p>那就是...奥兹玛。</p>
|
||||
<p>第十一使徒,混沌之神。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"你终于来了。"</p>
|
||||
<p>奥兹玛的声音低沉而沙哑,带着无尽的悲伤。</p>
|
||||
<p>林克停下脚步,看着那个巨大的身影。</p>
|
||||
<p>"我是林克。"他说,"我来...是为了拯救你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百六十九章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(奥兹玛篇·第六章)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-168.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-170.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-139.html" class="sidebar-chapter ">第139章:使徒会晤</a>
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter current">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter ">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(169)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
@ -1,981 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||
<meta http-equiv="Cache-Control" content="no-cache, no-store, must-revalidate">
|
||||
<meta http-equiv="Pragma" content="no-cache">
|
||||
<meta http-equiv="Expires" content="0">
|
||||
<title>黑暗中的记忆 - 阿拉德:剑之回响</title>
|
||||
<link rel="preconnect" href="https://fonts.googleapis.com">
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
|
||||
<link href="https://fonts.googleapis.com/css2?family=Noto+Serif+SC:wght@400;600;700&family=Noto+Sans+SC:wght@300;400;500;700&display=swap" rel="stylesheet">
|
||||
<style>
|
||||
:root {
|
||||
--bg-primary: linear-gradient(135deg, #0f0c29 0%, #302b63 50%, #24243e 100%);
|
||||
--text-primary: #e0e0e0;
|
||||
--text-secondary: #888;
|
||||
--accent-gradient: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
--border-color: rgba(255,255,255,0.1);
|
||||
--btn-bg: rgba(255,255,255,0.1);
|
||||
--btn-hover: rgba(255,255,255,0.2);
|
||||
}
|
||||
|
||||
[data-theme="light"] {
|
||||
--bg-primary: linear-gradient(135deg, #f5f7fa 0%, #c3cfe2 100%);
|
||||
--text-primary: #333;
|
||||
--text-secondary: #666;
|
||||
--border-color: rgba(0,0,0,0.1);
|
||||
--btn-bg: rgba(0,0,0,0.05);
|
||||
--btn-hover: rgba(0,0,0,0.1);
|
||||
}
|
||||
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: 'Noto Serif SC', serif;
|
||||
background: var(--bg-primary);
|
||||
color: var(--text-primary);
|
||||
line-height: 1.8;
|
||||
min-height: 100vh;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.container {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
padding: 20px;
|
||||
padding-bottom: 120px;
|
||||
}
|
||||
|
||||
/* 顶部导航 */
|
||||
.top-nav {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 10px 20px;
|
||||
}
|
||||
|
||||
.top-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-link {
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.nav-link:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.chapter-header {
|
||||
text-align: center;
|
||||
padding: 80px 0 40px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
margin-bottom: 40px;
|
||||
}
|
||||
|
||||
.chapter-number {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
letter-spacing: 4px;
|
||||
text-transform: uppercase;
|
||||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.chapter-title {
|
||||
font-size: 32px;
|
||||
font-weight: 700;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.chapter-meta {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 18px;
|
||||
line-height: 2;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
.chapter-content p {
|
||||
margin-bottom: 1.5em;
|
||||
text-indent: 2em;
|
||||
}
|
||||
|
||||
.chapter-content p:first-of-type::first-letter {
|
||||
font-size: 3em;
|
||||
float: left;
|
||||
line-height: 1;
|
||||
margin-right: 8px;
|
||||
margin-top: -5px;
|
||||
background: var(--accent-gradient);
|
||||
-webkit-background-clip: text;
|
||||
-webkit-text-fill-color: transparent;
|
||||
background-clip: text;
|
||||
font-weight: 700;
|
||||
}
|
||||
|
||||
/* 固定底部导航 */
|
||||
.fixed-nav {
|
||||
position: fixed;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
background: rgba(0,0,0,0.3);
|
||||
backdrop-filter: blur(10px);
|
||||
border-top: 1px solid var(--border-color);
|
||||
z-index: 1000;
|
||||
padding: 15px 20px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
max-width: 800px;
|
||||
margin: 0 auto;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 12px 24px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
text-decoration: none;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.nav-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: translateY(-2px);
|
||||
}
|
||||
|
||||
.nav-btn.disabled {
|
||||
opacity: 0.3;
|
||||
cursor: not-allowed;
|
||||
pointer-events: none;
|
||||
}
|
||||
|
||||
.nav-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
}
|
||||
|
||||
/* 右侧滚动按钮 */
|
||||
.scroll-buttons {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
bottom: 90px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
gap: 10px;
|
||||
z-index: 1001;
|
||||
}
|
||||
|
||||
.scroll-btn {
|
||||
width: 40px;
|
||||
height: 40px;
|
||||
border-radius: 8px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 16px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.scroll-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
/* TTS弹出面板 */
|
||||
.tts-overlay {
|
||||
position: fixed;
|
||||
top: 0;
|
||||
left: 0;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
background: rgba(0,0,0,0.5);
|
||||
z-index: 2000;
|
||||
display: none;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
}
|
||||
|
||||
.tts-overlay.show {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
background: rgba(30,30,50,0.95);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 16px;
|
||||
border: 1px solid var(--border-color);
|
||||
padding: 24px;
|
||||
width: 90%;
|
||||
max-width: 400px;
|
||||
box-shadow: 0 10px 40px rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .tts-panel {
|
||||
background: rgba(255,255,255,0.95);
|
||||
}
|
||||
|
||||
.tts-header {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
align-items: center;
|
||||
margin-bottom: 20px;
|
||||
padding-bottom: 15px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 18px;
|
||||
font-weight: 600;
|
||||
color: var(--text-primary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-close {
|
||||
width: 32px;
|
||||
height: 32px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 18px;
|
||||
transition: all 0.3s ease;
|
||||
}
|
||||
|
||||
.tts-close:hover {
|
||||
background: var(--btn-hover);
|
||||
}
|
||||
|
||||
.tts-controls {
|
||||
display: flex;
|
||||
justify-content: center;
|
||||
gap: 16px;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 56px;
|
||||
height: 56px;
|
||||
border-radius: 50%;
|
||||
background: var(--btn-bg);
|
||||
border: 2px solid var(--border-color);
|
||||
color: var(--text-primary);
|
||||
cursor: pointer;
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
font-size: 20px;
|
||||
transition: all 0.3s ease;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-btn:hover {
|
||||
background: var(--btn-hover);
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-btn.active {
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
border-color: #667eea;
|
||||
transform: scale(1.1);
|
||||
}
|
||||
|
||||
.tts-progress {
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
|
||||
.tts-progress-bar {
|
||||
height: 6px;
|
||||
background: var(--btn-bg);
|
||||
border-radius: 3px;
|
||||
overflow: hidden;
|
||||
margin-bottom: 8px;
|
||||
}
|
||||
|
||||
.tts-progress-fill {
|
||||
height: 100%;
|
||||
background: linear-gradient(135deg, #667eea 0%, #764ba2 100%);
|
||||
width: 0%;
|
||||
transition: width 0.1s ease;
|
||||
}
|
||||
|
||||
.tts-time {
|
||||
font-size: 13px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
.tts-speed {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
gap: 12px;
|
||||
}
|
||||
|
||||
.tts-speed-label {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
.tts-speed-select {
|
||||
padding: 8px 16px;
|
||||
background: var(--btn-bg);
|
||||
border: 1px solid var(--border-color);
|
||||
border-radius: 8px;
|
||||
color: var(--text-primary);
|
||||
font-size: 14px;
|
||||
cursor: pointer;
|
||||
font-family: 'Noto Sans SC', sans-serif;
|
||||
}
|
||||
|
||||
/* 侧边栏 - 标题固定,内容滚动 */
|
||||
.sidebar {
|
||||
position: fixed;
|
||||
right: 20px;
|
||||
top: 50%;
|
||||
transform: translateY(-50%);
|
||||
background: rgba(0,0,0,0.5);
|
||||
backdrop-filter: blur(10px);
|
||||
border-radius: 12px;
|
||||
border: 1px solid var(--border-color);
|
||||
width: 200px;
|
||||
max-height: 70vh;
|
||||
z-index: 999;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sidebar-title {
|
||||
font-size: 14px;
|
||||
color: var(--text-secondary);
|
||||
text-transform: uppercase;
|
||||
letter-spacing: 2px;
|
||||
padding: 15px 20px;
|
||||
border-bottom: 1px solid var(--border-color);
|
||||
flex-shrink: 0;
|
||||
}
|
||||
|
||||
.sidebar-content {
|
||||
overflow-y: auto;
|
||||
padding: 10px 20px 20px;
|
||||
flex: 1;
|
||||
scrollbar-width: thin;
|
||||
scrollbar-color: transparent transparent;
|
||||
transition: scrollbar-color 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover {
|
||||
scrollbar-color: rgba(255,255,255,0.3) transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar {
|
||||
width: 6px;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar-content::-webkit-scrollbar-thumb {
|
||||
background: transparent;
|
||||
border-radius: 3px;
|
||||
transition: background 0.3s ease;
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.3);
|
||||
}
|
||||
|
||||
.sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(255,255,255,0.5);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover {
|
||||
scrollbar-color: rgba(0,0,0,0.3) transparent;
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb {
|
||||
background: rgba(0,0,0,0.3);
|
||||
}
|
||||
|
||||
[data-theme="light"] .sidebar-content:hover::-webkit-scrollbar-thumb:hover {
|
||||
background: rgba(0,0,0,0.5);
|
||||
}
|
||||
|
||||
.sidebar-chapter {
|
||||
display: block;
|
||||
padding: 8px 0;
|
||||
color: #aaa;
|
||||
text-decoration: none;
|
||||
font-size: 13px;
|
||||
border-bottom: 1px solid rgba(255,255,255,0.05);
|
||||
transition: all 0.3s ease;
|
||||
line-height: 1.5;
|
||||
}
|
||||
|
||||
.sidebar-chapter:hover {
|
||||
color: #667eea;
|
||||
}
|
||||
|
||||
.sidebar-chapter.current {
|
||||
color: #667eea;
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
@media (max-width: 1200px) {
|
||||
.sidebar {
|
||||
display: none;
|
||||
}
|
||||
}
|
||||
|
||||
@media (max-width: 600px) {
|
||||
.chapter-title {
|
||||
font-size: 24px;
|
||||
}
|
||||
|
||||
.chapter-content {
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.fixed-nav-content {
|
||||
gap: 8px;
|
||||
}
|
||||
|
||||
.nav-btn {
|
||||
padding: 10px 12px;
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.scroll-buttons {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.tts-panel {
|
||||
padding: 20px;
|
||||
width: 95%;
|
||||
}
|
||||
|
||||
.tts-btn {
|
||||
width: 48px;
|
||||
height: 48px;
|
||||
font-size: 18px;
|
||||
}
|
||||
|
||||
.tts-title {
|
||||
font-size: 16px;
|
||||
}
|
||||
}
|
||||
|
||||
/* 滚动条样式 */
|
||||
.sidebar::-webkit-scrollbar {
|
||||
width: 4px;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-track {
|
||||
background: transparent;
|
||||
}
|
||||
|
||||
.sidebar::-webkit-scrollbar-thumb {
|
||||
background: rgba(255,255,255,0.2);
|
||||
border-radius: 2px;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
<!-- 顶部导航 -->
|
||||
<nav class="top-nav">
|
||||
<div class="top-nav-content">
|
||||
<a href="../index.html" class="nav-link">返回首页</a>
|
||||
<button class="nav-link" id="themeToggle">切换主题</button>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<div class="container">
|
||||
<header class="chapter-header">
|
||||
<div class="chapter-number">Chapter 170</div>
|
||||
<h1 class="chapter-title">{{CHAPTER_TITLE}}</h1>
|
||||
</header>
|
||||
|
||||
<article class="chapter-content">
|
||||
<p>林克正要走向奥兹玛,周围突然涌起一阵浓重的黑暗。</p>
|
||||
<p>奥兹玛的身影消失在黑暗中,取而代之的是一片模糊的画面。</p>
|
||||
<p>"这是...什么?"敏泰惊讶地问。</p>
|
||||
<p>"记忆幻象。"艾丽丝说,"奥兹玛的力量在向你展示他的过去。"</p>
|
||||
<p>林克看着周围的画面,看到了一个熟悉的场景。</p>
|
||||
<p>那是一座宏伟的城市,城中人来人往,热闹非凡。</p>
|
||||
<p>建筑风格古老而华丽,士兵们穿着闪亮的铠甲巡逻,商人们在街道上叫卖。</p>
|
||||
<p>"那是佩鲁斯帝国的都城。"艾丽丝说,"曾经大陆最繁华的城市之一。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面中,两个身影正在城中行走。</p>
|
||||
<p>一个身材高大,手持巨剑,是一个战士。他的步伐沉稳,眼神锐利,浑身散发着强大的气场。</p>
|
||||
<p>另一个穿着魔法师长袍,银色长发随风飘动,面容俊美。他的周身散发着淡淡的魔力光芒,让人不敢直视。</p>
|
||||
<p>"卡赞...奥兹玛..."林克认出了他们。</p>
|
||||
<p>画面中的奥兹玛脸上带着笑容,正在和卡赞说笑。两人之间的友谊显而易见,那是无需言语的默契。</p>
|
||||
<p>他们是挚友,也是帝国最强的组合。</p>
|
||||
<p>"那时候...他们还不知道即将发生的一切。"艾丽丝轻声说。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面流转。</p>
|
||||
<p>林克看到了帝国皇帝——一个阴险的中年男人,在暗处注视着卡赞和奥兹玛。</p>
|
||||
<p>皇帝的眼神中充满了恐惧和忌惮。</p>
|
||||
<p>"他们的力量太强了..."皇帝喃喃道,"如果不除掉他们,帝国的统治会动摇。"</p>
|
||||
<p>他转向身边的侍从:"按照计划行事。"</p>
|
||||
<p>林克握紧拳头。</p>
|
||||
<p>这就是阴谋的开始。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>下一个画面,林克看到卡赞被诬陷谋反。</p>
|
||||
<p>皇帝在大殿上宣布卡赞叛国的罪名,命令奥兹玛率军镇压。</p>
|
||||
<p>奥兹玛震惊地看着皇帝,不敢相信。</p>
|
||||
<p>"陛下,卡赞大人不可能谋反!我们并肩作战多年,他绝不会背叛帝国!"</p>
|
||||
<p>"这是事实。"皇帝冷冷地说,"证据确凿。去吧,证明你的忠诚。"</p>
|
||||
<p>奥兹玛犹豫了,他看向站在一旁的大臣们,但所有人都低下了头。</p>
|
||||
<p>最终,他点头:"遵命。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面再次流转。</p>
|
||||
<p>林克看到奥兹玛带着军队追赶卡赞。</p>
|
||||
<p>卡赞站在山顶,手持巨剑,眼神中充满困惑和愤怒。</p>
|
||||
<p>"奥兹玛,你真的相信我会谋反吗?"</p>
|
||||
<p>"我不知道。"奥兹玛的声音颤抖,"但皇帝的命令..."</p>
|
||||
<p>"皇帝?"卡赞发出一声冷笑,"你真的那么天真吗?皇帝只是恐惧我们的力量!"</p>
|
||||
<p>"你在说什么?"</p>
|
||||
<p>"想想看,我们两个加起来,整个帝国无人能敌。皇帝怎么能不害怕?"</p>
|
||||
<p>奥兹玛愣住了。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>两人开始战斗。</p>
|
||||
<p>卡赞的巨剑与奥兹玛的魔法碰撞,爆发出刺目的光芒。</p>
|
||||
<p>周围的山石被震碎,大地龟裂。</p>
|
||||
<p>这是两个帝国最强者的对决,也是挚友之间的悲剧。</p>
|
||||
<p>就在他们交战最激烈的时候,帝国军队突然出现,将两人包围。</p>
|
||||
<p>"逮捕他们!"</p>
|
||||
<p>奥兹玛震惊地看着皇帝:"陛下,这是...?"</p>
|
||||
<p>"你们两人的力量太强了。"皇帝冷笑,"帝国容不下你们。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面切换到牢狱中。</p>
|
||||
<p>奥兹玛和卡赞被锁链束缚,身上满是伤痕。</p>
|
||||
<p>皇帝出现在牢门外,脸上带着残忍的笑容。</p>
|
||||
<p>"奥兹玛,告诉你一个消息。"</p>
|
||||
<p>"你的家人,已经被处决了。"</p>
|
||||
<p>"你的恋人莉兹...也被杀了。"</p>
|
||||
<p>奥兹玛瞪大了眼睛,发出撕心裂肺的嘶吼:"不!!为什么?!他们是无辜的!"</p>
|
||||
<p>黑暗的力量从他体内涌出,冲击着牢狱的墙壁。</p>
|
||||
<p>"因为我要让你绝望。"皇帝说,"只有绝望的人,才会接受死神的提议。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一个身影从黑暗中出现。</p>
|
||||
<p>那是一个穿着黑色斗篷的人,看不清面容,只能看到一双闪烁着诡异光芒的眼睛。</p>
|
||||
<p>"我可以给你力量。"那个声音说,"复仇的力量。"</p>
|
||||
<p>奥兹玛抬起头,眼中燃烧着疯狂的火焰:"你是谁?"</p>
|
||||
<p>"我是死神。"那个人说,"我可以让你毁灭一切,让你复仇。"</p>
|
||||
<p>"代价是什么?"</p>
|
||||
<p>"你的灵魂。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克想要喊叫,想要阻止奥兹玛。</p>
|
||||
<p>但这是幻象,他无法干预。</p>
|
||||
<p>他只能看着奥兹玛点头:"好。只要能复仇,我愿意付出一切。"</p>
|
||||
<p>那个身影伸出手,黑暗的力量涌入奥兹玛的体内。</p>
|
||||
<p>奥兹玛的身体开始扭曲变形,银色的长发变成了黑色,俊美的面容变得扭曲。</p>
|
||||
<p>他的眼睛变成了红色,充满了仇恨和疯狂。</p>
|
||||
<p>"从现在开始,你是混沌之神奥兹玛。"那个声音说,"去毁灭这个世界吧。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面再次流转。</p>
|
||||
<p>林克看到了暗黑圣战的场景。</p>
|
||||
<p>奥兹玛散播血之诅咒,无数人变成了伪装者。</p>
|
||||
<p>人与人之间失去了信任,每个人都怀疑身边的人是不是恶魔。</p>
|
||||
<p>世界陷入了黑暗和混乱。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>然后,他看到了米歇尔。</p>
|
||||
<p>年轻的米歇尔手持十字架,带领圣职者们与奥兹玛的军队战斗。</p>
|
||||
<p>他的眼中充满了悲伤,但没有犹豫。</p>
|
||||
<p>"奥兹玛,我必须阻止你。"</p>
|
||||
<p>奥兹玛看着他,眼中闪过一丝挣扎,但很快被疯狂取代:"米歇尔...你也来阻止我吗?"</p>
|
||||
<p>"我不想杀你。"米歇尔说,"但我必须封印你。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面显示了两人的战斗。</p>
|
||||
<p>神圣的力量与混沌的力量碰撞,天地震动。</p>
|
||||
<p>最终,米歇尔将奥兹玛封印在黑色大地。</p>
|
||||
<p>"对不起了,老朋友。"米歇尔说,"我会一直守着你,直到有人能让你解脱。"</p>
|
||||
<p>奥兹玛在封印中渐渐沉睡,但他的眼中依然燃烧着仇恨。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>画面消失了。</p>
|
||||
<p>林克回到现实,浑身冷汗。</p>
|
||||
<p>"林克,你没事吧?"艾丽丝关切地问。</p>
|
||||
<p>"我看到了...奥兹玛的记忆。"林克说,"他被背叛得太惨了。"</p>
|
||||
<p>艾丽丝点头:"这就是为什么米歇尔要让你拯救他。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>就在这时,一道金色的光芒从天而降。</p>
|
||||
<p>米歇尔的分身出现在他们面前。</p>
|
||||
<p>"米歇尔大人?"敏泰惊讶地说。</p>
|
||||
<p>米歇尔看向林克:"你看到了奥兹玛的记忆?"</p>
|
||||
<p>"是的。"林克点头,"他被背叛得太惨了。皇帝利用了他,赫尔德欺骗了他。"</p>
|
||||
<p>米歇尔叹了口气:"是的...那是我一直以来的愧疚。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>"愧疚?"艾拉问。</p>
|
||||
<p>"在帝国陷害他们的时候,我应该站出来。"米歇尔说,"但我选择了沉默。"</p>
|
||||
<p>"那时候我还是教会的圣职者,不想卷入政治斗争。"</p>
|
||||
<p>"如果我早一点站出来,也许...奥兹玛就不会堕落。"</p>
|
||||
<p>林克看着他:"你无法预知未来。"</p>
|
||||
<p>"但我可以做出选择。"米歇尔说,"所以我选择封印他,守护他,直到有人能拯救他。"</p>
|
||||
<p>"那个人就是你,林克。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>林克握紧圣者之十字:"我会尽力。"</p>
|
||||
<p>米歇尔露出欣慰的笑容:"我相信你。"</p>
|
||||
<p>他伸出手,一道金色的光芒笼罩了林克。</p>
|
||||
<p>"这是我最后的祝福。"米歇尔说,"它会帮助你抵抗奥兹玛的精神攻击。"</p>
|
||||
<p>林克感受着体内涌动的神圣力量,点头:"谢谢。"</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p>米歇尔的身影开始消散:"去吧,奥兹玛在等着你。"</p>
|
||||
<p>"拯救他...让他解脱。"</p>
|
||||
<p>林克点头,带着众人继续前进。</p>
|
||||
<p>前方,混沌王座上的奥兹玛正静静地等待。</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0;">···</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(第一百七十章完)</p>
|
||||
<p style="text-align: center; color: var(--text-secondary); text-indent: 0; margin-top: 2em;">(奥兹玛篇·第七章)</p>
|
||||
|
||||
</article>
|
||||
</div>
|
||||
|
||||
<!-- 固定底部导航 -->
|
||||
<nav class="fixed-nav">
|
||||
<div class="fixed-nav-content">
|
||||
<a href="chapter-169.html" class="nav-btn ">上一章</a>
|
||||
<a href="../chapters.html" class="nav-btn">目录</a>
|
||||
<button class="nav-btn" id="ttsToggleBtn">朗读</button>
|
||||
<a href="chapter-171.html" class="nav-btn ">下一章</a>
|
||||
</div>
|
||||
</nav>
|
||||
|
||||
<!-- 右侧滚动按钮 -->
|
||||
<div class="scroll-buttons">
|
||||
<button class="scroll-btn" id="scrollTop" title="回到顶部">顶</button>
|
||||
<button class="scroll-btn" id="scrollBottom" title="回到底部">底</button>
|
||||
</div>
|
||||
|
||||
<!-- TTS弹出面板 -->
|
||||
<div class="tts-overlay" id="ttsOverlay">
|
||||
<div class="tts-panel">
|
||||
<div class="tts-header">
|
||||
<div class="tts-title">🔊 语音朗读</div>
|
||||
<button class="tts-close" id="ttsClose">×</button>
|
||||
</div>
|
||||
<div class="tts-controls">
|
||||
<button class="tts-btn" id="ttsPlay" title="播放">▶</button>
|
||||
<button class="tts-btn" id="ttsPause" title="暂停">⏸</button>
|
||||
<button class="tts-btn" id="ttsStop" title="停止">⏹</button>
|
||||
</div>
|
||||
<div class="tts-progress">
|
||||
<div class="tts-progress-bar">
|
||||
<div class="tts-progress-fill" id="ttsProgressFill"></div>
|
||||
</div>
|
||||
<div class="tts-time" id="ttsTime">0 / 0 句</div>
|
||||
</div>
|
||||
<div class="tts-speed">
|
||||
<span class="tts-speed-label">朗读速度:</span>
|
||||
<select class="tts-speed-select" id="ttsSpeed">
|
||||
<option value="0.5">慢速 (0.5x)</option>
|
||||
<option value="0.75">较慢 (0.75x)</option>
|
||||
<option value="1" selected>正常 (1x)</option>
|
||||
<option value="1.25">较快 (1.25x)</option>
|
||||
<option value="1.5">快速 (1.5x)</option>
|
||||
<option value="2">极速 (2x)</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!-- 侧边栏章节导航 -->
|
||||
<aside class="sidebar">
|
||||
<div class="sidebar-title">章节导航</div>
|
||||
<div class="sidebar-content" id="sidebarContent">
|
||||
<a href="chapter-140.html" class="sidebar-chapter ">第140章:复仇之剑</a>
|
||||
<a href="chapter-141.html" class="sidebar-chapter ">第141章:寂静城再访</a>
|
||||
<a href="chapter-142.html" class="sidebar-chapter ">第142章:时间之钥</a>
|
||||
<a href="chapter-143.html" class="sidebar-chapter ">第143章:翡翠梦魇</a>
|
||||
<a href="chapter-144.html" class="sidebar-chapter ">第144章:诅咒的守护者</a>
|
||||
<a href="chapter-145.html" class="sidebar-chapter ">第145章:精灵的誓言</a>
|
||||
<a href="chapter-146.html" class="sidebar-chapter ">第146章:深渊之眼</a>
|
||||
<a href="chapter-147.html" class="sidebar-chapter ">第147章:赫尔德的仪式</a>
|
||||
<a href="chapter-148.html" class="sidebar-chapter ">第148章:战后余晖</a>
|
||||
<a href="chapter-149.html" class="sidebar-chapter ">第149章:泰波尔斯的召唤</a>
|
||||
<a href="chapter-150.html" class="sidebar-chapter ">第150章:天空之城</a>
|
||||
<a href="chapter-151.html" class="sidebar-chapter ">第151章:风暴试炼</a>
|
||||
<a href="chapter-152.html" class="sidebar-chapter ">第152章:光芒与暗影</a>
|
||||
<a href="chapter-153.html" class="sidebar-chapter ">第153章:天空之战(上)</a>
|
||||
<a href="chapter-154.html" class="sidebar-chapter ">第154章:天空之战(中)</a>
|
||||
<a href="chapter-155.html" class="sidebar-chapter ">第155章:天空之战(下)</a>
|
||||
<a href="chapter-156.html" class="sidebar-chapter ">第156章:格兰之森异象</a>
|
||||
<a href="chapter-157.html" class="sidebar-chapter ">第157章:魔界深处</a>
|
||||
<a href="chapter-158.html" class="sidebar-chapter ">第158章:幻象迷宫</a>
|
||||
<a href="chapter-159.html" class="sidebar-chapter ">第159章:无形之战</a>
|
||||
<a href="chapter-160.html" class="sidebar-chapter ">第160章:无形者的秘密</a>
|
||||
<a href="chapter-161.html" class="sidebar-chapter ">第161章:光之试炼</a>
|
||||
<a href="chapter-162.html" class="sidebar-chapter ">第162章:希洛克的陷阱</a>
|
||||
<a href="chapter-163.html" class="sidebar-chapter ">第163章:无形之战</a>
|
||||
<a href="chapter-164.html" class="sidebar-chapter ">第164章:日常的温馨</a>
|
||||
<a href="chapter-165.html" class="sidebar-chapter ">第165章:莎莎的信</a>
|
||||
<a href="chapter-166.html" class="sidebar-chapter ">第166章:圣者之鸣号</a>
|
||||
<a href="chapter-167.html" class="sidebar-chapter ">第167章:黑色大地入口</a>
|
||||
<a href="chapter-168.html" class="sidebar-chapter ">第168章:焦黑之地深入</a>
|
||||
<a href="chapter-169.html" class="sidebar-chapter ">第169章:暗黑骑士团</a>
|
||||
<a href="chapter-170.html" class="sidebar-chapter current">第170章:黑暗中的记忆</a>
|
||||
<a href="chapter-171.html" class="sidebar-chapter ">第171章:混沌王座</a>
|
||||
<a href="chapter-172.html" class="sidebar-chapter ">第172章:混沌之神的力量</a>
|
||||
<a href="chapter-173.html" class="sidebar-chapter ">第173章:米歇尔的羁绊</a>
|
||||
<a href="chapter-174.html" class="sidebar-chapter ">第174章:创世之光的净化</a>
|
||||
<a href="chapter-175.html" class="sidebar-chapter ">第175章:混沌的终结</a>
|
||||
<a href="chapter-176.html" class="sidebar-chapter ">第176章:篇章落幕</a>
|
||||
<a href="chapter-177.html" class="sidebar-chapter ">第177章:番外·米歇尔的最后祝福</a>
|
||||
<a href="chapter-178.html" class="sidebar-chapter ">第178章:番外·奥兹玛的遗言</a>
|
||||
|
||||
</div>
|
||||
</aside>
|
||||
|
||||
<script>
|
||||
// 记录阅读进度
|
||||
let readChapters = JSON.parse(localStorage.getItem('readChapters') || '[]');
|
||||
if (!readChapters.includes(170)) {
|
||||
readChapters.push({{CHAPTER_ID}});
|
||||
localStorage.setItem('readChapters', JSON.stringify(readChapters));
|
||||
}
|
||||
|
||||
// 主题切换
|
||||
const themeToggle = document.getElementById('themeToggle');
|
||||
const savedTheme = localStorage.getItem('theme') || 'dark';
|
||||
document.documentElement.setAttribute('data-theme', savedTheme);
|
||||
themeToggle.textContent = savedTheme === 'dark' ? '浅色' : '深色';
|
||||
|
||||
themeToggle.addEventListener('click', () => {
|
||||
const currentTheme = document.documentElement.getAttribute('data-theme');
|
||||
const newTheme = currentTheme === 'dark' ? 'light' : 'dark';
|
||||
document.documentElement.setAttribute('data-theme', newTheme);
|
||||
localStorage.setItem('theme', newTheme);
|
||||
themeToggle.textContent = newTheme === 'dark' ? '浅色' : '深色';
|
||||
});
|
||||
|
||||
// 滚动到顶部
|
||||
document.getElementById('scrollTop').addEventListener('click', () => {
|
||||
window.scrollTo({ top: 0, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 滚动到底部
|
||||
document.getElementById('scrollBottom').addEventListener('click', () => {
|
||||
window.scrollTo({ top: document.body.scrollHeight, behavior: 'smooth' });
|
||||
});
|
||||
|
||||
// 页面加载时,侧边栏自动滚动到当前章节
|
||||
window.addEventListener('load', () => {
|
||||
const sidebarContent = document.getElementById('sidebarContent');
|
||||
const currentChapter = sidebarContent.querySelector('.current');
|
||||
if (currentChapter) {
|
||||
currentChapter.scrollIntoView({ behavior: 'smooth', block: 'center' });
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS弹出面板 ==========
|
||||
const ttsOverlay = document.getElementById('ttsOverlay');
|
||||
const ttsToggleBtn = document.getElementById('ttsToggleBtn');
|
||||
const ttsClose = document.getElementById('ttsClose');
|
||||
|
||||
// 打开TTS面板
|
||||
ttsToggleBtn.addEventListener('click', () => {
|
||||
ttsOverlay.classList.add('show');
|
||||
initTTS();
|
||||
});
|
||||
|
||||
// 关闭TTS面板
|
||||
ttsClose.addEventListener('click', () => {
|
||||
ttsOverlay.classList.remove('show');
|
||||
});
|
||||
|
||||
// 点击遮罩关闭
|
||||
ttsOverlay.addEventListener('click', (e) => {
|
||||
if (e.target === ttsOverlay) {
|
||||
ttsOverlay.classList.remove('show');
|
||||
}
|
||||
});
|
||||
|
||||
// ========== TTS语音朗读功能 ==========
|
||||
let ttsSynth = window.speechSynthesis;
|
||||
let ttsUtterance = null;
|
||||
let ttsText = '';
|
||||
let ttsSentences = [];
|
||||
let ttsCurrentIndex = 0;
|
||||
let ttsIsPlaying = false;
|
||||
let ttsIsPaused = false;
|
||||
let ttsSpeed = 1;
|
||||
|
||||
// 初始化:提取章节内容
|
||||
function initTTS() {
|
||||
const contentEl = document.querySelector('.chapter-content');
|
||||
if (!contentEl) return;
|
||||
|
||||
// 获取所有段落文本,清理HTML标签
|
||||
ttsText = contentEl.innerText || contentEl.textContent;
|
||||
// 分割成句子(中文按句号、问号、感叹号分割)
|
||||
ttsSentences = ttsText.match(/[^。!?\n]+[。!?\n]+|[^。!?\n]+$/g) || [ttsText];
|
||||
ttsSentences = ttsSentences.filter(s => s.trim().length > 0);
|
||||
|
||||
updateTTSProgress();
|
||||
}
|
||||
|
||||
// 更新进度显示
|
||||
function updateTTSProgress() {
|
||||
const total = ttsSentences.length;
|
||||
const current = ttsCurrentIndex;
|
||||
document.getElementById('ttsTime').textContent = `${current} / ${total} 句`;
|
||||
const percent = total > 0 ? (current / total * 100) : 0;
|
||||
document.getElementById('ttsProgressFill').style.width = `${percent}%`;
|
||||
}
|
||||
|
||||
// 播放当前句子
|
||||
function playCurrentSentence() {
|
||||
if (ttsCurrentIndex >= ttsSentences.length) {
|
||||
stopTTS();
|
||||
return;
|
||||
}
|
||||
|
||||
const text = ttsSentences[ttsCurrentIndex].trim();
|
||||
ttsUtterance = new SpeechSynthesisUtterance(text);
|
||||
ttsUtterance.lang = 'zh-CN';
|
||||
ttsUtterance.rate = ttsSpeed;
|
||||
|
||||
// 尝试选择中文语音
|
||||
const voices = ttsSynth.getVoices();
|
||||
const zhVoice = voices.find(v => v.lang.includes('zh') || v.lang.includes('CN'));
|
||||
if (zhVoice) {
|
||||
ttsUtterance.voice = zhVoice;
|
||||
}
|
||||
|
||||
ttsUtterance.onend = () => {
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsUtterance.onerror = (e) => {
|
||||
console.error('TTS error:', e);
|
||||
if (ttsIsPlaying) {
|
||||
ttsCurrentIndex++;
|
||||
updateTTSProgress();
|
||||
playCurrentSentence();
|
||||
}
|
||||
};
|
||||
|
||||
ttsSynth.speak(ttsUtterance);
|
||||
}
|
||||
|
||||
// 播放
|
||||
function playTTS() {
|
||||
if (ttsSentences.length === 0) {
|
||||
initTTS();
|
||||
}
|
||||
|
||||
if (ttsIsPaused) {
|
||||
ttsSynth.resume();
|
||||
ttsIsPaused = false;
|
||||
} else {
|
||||
ttsIsPlaying = true;
|
||||
playCurrentSentence();
|
||||
}
|
||||
|
||||
document.getElementById('ttsPlay').classList.add('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.add('active');
|
||||
}
|
||||
|
||||
// 暂停
|
||||
function pauseTTS() {
|
||||
if (ttsIsPlaying) {
|
||||
ttsSynth.pause();
|
||||
ttsIsPaused = true;
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.add('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
}
|
||||
|
||||
// 停止
|
||||
function stopTTS() {
|
||||
ttsSynth.cancel();
|
||||
ttsIsPlaying = false;
|
||||
ttsIsPaused = false;
|
||||
ttsCurrentIndex = 0;
|
||||
updateTTSProgress();
|
||||
document.getElementById('ttsPlay').classList.remove('active');
|
||||
document.getElementById('ttsPause').classList.remove('active');
|
||||
ttsToggleBtn.classList.remove('active');
|
||||
}
|
||||
|
||||
// 设置速度
|
||||
function setTTSSpeed(speed) {
|
||||
ttsSpeed = parseFloat(speed);
|
||||
// 如果正在播放,需要重新开始当前句子
|
||||
if (ttsIsPlaying && !ttsIsPaused) {
|
||||
ttsSynth.cancel();
|
||||
playCurrentSentence();
|
||||
}
|
||||
}
|
||||
|
||||
// 绑定事件
|
||||
document.getElementById('ttsPlay').addEventListener('click', playTTS);
|
||||
document.getElementById('ttsPause').addEventListener('click', pauseTTS);
|
||||
document.getElementById('ttsStop').addEventListener('click', stopTTS);
|
||||
document.getElementById('ttsSpeed').addEventListener('change', (e) => setTTSSpeed(e.target.value));
|
||||
|
||||
// 加载语音列表(某些浏览器需要异步加载)
|
||||
if (speechSynthesis.onvoiceschanged !== undefined) {
|
||||
speechSynthesis.onvoiceschanged = initTTS;
|
||||
}
|
||||
|
||||
// 页面离开时停止播放
|
||||
window.addEventListener('beforeunload', stopTTS);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user