diff --git a/docs/guides/presenter-view.md b/docs/guides/presenter-view.md index d3d15d8..92f25bc 100644 --- a/docs/guides/presenter-view.md +++ b/docs/guides/presenter-view.md @@ -71,8 +71,8 @@ See [Authoring slides](slides.md#speaker-notes) and ## Using a second screen To present on a projector while keeping the panel on your laptop screen, -click the "Open presenter view" button in the status bar. -It opens a second window at the same position +click the "Open a synced window" button in the status bar. +It opens another window at the same position (see [Multi-window sync](#multi-window-sync) for what makes this work in a static build). In the window on your laptop screen, press p to open the panel. Leave the other window full-screen on the projector. @@ -90,7 +90,7 @@ How position sync reaches other windows depends on how the deck is running: - **`inkflow build` output** (including a bare `file://` double-click, with no server at all) has no WebSocket to relay over, so it syncs exactly **two** windows directly: - the one you launch "Open presenter view" from, and the window it opens. + the one you launch "Open a synced window" from, and the window it opens. They talk to each other over a direct browser-to-browser link that only exists between opener and opened window, so a second window opened independently diff --git a/src/css/presenter/base.css b/src/css/presenter/base.css index 05d4e61..f2b0254 100644 --- a/src/css/presenter/base.css +++ b/src/css/presenter/base.css @@ -96,6 +96,51 @@ body { background: rgba(0, 0, 0, 0.08); } +/* ── Status-bar tooltips: driven by data-tooltip (not title) so the slow, unstyled + native browser tooltip never doubles up with this one. Anchored above the bar, + since #statusbar sits at the bottom of the viewport. ── */ +.hud-btn[data-tooltip] { + position: relative; +} +.hud-btn[data-tooltip]::after { + content: attr(data-tooltip); + position: absolute; + bottom: calc(100% + 8px); + left: 50%; + transform: translateX(-50%); + background: var(--surface); + color: var(--text); + border: 1px solid var(--overlay); + border-radius: 4px; + padding: 0.3rem 0.5rem; + font-size: 0.72rem; + white-space: nowrap; + box-shadow: 0 6px 18px rgba(0, 0, 0, 0.35); + pointer-events: none; + opacity: 0; + transition: opacity 0.1s ease; + z-index: 40; +} +.hud-btn[data-tooltip]:hover::after, +.hud-btn[data-tooltip]:focus-visible::after { + opacity: 1; + transition-delay: 0.35s; +} +/* Suppress while the sync dropdown is open — the tooltip would sit under the menu. */ +#btn-sync[aria-expanded="true"]:hover::after { + opacity: 0; + transition-delay: 0s; +} +/* Edge buttons: keep the bubble on-screen instead of centering off the bar. */ +#btn-theme[data-tooltip]::after { + left: 0; + transform: none; +} +#log-indicator[data-tooltip]::after { + left: auto; + right: 0; +} + .hud-sep { width: 1px; height: 16px; diff --git a/src/inkflow/bundles/presenter.css b/src/inkflow/bundles/presenter.css index 83f1a63..ba91d24 100644 --- a/src/inkflow/bundles/presenter.css +++ b/src/inkflow/bundles/presenter.css @@ -116,6 +116,45 @@ body { [data-theme=light] .hud-btn:hover { background: rgba(0, 0, 0, 0.08); } +.hud-btn[data-tooltip] { + position: relative; +} +.hud-btn[data-tooltip]::after { + content: attr(data-tooltip); + position: absolute; + bottom: calc(100% + 8px); + left: 50%; + transform: translateX(-50%); + background: var(--surface); + color: var(--text); + border: 1px solid var(--overlay); + border-radius: 4px; + padding: 0.3rem 0.5rem; + font-size: 0.72rem; + white-space: nowrap; + box-shadow: 0 6px 18px rgba(0, 0, 0, 0.35); + pointer-events: none; + opacity: 0; + transition: opacity 0.1s ease; + z-index: 40; +} +.hud-btn[data-tooltip]:hover::after, +.hud-btn[data-tooltip]:focus-visible::after { + opacity: 1; + transition-delay: 0.35s; +} +#btn-sync[aria-expanded=true]:hover::after { + opacity: 0; + transition-delay: 0s; +} +#btn-theme[data-tooltip]::after { + left: 0; + transform: none; +} +#log-indicator[data-tooltip]::after { + left: auto; + right: 0; +} .hud-sep { width: 1px; height: 16px; diff --git a/src/inkflow/bundles/presenter.js b/src/inkflow/bundles/presenter.js index 711bc28..c7a10bc 100644 --- a/src/inkflow/bundles/presenter.js +++ b/src/inkflow/bundles/presenter.js @@ -2858,7 +2858,7 @@ function renderSyncButton() { btnSync.dataset.mode = state.syncMode; const label = SYNC_LABELS[state.syncMode]; - btnSync.title = `Sync: ${label} (s)`; + btnSync.dataset.tooltip = `Sync: ${label} (s)`; btnSync.setAttribute("aria-label", `Sync mode: ${label}`); for (const row of syncMenu.querySelectorAll(".sync-row")) { const active = row.dataset.mode === state.syncMode; diff --git a/src/inkflow/presenter.html b/src/inkflow/presenter.html index 916a179..cb22a5d 100644 --- a/src/inkflow/presenter.html +++ b/src/inkflow/presenter.html @@ -140,7 +140,7 @@