feat(skin): add error handling for audio players (#1048)

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
Sam Potts
2026-03-23 09:33:55 +11:00
committed by GitHub
co-authored by Claude Opus 4.6
parent 559d5169b5
commit df927f67fc
43 changed files with 648 additions and 377 deletions
+47 -5
View File
@@ -1,5 +1,3 @@
@import "../../shared/css/audio/icon-state.css";
@import "../../shared/css/audio/tooltip-state.css";
@import "./components/reset.css";
@import "./components/root.css";
@import "./components/surface.css";
@@ -11,6 +9,8 @@
@import "./components/icons.css";
@import "./components/slider.css";
@import "./components/popup.css";
@import "../../shared/css/audio/icon-state.css";
@import "../../shared/css/audio/tooltip-state.css";
/* ==========================================================================
Root
@@ -23,26 +23,68 @@
--media-surface-outer-border-color: oklch(0 0 0 / 0.05);
--media-surface-shadow-color: oklch(0 0 0 / 0.15);
--media-surface-backdrop-filter: blur(16px) saturate(1.5);
--media-controls-text-color: var(--media-color-primary, oklch(0 0 0));
--media-text-color: var(--media-color-primary, oklch(0 0 0));
@media (prefers-color-scheme: dark) {
--media-border-color: oklch(1 0 0 / 0.1);
--media-surface-background-color: oklch(0 0 0 / 0.4);
--media-controls-text-color: var(--media-color-primary, oklch(1 0 0));
--media-text-color: var(--media-color-primary, oklch(1 0 0));
}
}
/* ==========================================================================
Error Dialog
========================================================================== */
.media-default-skin--audio .media-error__dialog {
position: absolute;
inset: 0;
z-index: 20;
display: flex;
align-items: center;
gap: 0.75rem;
padding-inline: 1.25rem 0.125rem;
transition-property: opacity, filter;
transition-duration: 300ms;
transition-delay: 100ms;
transition-timing-function: ease-out;
border-radius: calc(infinity * 1px);
background-color: var(--media-surface-background-color);
backdrop-filter: var(--media-surface-backdrop-filter);
color: var(--media-text-color);
/* Simple, fast transition for reduced motion users */
@media (prefers-reduced-motion: reduce) {
transition-duration: 100ms;
transition-delay: 0ms;
}
}
.media-default-skin .media-error[data-starting-style] .media-error__dialog,
.media-default-skin .media-error[data-ending-style] .media-error__dialog {
opacity: 0;
filter: blur(4px);
}
.media-default-skin--audio .media-error__content {
flex: 1;
display: flex;
gap: 0.5rem;
align-items: center;
}
/* ==========================================================================
Controls
========================================================================== */
.media-default-skin--audio .media-controls {
color: var(--media-controls-text-color);
color: var(--media-text-color);
}
/* ==========================================================================
Sliders
========================================================================== */
.media-default-skin--audio .media-slider__track {
background-color: oklch(0 0 0 / 0.1);
@@ -9,15 +9,11 @@
justify-content: center;
flex-shrink: 0;
padding: 0.5rem 1rem;
background: oklch(1 0 0);
border: none;
border-radius: calc(infinity * 1px);
outline: 2px solid transparent;
outline-offset: -2px;
color: oklch(0 0 0);
font-weight: 500;
text-align: center;
transition-property: background-color, color, outline-offset, scale;
transition-property: background-color, outline-offset, scale;
transition-duration: 150ms;
transition-timing-function: ease-out;
cursor: pointer;
@@ -25,10 +21,14 @@
touch-action: manipulation;
&:focus-visible {
outline-color: oklch(62.3% 0.214 259.815);
outline-color: currentColor;
outline-offset: 2px;
}
&:active {
scale: 0.98;
}
&[disabled] {
opacity: 0.5;
filter: grayscale(1);
@@ -40,12 +40,16 @@
}
}
/* Icon button variant */
.media-default-skin .media-button--icon {
display: grid;
width: 2.125rem;
padding: 0;
aspect-ratio: 1;
/* Primary button variant */
.media-default-skin .media-button--primary {
background: oklch(1 0 0);
color: oklch(0 0 0);
font-weight: 500;
text-align: center;
}
/* Subtle button variant */
.media-default-skin .media-button--subtle {
background: transparent;
color: inherit;
text-shadow: inherit;
@@ -56,6 +60,14 @@
background-color: oklch(from currentColor l c h / 0.1);
text-decoration: none;
}
}
/* Icon button variant */
.media-default-skin .media-button--icon {
display: grid;
width: 2.125rem;
padding: 0;
aspect-ratio: 1;
&:active {
scale: 0.9;
@@ -72,7 +84,7 @@
position: absolute;
right: -1px;
bottom: -3px;
font-size: 0.75em;
font-size: 10px;
font-weight: 480;
font-variant-numeric: tabular-nums;
}
@@ -3,57 +3,7 @@
========================================================================== */
.media-default-skin .media-error {
position: absolute;
inset: 0;
z-index: 20;
display: flex;
align-items: center;
justify-content: center;
}
.media-default-skin .media-error__dialog {
display: flex;
flex-direction: column;
gap: 0.75rem;
max-width: 18rem;
padding: 0.75rem;
border-radius: 1.75rem;
color: oklch(1 0 0);
font-size: 0.875rem;
transition-property: opacity, scale;
transition-duration: 500ms;
transition-delay: 100ms;
transition-timing-function: linear(
0,
0.034 1.5%,
0.763 9.7%,
1.066 13.9%,
1.198 19.9%,
1.184 21.8%,
0.963 37.5%,
0.997 50.9%,
1
);
/* Simple, fast transition for reduced motion users */
@media (prefers-reduced-motion: reduce) {
transition-duration: 100ms;
transition-delay: 0ms;
transition-timing-function: ease-out;
}
}
.media-default-skin .media-error[data-starting-style] .media-error__dialog,
.media-default-skin .media-error[data-ending-style] .media-error__dialog {
opacity: 0;
scale: 0.5;
}
.media-default-skin .media-error__content {
display: flex;
flex-direction: column;
gap: 0.5rem;
padding: 0.5rem 0.5rem 0.375rem;
outline: none;
}
.media-default-skin .media-error__title {
@@ -74,3 +24,7 @@
flex: 1;
}
}
.media-default-skin .media-error[data-open] ~ .media-controls * {
visibility: hidden;
}
@@ -79,6 +79,22 @@
outline-color: oklch(from currentColor l c h / 0.25);
outline-offset: 0;
}
&::after {
content: "";
position: absolute;
inset: -4px;
border-radius: inherit;
box-shadow: 0 0 0 2px oklch(1 0 0);
transition-property: opacity, scale;
transition-duration: 150ms;
transition-timing-function: ease-out;
}
&:not(:focus-visible)::after {
scale: 0.5;
opacity: 0;
}
}
.media-default-skin .media-slider:active .media-slider__thumb,
+69 -2
View File
@@ -1,5 +1,3 @@
@import "../../shared/css/video/icon-state.css";
@import "../../shared/css/video/tooltip-state.css";
@import "./components/reset.css";
@import "./components/root.css";
@import "./components/surface.css";
@@ -16,6 +14,8 @@
@import "./components/slider.css";
@import "./components/popup.css";
@import "./components/captions.css";
@import "../../shared/css/video/icon-state.css";
@import "../../shared/css/video/tooltip-state.css";
/* ==========================================================================
Root
@@ -67,6 +67,69 @@
}
}
/* ==========================================================================
Error Dialog
========================================================================== */
.media-default-skin--video .media-error {
position: absolute;
inset: 0;
z-index: 20;
display: flex;
align-items: center;
justify-content: center;
}
.media-default-skin--video .media-error__dialog {
display: flex;
flex-direction: column;
gap: 0.75rem;
max-width: 18rem;
padding: 0.75rem;
border-radius: 1.75rem;
color: oklch(1 0 0);
text-shadow: 0 1px 0 oklch(0 0 0 / 0.25);
transition-property: opacity, scale;
transition-duration: 500ms;
transition-delay: 100ms;
transition-timing-function: linear(
0,
0.034 1.5%,
0.763 9.7%,
1.066 13.9%,
1.198 19.9%,
1.184 21.8%,
0.963 37.5%,
0.997 50.9%,
1
);
/* Simple, fast transition for reduced motion users */
@media (prefers-reduced-motion: reduce) {
transition-duration: 100ms;
transition-delay: 0ms;
transition-timing-function: ease-out;
}
}
.media-default-skin .media-error[data-starting-style] .media-error__dialog,
.media-default-skin .media-error[data-ending-style] .media-error__dialog {
opacity: 0;
scale: 0.5;
}
.media-default-skin--video .media-error__content {
display: flex;
flex-direction: column;
gap: 0.5rem;
padding: 0.5rem 0.5rem 0.375rem;
text-shadow: inherit;
}
.media-default-skin--video .media-error__title {
font-size: 1rem;
}
/* ==========================================================================
Controls (hide/show behavior)
========================================================================== */
@@ -111,6 +174,10 @@
}
}
.media-default-skin--video .media-error[data-open] ~ .media-controls {
display: none;
}
/* Hide cursor when controls are hidden in fullscreen */
@media (pointer: fine) {
.media-default-skin--video:fullscreen:has(.media-controls:not([data-visible])) {