|
@@ -4,7 +4,7 @@
|
|
|
<meta charset="UTF-8">
|
|
<meta charset="UTF-8">
|
|
|
<title>Deck · Multi-file Slide Index</title>
|
|
<title>Deck · Multi-file Slide Index</title>
|
|
|
<!--
|
|
<!--
|
|
|
- deck_index.html — 多文件 slide deck 的拼接器
|
|
|
|
|
|
|
+ deck_index.html — 多文件 slide deck 的拼接器(双模式)
|
|
|
|
|
|
|
|
配合「每页一个独立 HTML」架构使用。与单文件 deck_stage.js 对比:
|
|
配合「每页一个独立 HTML」架构使用。与单文件 deck_stage.js 对比:
|
|
|
· 每页独立作用域(CSS/JS 都隔离),一页出 bug 不影响其他页
|
|
· 每页独立作用域(CSS/JS 都隔离),一页出 bug 不影响其他页
|
|
@@ -12,6 +12,11 @@
|
|
|
· 多 agent 可并行做不同页,merge 时零冲突
|
|
· 多 agent 可并行做不同页,merge 时零冲突
|
|
|
· 适合 ≥15 页的讲座/课件/长 deck
|
|
· 适合 ≥15 页的讲座/课件/长 deck
|
|
|
|
|
|
|
|
|
|
+ 两种模式(body[data-mode] 控制):
|
|
|
|
|
+ · 概览墙 overview(默认进入):所有页缩略成 3D 透视卡片墙,景深斜铺、悬浮投影。
|
|
|
|
|
+ 点任意卡片 → 从该页进入演示;右下角「▶ 开始演示」从第 1 页(或记忆页)进入。
|
|
|
|
|
+ · 全屏演示 present:单页 fit 缩放翻页。ESC 或左上「⊞ 概览」回到概览墙。
|
|
|
|
|
+
|
|
|
用法:
|
|
用法:
|
|
|
1. 把本文件复制到 deck 根目录,重命名 index.html
|
|
1. 把本文件复制到 deck 根目录,重命名 index.html
|
|
|
2. 在同目录建 slides/ 子目录,放每一页独立 HTML
|
|
2. 在同目录建 slides/ 子目录,放每一页独立 HTML
|
|
@@ -23,7 +28,7 @@
|
|
|
· shared/chrome.html — 页眉页脚可复用片段
|
|
· shared/chrome.html — 页眉页脚可复用片段
|
|
|
· 每页 HTML 自己 <link> 进去即可
|
|
· 每页 HTML 自己 <link> 进去即可
|
|
|
|
|
|
|
|
- 键盘:← / → / Space / PgUp / PgDown / Home / End / 1-9 跳页 / P 打印
|
|
|
|
|
|
|
+ 键盘(演示模式):← / → / Space / PgUp / PgDown / Home / End / 1-9 跳页 / P 打印 / ESC 回概览
|
|
|
-->
|
|
-->
|
|
|
|
|
|
|
|
<!-- ═══════════════════════════════════════════════════════ -->
|
|
<!-- ═══════════════════════════════════════════════════════ -->
|
|
@@ -50,6 +55,115 @@
|
|
|
overflow: hidden;
|
|
overflow: hidden;
|
|
|
font-family: -apple-system, "PingFang SC", sans-serif;
|
|
font-family: -apple-system, "PingFang SC", sans-serif;
|
|
|
}
|
|
}
|
|
|
|
|
+
|
|
|
|
|
+ /* ── 模式显隐:默认 overview ───────────────────────────── */
|
|
|
|
|
+ body[data-mode="overview"] { background: #f0eee9; overflow: auto; }
|
|
|
|
|
+ body[data-mode="overview"] #present-ui { display: none; }
|
|
|
|
|
+ body[data-mode="present"] #overview { display: none; }
|
|
|
|
|
+ body[data-mode="present"] .start-btn { display: none; }
|
|
|
|
|
+
|
|
|
|
|
+ /* ════════════════════════════════════════════════════════ */
|
|
|
|
|
+ /* 模式 A · 概览墙(3D 透视卡片墙) */
|
|
|
|
|
+ /* ════════════════════════════════════════════════════════ */
|
|
|
|
|
+ #overview {
|
|
|
|
|
+ min-height: 100%;
|
|
|
|
|
+ padding: 7vw 5vw 14vw;
|
|
|
|
|
+ /* 透视容器:景深 */
|
|
|
|
|
+ perspective: 1600px;
|
|
|
|
|
+ perspective-origin: 50% 38%;
|
|
|
|
|
+ }
|
|
|
|
|
+ .wall {
|
|
|
|
|
+ display: grid;
|
|
|
|
|
+ grid-template-columns: repeat(4, 1fr);
|
|
|
|
|
+ gap: 2.4vw;
|
|
|
|
|
+ max-width: 1500px;
|
|
|
|
|
+ margin: 0 auto;
|
|
|
|
|
+ transform-style: preserve-3d;
|
|
|
|
|
+ /* 近处向左下、远处向右上铺开 */
|
|
|
|
|
+ transform: rotateX(28deg) rotateZ(-14deg);
|
|
|
|
|
+ }
|
|
|
|
|
+ .card {
|
|
|
|
|
+ position: relative;
|
|
|
|
|
+ aspect-ratio: 16 / 9;
|
|
|
|
|
+ border-radius: 10px;
|
|
|
|
|
+ overflow: hidden;
|
|
|
|
|
+ background: #fff;
|
|
|
|
|
+ cursor: pointer;
|
|
|
|
|
+ box-shadow: 0 18px 40px rgba(40, 34, 24, 0.22),
|
|
|
|
|
+ 0 4px 12px rgba(40, 34, 24, 0.14);
|
|
|
|
|
+ transition: transform 0.45s cubic-bezier(.2,.7,.2,1),
|
|
|
|
|
+ box-shadow 0.45s cubic-bezier(.2,.7,.2,1);
|
|
|
|
|
+ transform-style: preserve-3d;
|
|
|
|
|
+ will-change: transform;
|
|
|
|
|
+ }
|
|
|
|
|
+ .card:hover {
|
|
|
|
|
+ /* 抬起 + 微微「正过来」给预览感 */
|
|
|
|
|
+ transform: translateZ(80px) rotateX(-14deg) rotateZ(14deg);
|
|
|
|
|
+ box-shadow: 0 40px 80px rgba(40, 34, 24, 0.32),
|
|
|
|
|
+ 0 10px 24px rgba(40, 34, 24, 0.20);
|
|
|
|
|
+ z-index: 2;
|
|
|
|
|
+ }
|
|
|
|
|
+ .card .thumb {
|
|
|
|
|
+ position: absolute;
|
|
|
|
|
+ top: 0; left: 0;
|
|
|
|
|
+ width: 1920px;
|
|
|
|
|
+ height: 1080px;
|
|
|
|
|
+ transform-origin: top left;
|
|
|
|
|
+ /* scale 由 JS 按卡片实际宽度设置 */
|
|
|
|
|
+ pointer-events: none;
|
|
|
|
|
+ }
|
|
|
|
|
+ .card .thumb iframe {
|
|
|
|
|
+ width: 1920px;
|
|
|
|
|
+ height: 1080px;
|
|
|
|
|
+ border: 0;
|
|
|
|
|
+ display: block;
|
|
|
|
|
+ background: #fff;
|
|
|
|
|
+ pointer-events: none;
|
|
|
|
|
+ }
|
|
|
|
|
+ .card .num {
|
|
|
|
|
+ position: absolute;
|
|
|
|
|
+ bottom: 8px; left: 10px;
|
|
|
|
|
+ background: rgba(20, 16, 10, 0.72);
|
|
|
|
|
+ color: #fff;
|
|
|
|
|
+ font-size: 12px;
|
|
|
|
|
+ line-height: 1;
|
|
|
|
|
+ padding: 5px 9px;
|
|
|
|
|
+ border-radius: 6px;
|
|
|
|
|
+ font-variant-numeric: tabular-nums;
|
|
|
|
|
+ letter-spacing: 0.04em;
|
|
|
|
|
+ z-index: 3;
|
|
|
|
|
+ pointer-events: none;
|
|
|
|
|
+ }
|
|
|
|
|
+ #overview-title {
|
|
|
|
|
+ text-align: center;
|
|
|
|
|
+ color: #5a5346;
|
|
|
|
|
+ font-size: 15px;
|
|
|
|
|
+ letter-spacing: 0.18em;
|
|
|
|
|
+ margin: 0 auto 5vw;
|
|
|
|
|
+ text-transform: uppercase;
|
|
|
|
|
+ opacity: 0.7;
|
|
|
|
|
+ }
|
|
|
|
|
+ .start-btn {
|
|
|
|
|
+ position: fixed;
|
|
|
|
|
+ bottom: 28px; right: 28px;
|
|
|
|
|
+ background: #1a1712;
|
|
|
|
|
+ color: #fff;
|
|
|
|
|
+ border: 0;
|
|
|
|
|
+ padding: 14px 26px;
|
|
|
|
|
+ border-radius: 999px;
|
|
|
|
|
+ font-size: 15px;
|
|
|
|
|
+ font-family: inherit;
|
|
|
|
|
+ letter-spacing: 0.04em;
|
|
|
|
|
+ cursor: pointer;
|
|
|
|
|
+ z-index: 200;
|
|
|
|
|
+ box-shadow: 0 8px 28px rgba(40, 34, 24, 0.28);
|
|
|
|
|
+ transition: transform 0.18s, box-shadow 0.18s;
|
|
|
|
|
+ }
|
|
|
|
|
+ .start-btn:hover { transform: translateY(-2px); box-shadow: 0 12px 34px rgba(40, 34, 24, 0.36); }
|
|
|
|
|
+
|
|
|
|
|
+ /* ════════════════════════════════════════════════════════ */
|
|
|
|
|
+ /* 模式 B · 全屏演示 */
|
|
|
|
|
+ /* ════════════════════════════════════════════════════════ */
|
|
|
#stage {
|
|
#stage {
|
|
|
position: fixed;
|
|
position: fixed;
|
|
|
top: 50%; left: 50%;
|
|
top: 50%; left: 50%;
|
|
@@ -59,7 +173,7 @@
|
|
|
box-shadow: 0 10px 60px rgba(0,0,0,0.4);
|
|
box-shadow: 0 10px 60px rgba(0,0,0,0.4);
|
|
|
/* size set by JS from DECK_WIDTH/HEIGHT */
|
|
/* size set by JS from DECK_WIDTH/HEIGHT */
|
|
|
}
|
|
}
|
|
|
- iframe {
|
|
|
|
|
|
|
+ #stage iframe {
|
|
|
width: 100%;
|
|
width: 100%;
|
|
|
height: 100%;
|
|
height: 100%;
|
|
|
border: 0;
|
|
border: 0;
|
|
@@ -84,6 +198,23 @@
|
|
|
}
|
|
}
|
|
|
.counter:hover { opacity: 1; }
|
|
.counter:hover { opacity: 1; }
|
|
|
.counter .label { color: rgba(255,255,255,0.7); margin-left: 8px; }
|
|
.counter .label { color: rgba(255,255,255,0.7); margin-left: 8px; }
|
|
|
|
|
+ .overview-btn {
|
|
|
|
|
+ position: fixed;
|
|
|
|
|
+ top: 20px; left: 20px;
|
|
|
|
|
+ background: rgba(0,0,0,0.55);
|
|
|
|
|
+ color: rgba(255,255,255,0.85);
|
|
|
|
|
+ border: 0;
|
|
|
|
|
+ padding: 7px 14px;
|
|
|
|
|
+ border-radius: 999px;
|
|
|
|
|
+ font-size: 13px;
|
|
|
|
|
+ font-family: inherit;
|
|
|
|
|
+ letter-spacing: 0.04em;
|
|
|
|
|
+ cursor: pointer;
|
|
|
|
|
+ z-index: 100;
|
|
|
|
|
+ opacity: 0.6;
|
|
|
|
|
+ transition: opacity 0.2s;
|
|
|
|
|
+ }
|
|
|
|
|
+ .overview-btn:hover { opacity: 1; }
|
|
|
.nav-zone {
|
|
.nav-zone {
|
|
|
position: fixed;
|
|
position: fixed;
|
|
|
top: 0; bottom: 0;
|
|
top: 0; bottom: 0;
|
|
@@ -115,8 +246,9 @@
|
|
|
@media print {
|
|
@media print {
|
|
|
@page { size: 1920px 1080px; margin: 0; }
|
|
@page { size: 1920px 1080px; margin: 0; }
|
|
|
html, body { background: #fff; overflow: visible; height: auto; }
|
|
html, body { background: #fff; overflow: visible; height: auto; }
|
|
|
|
|
+ body[data-mode] #overview { display: none !important; }
|
|
|
#stage { position: static; transform: none !important; box-shadow: none; }
|
|
#stage { position: static; transform: none !important; box-shadow: none; }
|
|
|
- .counter, .nav-zone { display: none !important; }
|
|
|
|
|
|
|
+ .counter, .nav-zone, .overview-btn, .start-btn { display: none !important; }
|
|
|
/* In print mode we render all slides sequentially — see JS */
|
|
/* In print mode we render all slides sequentially — see JS */
|
|
|
.print-stack { display: block; }
|
|
.print-stack { display: block; }
|
|
|
.print-stack iframe {
|
|
.print-stack iframe {
|
|
@@ -128,15 +260,25 @@
|
|
|
}
|
|
}
|
|
|
</style>
|
|
</style>
|
|
|
</head>
|
|
</head>
|
|
|
-<body>
|
|
|
|
|
|
|
+<body data-mode="overview">
|
|
|
|
|
|
|
|
-<div id="stage">
|
|
|
|
|
- <iframe id="frame" src="about:blank"></iframe>
|
|
|
|
|
|
|
+<!-- ── 模式 A · 概览墙 ─────────────────────────────────────── -->
|
|
|
|
|
+<div id="overview">
|
|
|
|
|
+ <div id="overview-title">Overview · 点击任意页进入演示</div>
|
|
|
|
|
+ <div class="wall" id="wall"></div>
|
|
|
</div>
|
|
</div>
|
|
|
|
|
+<button class="start-btn" id="startBtn">▶ 开始演示</button>
|
|
|
|
|
|
|
|
-<div class="nav-zone left" id="navL"><div class="nav-hint">‹</div></div>
|
|
|
|
|
-<div class="nav-zone right" id="navR"><div class="nav-hint">›</div></div>
|
|
|
|
|
-<div class="counter" id="counter">1 / 1</div>
|
|
|
|
|
|
|
+<!-- ── 模式 B · 全屏演示 ───────────────────────────────────── -->
|
|
|
|
|
+<div id="present-ui">
|
|
|
|
|
+ <div id="stage">
|
|
|
|
|
+ <iframe id="frame" src="about:blank"></iframe>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <button class="overview-btn" id="overviewBtn">⊞ 概览</button>
|
|
|
|
|
+ <div class="nav-zone left" id="navL"><div class="nav-hint">‹</div></div>
|
|
|
|
|
+ <div class="nav-zone right" id="navR"><div class="nav-hint">›</div></div>
|
|
|
|
|
+ <div class="counter" id="counter">1 / 1</div>
|
|
|
|
|
+</div>
|
|
|
|
|
|
|
|
<!-- Print-only stack: populated on beforeprint, stripped on afterprint -->
|
|
<!-- Print-only stack: populated on beforeprint, stripped on afterprint -->
|
|
|
<div class="print-stack" id="printStack" style="display:none;"></div>
|
|
<div class="print-stack" id="printStack" style="display:none;"></div>
|
|
@@ -150,12 +292,58 @@
|
|
|
const frame = document.getElementById('frame');
|
|
const frame = document.getElementById('frame');
|
|
|
const counter = document.getElementById('counter');
|
|
const counter = document.getElementById('counter');
|
|
|
const printStack = document.getElementById('printStack');
|
|
const printStack = document.getElementById('printStack');
|
|
|
|
|
+ const wall = document.getElementById('wall');
|
|
|
const storageKey = 'deck-index-' + location.pathname;
|
|
const storageKey = 'deck-index-' + location.pathname;
|
|
|
let current = 0;
|
|
let current = 0;
|
|
|
|
|
|
|
|
stage.style.width = W + 'px';
|
|
stage.style.width = W + 'px';
|
|
|
stage.style.height = H + 'px';
|
|
stage.style.height = H + 'px';
|
|
|
|
|
|
|
|
|
|
+ /* ── 模式切换 ─────────────────────────────────────────── */
|
|
|
|
|
+ function setMode(mode) {
|
|
|
|
|
+ document.body.setAttribute('data-mode', mode);
|
|
|
|
|
+ if (mode === 'present') { fit(); show(current); }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* ════════ 模式 A · 概览墙 ════════ */
|
|
|
|
|
+ function buildWall() {
|
|
|
|
|
+ wall.innerHTML = '';
|
|
|
|
|
+ deck.forEach((item, i) => {
|
|
|
|
|
+ const card = document.createElement('div');
|
|
|
|
|
+ card.className = 'card';
|
|
|
|
|
+ card.dataset.idx = i;
|
|
|
|
|
+
|
|
|
|
|
+ const thumb = document.createElement('div');
|
|
|
|
|
+ thumb.className = 'thumb';
|
|
|
|
|
+ const ifr = document.createElement('iframe');
|
|
|
|
|
+ ifr.src = item.file;
|
|
|
|
|
+ ifr.setAttribute('scrolling', 'no');
|
|
|
|
|
+ thumb.appendChild(ifr);
|
|
|
|
|
+
|
|
|
|
|
+ const num = document.createElement('div');
|
|
|
|
|
+ num.className = 'num';
|
|
|
|
|
+ num.textContent = (i + 1) + (item.label ? ' · ' + item.label : '');
|
|
|
|
|
+
|
|
|
|
|
+ card.appendChild(thumb);
|
|
|
|
|
+ card.appendChild(num);
|
|
|
|
|
+ card.addEventListener('click', () => { current = i; setMode('present'); });
|
|
|
|
|
+ wall.appendChild(card);
|
|
|
|
|
+ });
|
|
|
|
|
+ scaleThumbs();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 把 1920×1080 的缩略 iframe 缩放到卡片实际宽度
|
|
|
|
|
+ function scaleThumbs() {
|
|
|
|
|
+ document.querySelectorAll('.card').forEach(card => {
|
|
|
|
|
+ const thumb = card.querySelector('.thumb');
|
|
|
|
|
+ if (!thumb) return;
|
|
|
|
|
+ const w = card.clientWidth;
|
|
|
|
|
+ if (!w) return;
|
|
|
|
|
+ thumb.style.transform = 'scale(' + (w / W) + ')';
|
|
|
|
|
+ });
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ /* ════════ 模式 B · 全屏演示 ════════ */
|
|
|
function fit() {
|
|
function fit() {
|
|
|
const s = Math.min(window.innerWidth / W, window.innerHeight / H);
|
|
const s = Math.min(window.innerWidth / W, window.innerHeight / H);
|
|
|
const x = (window.innerWidth - W * s) / 2;
|
|
const x = (window.innerWidth - W * s) / 2;
|
|
@@ -168,7 +356,8 @@
|
|
|
function show(idx) {
|
|
function show(idx) {
|
|
|
if (idx < 0 || idx >= deck.length) return;
|
|
if (idx < 0 || idx >= deck.length) return;
|
|
|
current = idx;
|
|
current = idx;
|
|
|
- frame.src = deck[idx].file;
|
|
|
|
|
|
|
+ const wanted = deck[idx].file;
|
|
|
|
|
+ if (frame.getAttribute('src') !== wanted) frame.src = wanted;
|
|
|
counter.innerHTML = `${idx + 1} / ${deck.length} <span class="label">${deck[idx].label || ''}</span>`;
|
|
counter.innerHTML = `${idx + 1} / ${deck.length} <span class="label">${deck[idx].label || ''}</span>`;
|
|
|
try { localStorage.setItem(storageKey, String(idx)); } catch (_) {}
|
|
try { localStorage.setItem(storageKey, String(idx)); } catch (_) {}
|
|
|
if (location.hash !== '#' + (idx + 1)) {
|
|
if (location.hash !== '#' + (idx + 1)) {
|
|
@@ -182,12 +371,19 @@
|
|
|
// Keyboard
|
|
// Keyboard
|
|
|
document.addEventListener('keydown', (e) => {
|
|
document.addEventListener('keydown', (e) => {
|
|
|
if (e.target.tagName === 'INPUT' || e.target.tagName === 'TEXTAREA') return;
|
|
if (e.target.tagName === 'INPUT' || e.target.tagName === 'TEXTAREA') return;
|
|
|
|
|
+ // ESC 回概览(演示模式下)
|
|
|
|
|
+ if (e.key === 'Escape') {
|
|
|
|
|
+ if (document.body.getAttribute('data-mode') === 'present') { e.preventDefault(); setMode('overview'); }
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+ if (e.key === 'p' || e.key === 'P') { window.print(); return; }
|
|
|
|
|
+ // 其余翻页键仅在演示模式生效
|
|
|
|
|
+ if (document.body.getAttribute('data-mode') !== 'present') return;
|
|
|
switch (e.key) {
|
|
switch (e.key) {
|
|
|
case 'ArrowRight': case ' ': case 'PageDown': e.preventDefault(); next(); break;
|
|
case 'ArrowRight': case ' ': case 'PageDown': e.preventDefault(); next(); break;
|
|
|
case 'ArrowLeft': case 'PageUp': e.preventDefault(); prev(); break;
|
|
case 'ArrowLeft': case 'PageUp': e.preventDefault(); prev(); break;
|
|
|
case 'Home': e.preventDefault(); show(0); break;
|
|
case 'Home': e.preventDefault(); show(0); break;
|
|
|
case 'End': e.preventDefault(); show(deck.length - 1); break;
|
|
case 'End': e.preventDefault(); show(deck.length - 1); break;
|
|
|
- case 'p': case 'P': window.print(); break;
|
|
|
|
|
default:
|
|
default:
|
|
|
if (e.key >= '1' && e.key <= '9') {
|
|
if (e.key >= '1' && e.key <= '9') {
|
|
|
const i = parseInt(e.key, 10) - 1;
|
|
const i = parseInt(e.key, 10) - 1;
|
|
@@ -198,22 +394,35 @@
|
|
|
|
|
|
|
|
document.getElementById('navL').addEventListener('click', prev);
|
|
document.getElementById('navL').addEventListener('click', prev);
|
|
|
document.getElementById('navR').addEventListener('click', next);
|
|
document.getElementById('navR').addEventListener('click', next);
|
|
|
- window.addEventListener('resize', fit);
|
|
|
|
|
|
|
+ document.getElementById('startBtn').addEventListener('click', () => setMode('present'));
|
|
|
|
|
+ document.getElementById('overviewBtn').addEventListener('click', () => setMode('overview'));
|
|
|
|
|
+ window.addEventListener('resize', () => { fit(); scaleThumbs(); });
|
|
|
window.addEventListener('hashchange', () => {
|
|
window.addEventListener('hashchange', () => {
|
|
|
const m = location.hash.match(/^#(\d+)$/);
|
|
const m = location.hash.match(/^#(\d+)$/);
|
|
|
- if (m) show(parseInt(m[1], 10) - 1);
|
|
|
|
|
|
|
+ if (m) { current = parseInt(m[1], 10) - 1; setMode('present'); }
|
|
|
});
|
|
});
|
|
|
|
|
|
|
|
- // Initial: hash > localStorage > 0
|
|
|
|
|
|
|
+ // 起始页:hash > localStorage > 0(决定 current;hash 还会直接进演示)
|
|
|
const hashMatch = location.hash.match(/^#(\d+)$/);
|
|
const hashMatch = location.hash.match(/^#(\d+)$/);
|
|
|
- if (hashMatch) current = Math.min(parseInt(hashMatch[1], 10) - 1, deck.length - 1);
|
|
|
|
|
- else try {
|
|
|
|
|
- const v = parseInt(localStorage.getItem(storageKey), 10);
|
|
|
|
|
- if (!isNaN(v) && v >= 0 && v < deck.length) current = v;
|
|
|
|
|
- } catch (_) {}
|
|
|
|
|
|
|
+ if (hashMatch) {
|
|
|
|
|
+ current = Math.min(parseInt(hashMatch[1], 10) - 1, deck.length - 1);
|
|
|
|
|
+ } else {
|
|
|
|
|
+ try {
|
|
|
|
|
+ const v = parseInt(localStorage.getItem(storageKey), 10);
|
|
|
|
|
+ if (!isNaN(v) && v >= 0 && v < deck.length) current = v;
|
|
|
|
|
+ } catch (_) {}
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ // 先把演示舞台准备好(即便默认在概览,CSS 隐藏它)
|
|
|
fit();
|
|
fit();
|
|
|
show(current);
|
|
show(current);
|
|
|
|
|
|
|
|
|
|
+ buildWall();
|
|
|
|
|
+
|
|
|
|
|
+ // 默认进概览;但若 URL 带 #N,直接进演示从该页开始
|
|
|
|
|
+ if (hashMatch) setMode('present');
|
|
|
|
|
+ else setMode('overview');
|
|
|
|
|
+
|
|
|
// Print: build a stack of all iframes so browser prints every slide
|
|
// Print: build a stack of all iframes so browser prints every slide
|
|
|
window.addEventListener('beforeprint', () => {
|
|
window.addEventListener('beforeprint', () => {
|
|
|
printStack.innerHTML = '';
|
|
printStack.innerHTML = '';
|
|
@@ -223,12 +432,12 @@
|
|
|
printStack.appendChild(f);
|
|
printStack.appendChild(f);
|
|
|
});
|
|
});
|
|
|
printStack.style.display = 'block';
|
|
printStack.style.display = 'block';
|
|
|
- document.getElementById('stage').style.display = 'none';
|
|
|
|
|
|
|
+ stage.style.display = 'none';
|
|
|
});
|
|
});
|
|
|
window.addEventListener('afterprint', () => {
|
|
window.addEventListener('afterprint', () => {
|
|
|
printStack.innerHTML = '';
|
|
printStack.innerHTML = '';
|
|
|
printStack.style.display = 'none';
|
|
printStack.style.display = 'none';
|
|
|
- document.getElementById('stage').style.display = '';
|
|
|
|
|
|
|
+ stage.style.display = '';
|
|
|
});
|
|
});
|
|
|
})();
|
|
})();
|
|
|
</script>
|
|
</script>
|