v3: added index default tab selection setting, fixed notification pages not loading, reduced invite token length, global player state survives page reloads, many visual fixes
All checks were successful
Build and Publish Docker Image / build-and-push (push) Successful in 44s
All checks were successful
Build and Publish Docker Image / build-and-push (push) Successful in 44s
This commit is contained in:
120
src/App.css
120
src/App.css
@@ -207,6 +207,26 @@
|
||||
color: var(--color-danger);
|
||||
}
|
||||
|
||||
/* On the narrowest viewports the fixed-width action column squeezes the title
|
||||
into a sliver. Stack the block: title takes the full width on top, the
|
||||
vote/playlist actions sit in a row beneath it. */
|
||||
@media (max-width: 512px) {
|
||||
.dump-header-block {
|
||||
flex-direction: column;
|
||||
align-items: stretch;
|
||||
}
|
||||
|
||||
.dump-header-left {
|
||||
flex-direction: row;
|
||||
align-items: center;
|
||||
order: 2;
|
||||
}
|
||||
|
||||
.dump-header-right {
|
||||
order: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.dump-comment {
|
||||
font-size: 1.05rem;
|
||||
line-height: 1.72;
|
||||
@@ -1051,6 +1071,90 @@
|
||||
body.has-player {
|
||||
padding-bottom: var(--player-height, 0px);
|
||||
}
|
||||
|
||||
/* ── Floating "new dump" button ───────────────────────────────────────
|
||||
Revealed once the header scrolls out of view. Bottom-right by default, but
|
||||
moves to the top-right while the global player is mounted (it owns the
|
||||
bottom of the screen, full-width on mobile). Sits below the player and
|
||||
modal backdrop (both z-index 1000). */
|
||||
.dump-fab {
|
||||
position: fixed;
|
||||
--fab-size: 3.5rem;
|
||||
/* Sit just outside the right edge of the centered content lane — in the
|
||||
margin beside it — rather than over the content or pinned to the viewport
|
||||
edge. The lane width is `--fab-lane` (860px for most feeds; the journal
|
||||
grid is wider, see below). Falls back to a 1.25rem viewport gutter once
|
||||
that margin is too narrow to hold the button. */
|
||||
right: max(1.25rem, calc(50% - var(--fab-lane, 860px) / 2 - var(--fab-size) - 1rem));
|
||||
/* Anchored to the bottom-right by default, but expressed via `top` (rather
|
||||
than `bottom`) so the jump to the top-right when a player mounts can
|
||||
animate as a slide. `dvh` tracks the visible viewport on mobile; `vh` is
|
||||
the fallback for browsers without it. */
|
||||
top: calc(100vh - var(--fab-size) - 1.25rem - env(safe-area-inset-bottom, 0px));
|
||||
top: calc(100dvh - var(--fab-size) - 1.25rem - env(safe-area-inset-bottom, 0px));
|
||||
z-index: 900;
|
||||
width: var(--fab-size);
|
||||
height: var(--fab-size);
|
||||
display: flex;
|
||||
align-items: center;
|
||||
justify-content: center;
|
||||
padding: 0;
|
||||
border: none;
|
||||
/* Circle by default; a theme can square it off by setting --fab-radius: 0. */
|
||||
border-radius: var(--fab-radius, 50%);
|
||||
background: var(--color-accent);
|
||||
color: var(--color-on-accent);
|
||||
cursor: pointer;
|
||||
box-shadow: 0 4px 16px color-mix(in srgb, var(--color-accent) 45%, transparent),
|
||||
0 2px 6px rgba(0, 0, 0, 0.3);
|
||||
/* Hidden state: faded out, nudged down, non-interactive. */
|
||||
opacity: 0;
|
||||
transform: translateY(1rem) scale(0.9);
|
||||
pointer-events: none;
|
||||
transition: opacity 0.2s ease, transform 0.2s ease, background 0.15s ease,
|
||||
top 0.4s cubic-bezier(0.4, 0, 0.2, 1);
|
||||
}
|
||||
|
||||
.dump-fab-icon {
|
||||
width: 1.6rem;
|
||||
height: 1.6rem;
|
||||
}
|
||||
|
||||
.dump-fab--visible {
|
||||
opacity: 1;
|
||||
transform: translateY(0) scale(1);
|
||||
pointer-events: auto;
|
||||
}
|
||||
|
||||
.dump-fab:hover {
|
||||
background: var(--color-accent-hover);
|
||||
transform: translateY(-2px) scale(1);
|
||||
box-shadow: 0 6px 20px color-mix(in srgb, var(--color-accent) 55%, transparent),
|
||||
0 2px 6px rgba(0, 0, 0, 0.3);
|
||||
}
|
||||
|
||||
.dump-fab:active {
|
||||
transform: translateY(0) scale(0.96);
|
||||
}
|
||||
|
||||
/* The journal tab lays out its masonry grid in a wider lane than the other
|
||||
feeds, so the button must track that wider edge to stay aligned with it. */
|
||||
body:has(.journal-grid) {
|
||||
--fab-lane: 1180px;
|
||||
}
|
||||
|
||||
/* The player occupies the bottom of the screen (full-width on mobile), so when
|
||||
one is mounted slide the button up to the top-right corner to stay clear. */
|
||||
body.has-player .dump-fab {
|
||||
top: calc(1.25rem + env(safe-area-inset-top, 0px));
|
||||
}
|
||||
|
||||
/* Reserve room at the end of the scroll so the button never hides the last
|
||||
content when scrolled all the way down. */
|
||||
body.has-fab .page-content {
|
||||
padding-bottom: 5rem;
|
||||
}
|
||||
|
||||
.rich-content-thumbnail-btn {
|
||||
position: relative;
|
||||
padding: 0;
|
||||
@@ -1674,10 +1778,6 @@ body.has-player {
|
||||
display: flex;
|
||||
align-items: center;
|
||||
gap: 0.5rem;
|
||||
background: var(--color-surface);
|
||||
border: 1px solid var(--color-border-subtle);
|
||||
border-radius: 6px;
|
||||
padding: 0.3rem 0.5rem 0.3rem 0.75rem;
|
||||
max-width: 480px;
|
||||
}
|
||||
.invite-url {
|
||||
@@ -1685,11 +1785,18 @@ body.has-player {
|
||||
font-family: var(--font-mono, monospace);
|
||||
color: var(--color-text-muted);
|
||||
flex: 1;
|
||||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
min-width: 0;
|
||||
overflow-x: auto;
|
||||
white-space: nowrap;
|
||||
background: var(--color-surface);
|
||||
border: 1px solid var(--color-border-subtle);
|
||||
border-radius: 6px;
|
||||
padding: 0.35rem 0.6rem;
|
||||
}
|
||||
/* Always-visible copy target. Sits first so it's the obvious tap. */
|
||||
.invite-copy-btn {
|
||||
order: -1;
|
||||
flex-shrink: 0;
|
||||
padding: 0.2rem 0.65rem;
|
||||
border: 1px solid var(--color-border-subtle);
|
||||
border-radius: 4px;
|
||||
@@ -1698,7 +1805,6 @@ body.has-player {
|
||||
font-size: 0.75rem;
|
||||
cursor: pointer;
|
||||
white-space: nowrap;
|
||||
flex-shrink: 0;
|
||||
transition: background 0.12s;
|
||||
}
|
||||
.invite-copy-btn:hover {
|
||||
|
||||
Reference in New Issue
Block a user