waveframe 0.2.2 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
File without changes
@@ -1,20 +0,0 @@
1
- import { default as React } from 'react';
2
- /**
3
- * Props for the ArtworkOverlay component.
4
- */
5
- interface ArtworkOverlayProps {
6
- /** The URL or Object URL of the artwork image */
7
- artworkUrl?: string;
8
- /** The title of the track (used for alt text) */
9
- title?: string;
10
- /** Whether the artwork is currently being processed or the audio is analyzing */
11
- isLoading?: boolean;
12
- }
13
- /**
14
- * A purely visual component for displaying track artwork.
15
- *
16
- * It handles loading states with a blur effect and provides a consistent
17
- * container for the track image.
18
- */
19
- export declare const ArtworkOverlay: React.FC<ArtworkOverlayProps>;
20
- export {};
@@ -1,29 +0,0 @@
1
- import { default as React } from 'react';
2
- import { WaveframeTheme, TrackInfo, WaveformConfig } from '../types.js';
3
- interface SettingsPanelProps {
4
- theme: WaveframeTheme;
5
- trackInfo: TrackInfo;
6
- config: WaveformConfig;
7
- scale: number;
8
- engineState: {
9
- isPlaying: boolean;
10
- volume: number;
11
- muted: boolean;
12
- isAnalyzing: boolean;
13
- };
14
- onAnalyze: () => void;
15
- onThemeChange: (theme: Partial<WaveframeTheme>) => void;
16
- onTrackChange: (track: Partial<TrackInfo>) => void;
17
- onConfigChange: (config: Partial<WaveformConfig>) => void;
18
- onScaleChange: (scale: number) => void;
19
- onTogglePreset: (type: 'light' | 'dark') => void;
20
- onClearPeaks: () => void;
21
- onFileUpload: (e: React.ChangeEvent<HTMLInputElement>) => void;
22
- onArtworkUpload: (e: React.ChangeEvent<HTMLInputElement>) => void;
23
- onReset: () => void;
24
- onTogglePlay: () => void;
25
- onSetVolume: (v: number) => void;
26
- onSetMuted: (m: boolean) => void;
27
- }
28
- export declare const SettingsPanel: React.FC<SettingsPanelProps>;
29
- export {};
@@ -1,15 +0,0 @@
1
- import { default as React } from 'react';
2
- interface WaveformProps {
3
- peaks: number[];
4
- currentTime: number;
5
- duration: number;
6
- waveColor: string;
7
- progressColor: string;
8
- height: number;
9
- onSeek: (percentage: number) => void;
10
- resolution?: number | 'auto';
11
- barWidth?: number;
12
- barGap?: number;
13
- }
14
- export declare const Waveform: React.FC<WaveformProps>;
15
- export {};
@@ -1,75 +0,0 @@
1
- /**
2
- * Defines the core color palette for the Waveframe component.
3
- *
4
- * @example
5
- * ```tsx
6
- * const darkTheme: WaveframeTheme = {
7
- * bg: '#111827',
8
- * primary: '#ec4899',
9
- * text: '#f9fafb',
10
- * border: '#1f2937'
11
- * };
12
- * ```
13
- */
14
- export interface WaveframeTheme {
15
- /** The main background color of the player */
16
- bg: string;
17
- /** The primary accent color (used for play button and progress) */
18
- primary: string;
19
- /** The color of the text elements (title, artist, time) */
20
- text: string;
21
- /** The color of borders and dividers */
22
- border: string;
23
- }
24
- /**
25
- * Metadata associated with an audio track.
26
- *
27
- * @example
28
- * ```tsx
29
- * const track: TrackInfo = {
30
- * title: 'Electronic Sunset',
31
- * artist: 'Digital Nomad',
32
- * artwork: 'https://example.com/art.jpg', // or a Blob object
33
- * audioUrl: 'https://example.com/audio.mp3'
34
- * };
35
- * ```
36
- */
37
- export interface TrackInfo {
38
- /** The title of the track */
39
- title: string;
40
- /** The artist of the track */
41
- artist: string;
42
- /** The artwork source (URL string or Blob/File object) */
43
- artwork: string | Blob;
44
- /** The URL to the actual audio file */
45
- audioUrl: string;
46
- }
47
- /**
48
- * Defines the resolution of the waveform.
49
- * - `number`: A fixed number of bars to render.
50
- * - `'auto'`: Compute the number of bars dynamically based on the container width.
51
- */
52
- export type Resolution = number | 'auto';
53
- /**
54
- * Configuration options for how the waveform is rendered visually.
55
- *
56
- * @example
57
- * ```tsx
58
- * const config: WaveformConfig = {
59
- * resolution: 'auto',
60
- * barWidth: 2,
61
- * barGap: 1,
62
- * height: 100
63
- * };
64
- * ```
65
- */
66
- export interface WaveformConfig {
67
- /** The number of bars to render, or 'auto' to compute based on container width */
68
- resolution: Resolution;
69
- /** The width of each individual bar in pixels */
70
- barWidth: number;
71
- /** The spacing between each bar in pixels */
72
- barGap: number;
73
- /** The total height of the waveform in pixels */
74
- height: number;
75
- }
@@ -1,33 +0,0 @@
1
- /**
2
- * Loads audio from a URL, decodes it, and generates a specific number of peaks (samples).
3
- *
4
- * This is a high-level utility function that internally manages a `PeakAnalyzer` instance.
5
- *
6
- * @param audioUrl The URL of the audio file to analyze.
7
- * @param samples The number of peaks (bars) to generate. Defaults to 512.
8
- * @returns A promise resolving to an array of normalized peak values (0 to 1).
9
- *
10
- * @example
11
- * ```typescript
12
- * const peaks = await generatePeaks('https://example.com/audio.mp3', 256);
13
- * ```
14
- */
15
- export declare const generatePeaks: (audioUrl: string, samples?: number) => Promise<number[]>;
16
- /**
17
- * Loads audio into memory as a Blob and returns a temporary Object URL.
18
- *
19
- * Useful for ensuring audio data is fully loaded locally before starting
20
- * playback or analysis, which can help with CORS issues or slow networks.
21
- *
22
- * @param url The URL of the remote audio file.
23
- * @returns A promise resolving to a temporary `blob:` URL.
24
- */
25
- export declare const loadAudioToMemory: (url: string) => Promise<string>;
26
- /**
27
- * Cleanup function to prevent memory leaks from Object URLs.
28
- *
29
- * Call this when a `blob:` URL is no longer needed (e.g., when the component unmounts).
30
- *
31
- * @param url The Object URL to revoke.
32
- */
33
- export declare const revokeAudioMemory: (url: string) => void;
@@ -1,13 +0,0 @@
1
- /**
2
- * Formats seconds into a M:SS string
3
- */
4
- export declare const formatTime: (seconds: number) => string;
5
- /**
6
- * Resamples an array of peaks to a target count using bucket-max or linear interpolation
7
- */
8
- export declare const resamplePeaks: (peaks: number[], targetCount: number) => number[];
9
- /**
10
- * High-performance token-based syntax highlighter for React snippets
11
- */
12
- export declare const highlightCode: (code: string) => string[];
13
- export * from './audio.js';
@@ -1,7 +0,0 @@
1
- Object.defineProperty(exports,Symbol.toStringTag,{value:`Module`});var e=Object.create,t=Object.defineProperty,n=Object.getOwnPropertyDescriptor,r=Object.getOwnPropertyNames,i=Object.getPrototypeOf,a=Object.prototype.hasOwnProperty,o=(e,t)=>()=>(t||(e((t={exports:{}}).exports,t),e=null),t.exports),s=(e,i,o,s)=>{if(i&&typeof i==`object`||typeof i==`function`)for(var c=r(i),l=0,u=c.length,d;l<u;l++)d=c[l],!a.call(e,d)&&d!==o&&t(e,d,{get:(e=>i[e]).bind(null,d),enumerable:!(s=n(i,d))||s.enumerable});return e},c=(n,r,a)=>(a=n==null?{}:e(i(n)),s(r||!n||!n.__esModule?t(a,`default`,{value:n,enumerable:!0}):a,n));let l=require(`react`);l=c(l,1);var u=class{audio;listeners=new Set;_state;constructor(){this.audio=new Audio,this._state={isPlaying:!1,currentTime:0,duration:0,volume:1,muted:!1},this.initListeners()}initListeners(){this.audio.addEventListener(`play`,()=>this.updateState({isPlaying:!0})),this.audio.addEventListener(`pause`,()=>this.updateState({isPlaying:!1})),this.audio.addEventListener(`timeupdate`,()=>this.updateState({currentTime:this.audio.currentTime})),this.audio.addEventListener(`durationchange`,()=>this.updateState({duration:this.audio.duration})),this.audio.addEventListener(`volumechange`,()=>this.updateState({volume:this.audio.volume,muted:this.audio.muted})),this.audio.addEventListener(`ended`,()=>this.updateState({isPlaying:!1}))}updateState(e){this._state={...this._state,...e},this.notify()}notify(){this.listeners.forEach(e=>e(this._state))}subscribe(e){return this.listeners.add(e),()=>this.listeners.delete(e)}get state(){return this._state}setSource(e){this.audio.src=e,this.audio.load()}play(){return this.audio.play()}pause(){this.audio.pause()}togglePlay(){this._state.isPlaying?this.pause():this.play()}seek(e){this.audio.currentTime=e}setVolume(e){this.audio.volume=e}setMuted(e){this.audio.muted=e}dispose(){this.pause(),this.audio.src=``,this.listeners.clear()}},d=class{audioCtx=null;constructor(){}getContext(){return this.audioCtx||=new(window.AudioContext||window.webkitAudioContext),this.audioCtx}async generatePeaks(e,t=512){try{let n;if(typeof e==`string`){let t=await fetch(e);if(!t.ok)throw Error(`Failed to fetch audio: ${t.statusText}`);n=await t.arrayBuffer()}else n=await e.arrayBuffer();let r=(await this.getContext().decodeAudioData(n)).getChannelData(0),i=Math.floor(r.length/t),a=[];for(let e=0;e<t;e++){let t=0,n=e*i,o=n+i;for(let e=n;e<o;e++){let n=Math.abs(r[e]);n>t&&(t=n)}a.push(t)}let o=Math.max(...a);return a.map(e=>e/(o||1))}catch(e){throw console.error(`PeakAnalyzer Error:`,e),e}}dispose(){this.audioCtx&&=(this.audioCtx.close(),null)}},f=class{player;analyzer;listeners=new Set;_state;_media=null;_objectUrl=null;constructor(){this.player=new u,this.analyzer=new d,this._state={...this.player.state,peaks:[],isAnalyzing:!1,error:null},this.player.subscribe(e=>{this.updateState({...e})})}updateState(e){this._state={...this._state,...e},this.notify()}notify(){this.listeners.forEach(e=>e(this._state))}subscribe(e){return this.listeners.add(e),()=>this.listeners.delete(e)}getSnapshot(){return this._state}revokeOldSource(){this._objectUrl&&=(URL.revokeObjectURL(this._objectUrl),null)}load(e,t){if(this._media!==e){this.revokeOldSource(),this._media=e;let n;typeof e==`string`?n=e:(this._objectUrl=URL.createObjectURL(e),n=this._objectUrl),this.player.setSource(n);let r=t&&t.length>0;this.updateState({peaks:t||[],isAnalyzing:!1,error:null}),r||this.analyze()}else t&&t!==this._state.peaks&&this.updateState({peaks:t})}async analyze(e=512){if(!this._media){this.updateState({error:`No media loaded to analyze`});return}this.updateState({isAnalyzing:!0,error:null});try{let t=await this.analyzer.generatePeaks(this._media,e);this.updateState({peaks:t,isAnalyzing:!1})}catch(e){this.updateState({isAnalyzing:!1,error:e instanceof Error?e.message:`Analysis failed`})}}togglePlay(){this.player.togglePlay()}play(){this.player.play()}pause(){this.player.pause()}seek(e){let{duration:t}=this._state;t&&this.player.seek(e*t)}setVolume(e){this.player.setVolume(e)}setMuted(e){this.player.setMuted(e)}dispose(){this.revokeOldSource(),this.player.dispose(),this.analyzer.dispose(),this.listeners.clear()}},p=e=>(0,l.useSyncExternalStore)(t=>e.subscribe(t),()=>e.getSnapshot()),m=(e,t={})=>{let{peaks:n,engine:r}=t,i=(0,l.useMemo)(()=>r||new f,[r]),a=r||i,o=p(a);return(0,l.useEffect)(()=>{e&&a.load(e,n)},[a,e,n]),(0,l.useEffect)(()=>()=>{r||i.dispose()},[i,r]),{state:o,engine:a,togglePlay:()=>a.togglePlay(),play:()=>a.play(),pause:()=>a.pause(),seek:e=>a.seek(e),setVolume:e=>a.setVolume(e),setMuted:e=>a.setMuted(e),analyze:e=>a.analyze(e)}},h=async(e,t=512)=>{let n=new d;try{return await n.generatePeaks(e,t)}finally{n.dispose()}},g=async e=>{let t=await(await fetch(e)).blob();return URL.createObjectURL(t)},_=e=>{e&&e.startsWith(`blob:`)&&URL.revokeObjectURL(e)},v=e=>isNaN(e)?`0:00`:`${Math.floor(e/60)}:${Math.floor(e%60).toString().padStart(2,`0`)}`,y=(e,t)=>{if(e.length===0)return[];if(e.length===t)return e;let n=Array(t),r=e.length/t;if(r>1)for(let i=0;i<t;i++){let t=0,a=Math.floor(i*r),o=Math.floor((i+1)*r);for(let n=a;n<o;n++)e[n]>t&&(t=e[n]);n[i]=t}else for(let i=0;i<t;i++){let t=i*r,a=Math.floor(t),o=Math.min(a+1,e.length-1),s=t-a;n[i]=e[a]+(e[o]-e[a])*s}return n},b=e=>e.split(`
2
- `).map(e=>{let t=e.replace(/&/g,`&amp;`).replace(/</g,`&lt;`).replace(/>/g,`&gt;`),n={},r=0,i=(e,t)=>{let i=`__TOKEN_${r++}__`;return n[i]=`<span class="${t}">${e}</span>`,i};return t=t.replace(/("(?:[^"\\]|\\.)*")/g,e=>i(e,`text-[#ce9178]`)),t=t.replace(/\b(\d+(\.\d+)?)\b/g,e=>i(e,`text-[#b5cea8]`)),t=t.replace(/\b(WaveframePlayer)\b/g,e=>i(e,`text-[#4ec9b0]`)),t=t.replace(/\b([a-z][a-zA-Z0-9]+)(?==)/g,e=>i(e,`text-[#9cdcfe]`)),t=t.replace(/(&lt;|&gt;|\{|\}|\/|:|,)/g,`<span class="text-gray-500">$1</span>`),Object.entries(n).forEach(([e,n])=>{t=t.replace(e,n)}),t}),x=(e,t)=>(0,l.useMemo)(()=>y(e,t),[e,t]),S=e=>{let[t,n]=(0,l.useState)(0);return(0,l.useEffect)(()=>{if(!e.current)return;let t=new ResizeObserver(e=>{for(let t of e)n(t.contentRect.width)});return t.observe(e.current),()=>t.disconnect()},[e]),t},C=o((e=>{var t=Symbol.for(`react.transitional.element`),n=Symbol.for(`react.fragment`);function r(e,n,r){var i=null;if(r!==void 0&&(i=``+r),n.key!==void 0&&(i=``+n.key),`key`in n)for(var a in r={},n)a!==`key`&&(r[a]=n[a]);else r=n;return n=r.ref,{$$typeof:t,type:e,key:i,ref:n===void 0?null:n,props:r}}e.Fragment=n,e.jsx=r,e.jsxs=r})),w=o((e=>{process.env.NODE_ENV!==`production`&&(function(){function t(e){if(e==null)return null;if(typeof e==`function`)return e.$$typeof===O?null:e.displayName||e.name||null;if(typeof e==`string`)return e;switch(e){case _:return`Fragment`;case y:return`Profiler`;case v:return`StrictMode`;case C:return`Suspense`;case w:return`SuspenseList`;case D:return`Activity`}if(typeof e==`object`)switch(typeof e.tag==`number`&&console.error(`Received an unexpected object in getComponentNameFromType(). This is likely a bug in React. Please file an issue.`),e.$$typeof){case g:return`Portal`;case x:return e.displayName||`Context`;case b:return(e._context.displayName||`Context`)+`.Consumer`;case S:var n=e.render;return e=e.displayName,e||=(e=n.displayName||n.name||``,e===``?`ForwardRef`:`ForwardRef(`+e+`)`),e;case T:return n=e.displayName||null,n===null?t(e.type)||`Memo`:n;case E:n=e._payload,e=e._init;try{return t(e(n))}catch{}}return null}function n(e){return``+e}function r(e){try{n(e);var t=!1}catch{t=!0}if(t){t=console;var r=t.error,i=typeof Symbol==`function`&&Symbol.toStringTag&&e[Symbol.toStringTag]||e.constructor.name||`Object`;return r.call(t,`The provided key is an unsupported type %s. This value must be coerced to a string before using it here.`,i),n(e)}}function i(e){if(e===_)return`<>`;if(typeof e==`object`&&e&&e.$$typeof===E)return`<...>`;try{var n=t(e);return n?`<`+n+`>`:`<...>`}catch{return`<...>`}}function a(){var e=k.A;return e===null?null:e.getOwner()}function o(){return Error(`react-stack-top-frame`)}function s(e){if(A.call(e,`key`)){var t=Object.getOwnPropertyDescriptor(e,`key`).get;if(t&&t.isReactWarning)return!1}return e.key!==void 0}function c(e,t){function n(){N||(N=!0,console.error("%s: `key` is not a prop. Trying to access it will result in `undefined` being returned. If you need to access the same value within the child component, you should pass it as a different prop. (https://react.dev/link/special-props)",t))}n.isReactWarning=!0,Object.defineProperty(e,`key`,{get:n,configurable:!0})}function l(){var e=t(this.type);return P[e]||(P[e]=!0,console.error(`Accessing element.ref was removed in React 19. ref is now a regular prop. It will be removed from the JSX Element type in a future release.`)),e=this.props.ref,e===void 0?null:e}function u(e,t,n,r,i,a){var o=n.ref;return e={$$typeof:h,type:e,key:t,props:n,_owner:r},(o===void 0?null:o)===null?Object.defineProperty(e,`ref`,{enumerable:!1,value:null}):Object.defineProperty(e,`ref`,{enumerable:!1,get:l}),e._store={},Object.defineProperty(e._store,`validated`,{configurable:!1,enumerable:!1,writable:!0,value:0}),Object.defineProperty(e,`_debugInfo`,{configurable:!1,enumerable:!1,writable:!0,value:null}),Object.defineProperty(e,`_debugStack`,{configurable:!1,enumerable:!1,writable:!0,value:i}),Object.defineProperty(e,`_debugTask`,{configurable:!1,enumerable:!1,writable:!0,value:a}),Object.freeze&&(Object.freeze(e.props),Object.freeze(e)),e}function d(e,n,i,o,l,d){var p=n.children;if(p!==void 0)if(o)if(j(p)){for(o=0;o<p.length;o++)f(p[o]);Object.freeze&&Object.freeze(p)}else console.error(`React.jsx: Static children should always be an array. You are likely explicitly calling React.jsxs or React.jsxDEV. Use the Babel transform instead.`);else f(p);if(A.call(n,`key`)){p=t(e);var m=Object.keys(n).filter(function(e){return e!==`key`});o=0<m.length?`{key: someKey, `+m.join(`: ..., `)+`: ...}`:`{key: someKey}`,L[p+o]||(m=0<m.length?`{`+m.join(`: ..., `)+`: ...}`:`{}`,console.error(`A props object containing a "key" prop is being spread into JSX:
3
- let props = %s;
4
- <%s {...props} />
5
- React keys must be passed directly to JSX without using spread:
6
- let props = %s;
7
- <%s key={someKey} {...props} />`,o,p,m,p),L[p+o]=!0)}if(p=null,i!==void 0&&(r(i),p=``+i),s(n)&&(r(n.key),p=``+n.key),`key`in n)for(var h in i={},n)h!==`key`&&(i[h]=n[h]);else i=n;return p&&c(i,typeof e==`function`?e.displayName||e.name||`Unknown`:e),u(e,p,i,a(),l,d)}function f(e){p(e)?e._store&&(e._store.validated=1):typeof e==`object`&&e&&e.$$typeof===E&&(e._payload.status===`fulfilled`?p(e._payload.value)&&e._payload.value._store&&(e._payload.value._store.validated=1):e._store&&(e._store.validated=1))}function p(e){return typeof e==`object`&&!!e&&e.$$typeof===h}var m=require(`react`),h=Symbol.for(`react.transitional.element`),g=Symbol.for(`react.portal`),_=Symbol.for(`react.fragment`),v=Symbol.for(`react.strict_mode`),y=Symbol.for(`react.profiler`),b=Symbol.for(`react.consumer`),x=Symbol.for(`react.context`),S=Symbol.for(`react.forward_ref`),C=Symbol.for(`react.suspense`),w=Symbol.for(`react.suspense_list`),T=Symbol.for(`react.memo`),E=Symbol.for(`react.lazy`),D=Symbol.for(`react.activity`),O=Symbol.for(`react.client.reference`),k=m.__CLIENT_INTERNALS_DO_NOT_USE_OR_WARN_USERS_THEY_CANNOT_UPGRADE,A=Object.prototype.hasOwnProperty,j=Array.isArray,M=console.createTask?console.createTask:function(){return null};m={react_stack_bottom_frame:function(e){return e()}};var N,P={},F=m.react_stack_bottom_frame.bind(m,o)(),I=M(i(o)),L={};e.Fragment=_,e.jsx=function(e,t,n){var r=1e4>k.recentlyCreatedOwnerStacks++;return d(e,t,n,!1,r?Error(`react-stack-top-frame`):F,r?M(i(e)):I)},e.jsxs=function(e,t,n){var r=1e4>k.recentlyCreatedOwnerStacks++;return d(e,t,n,!0,r?Error(`react-stack-top-frame`):F,r?M(i(e)):I)}})()})),T=o(((e,t)=>{process.env.NODE_ENV===`production`?t.exports=C():t.exports=w()}))(),E=(0,l.memo)(({artworkUrl:e,title:t,isLoading:n})=>(0,T.jsxs)(`div`,{className:`relative flex-shrink-0 w-32 h-32 md:w-40 md:h-40 overflow-hidden rounded-[var(--wf-artwork-rounded,0.75rem)] shadow-lg group/artwork`,children:[(0,T.jsx)(`div`,{className:`w-full h-full transition-all duration-700 ${n?`blur-md scale-110`:``}`,children:e?(0,T.jsx)(`img`,{src:e,alt:t,className:`w-full h-full object-cover transition-transform duration-500 group-hover/artwork:scale-110`}):(0,T.jsx)(`div`,{className:`w-full h-full bg-gradient-to-br from-[var(--wf-placeholder-from,#fb923c)] to-[var(--wf-placeholder-to,#ec4899)] flex items-center justify-center`,children:(0,T.jsx)(`svg`,{className:`w-16 h-16 text-white opacity-50`,fill:`currentColor`,viewBox:`0 0 24 24`,children:(0,T.jsx)(`path`,{d:`M12 3v10.55c-.59-.34-1.27-.55-2-.55-2.21 0-4 1.79-4 4s1.79 4 4 4 4-1.79 4-4V7h4V3h-6z`})})})}),n&&(0,T.jsx)(`div`,{className:`absolute inset-0 flex items-center justify-center bg-black/10 backdrop-blur-[1px]`,children:(0,T.jsx)(`div`,{className:`w-8 h-8 border-4 border-white/30 border-t-white rounded-full animate-spin`})})]}));E.displayName=`ArtworkOverlay`;var D=(0,l.memo)(({peaks:e,currentTime:t,duration:n,waveColor:r,progressColor:i,height:a,onSeek:o,resolution:s=`auto`,barWidth:c=2,barGap:u=1})=>{let d=(0,l.useRef)(null),f=(0,l.useRef)(null),p=(0,l.useRef)(null),m=S(p);(0,l.useEffect)(()=>{let t=d.current,n=f.current;if(!t||!n)return;let a=t.getContext(`2d`),o=n.getContext(`2d`);if(!a||!o)return;let l=window.devicePixelRatio||1,p=t.getBoundingClientRect(),m=p.width*l,h=p.height*l;[t,n].forEach(e=>{(e.width!==m||e.height!==h)&&(e.width=m,e.height=h)}),(()=>{if(e.length===0)return;let{width:n,height:d}=t;a.clearRect(0,0,n,d),o.clearRect(0,0,n,d);let f=n/e.length,p=typeof s==`number`?f*.7:c*l,m=typeof s==`number`?f*.3:u*l;a.lineCap=`round`,a.lineWidth=p,o.lineCap=`round`,o.lineWidth=p,e.forEach((e,t)=>{let n=t*(p+m)+p/2,s=e*d*.8,c=(d-s)/2,l=c+s;a.beginPath(),a.strokeStyle=r,a.moveTo(n,c),a.lineTo(n,l),a.stroke(),o.beginPath(),o.strokeStyle=i,o.moveTo(n,c),o.lineTo(n,l),o.stroke()})})()},[e,r,i,s,c,u,a]);let h=e=>{if(p.current&&n){let t=p.current.getBoundingClientRect(),n=e.clientX-t.left;o(Math.max(0,Math.min(1,n/t.width)))}},g=n?t/n*100:0;return(0,T.jsxs)(`div`,{ref:p,className:`relative w-full cursor-pointer overflow-hidden`,style:{height:`${a}px`},onClick:h,children:[(0,T.jsx)(`canvas`,{ref:d,className:`absolute inset-0 w-full h-full`}),(0,T.jsx)(`div`,{className:`absolute inset-0 h-full overflow-hidden transition-[width] duration-100 ease-linear pointer-events-none`,style:{width:`${g}%`},children:(0,T.jsx)(`canvas`,{ref:f,className:`absolute h-full`,style:{width:`${m}px`}})})]})});D.displayName=`Waveform`;var O=(0,l.memo)(({media:e,peaks:t,artwork:n,title:r,artist:i,waveColor:a,progressColor:o,height:s=80,className:c=``,style:u,resolution:d=`auto`,barWidth:f=2,barGap:p=1,theme:h,engine:g})=>{let{state:_,togglePlay:y,seek:b}=m(e,{peaks:t,engine:g}),{isPlaying:C,currentTime:w,duration:O,peaks:k,isAnalyzing:A}=_,[j,M]=(0,l.useState)(typeof n==`string`?n:void 0);(0,l.useEffect)(()=>{if(n instanceof Blob){let e=URL.createObjectURL(n);return M(e),()=>URL.revokeObjectURL(e)}else M(n)},[n]);let N=(0,l.useRef)(null),P=S(N),F=x(k,(0,l.useMemo)(()=>typeof d==`number`?d:P>0?Math.max(1,Math.floor(P/(f+p))):k.length||1,[d,P,f,p,k.length])),I=(0,l.useMemo)(()=>a||(h?h.bg===`#ffffff`?`#e5e7eb`:`#374151`:`#e5e7eb`),[a,h]),L=o||h?.primary||`#3b82f6`,R=(0,l.useMemo)(()=>({"--wf-bg-color":h?.bg||`white`,"--wf-border-color":h?.border||`#f3f4f6`,"--wf-title-color":h?.text||`#111827`,"--wf-artist-color":h?.text||`#6b7280`,"--wf-time-color":h?.text||`#9ca3af`,"--wf-play-btn-bg":h?.primary||`#3b82f6`,"--wf-placeholder-from":h?.primary||`#fb923c`,"--wf-placeholder-to":h?.bg||`#ec4899`,...u}),[h,u]);return(0,T.jsxs)(`div`,{className:`group relative flex flex-col md:flex-row items-stretch gap-6 p-6 bg-[var(--wf-bg-color,white)] border border-[var(--wf-border-color,#f3f4f6)] rounded-[var(--wf-rounded,1rem)] shadow-xl hover:shadow-2xl transition-all duration-300 overflow-hidden ${c}`,style:R,children:[(0,T.jsx)(E,{artworkUrl:j,title:r,isLoading:A}),(0,T.jsxs)(`div`,{className:`flex-1 w-full flex flex-col min-w-0`,children:[(0,T.jsxs)(`div`,{className:`flex items-center gap-4 mb-6`,children:[(0,T.jsx)(`button`,{onClick:y,className:`w-12 h-12 md:w-14 md:h-14 flex-shrink-0 flex items-center justify-center rounded-full bg-[var(--wf-play-btn-bg,#3b82f6)] text-white shadow-[0_4px_12px_rgba(0,0,0,0.15)] hover:shadow-[0_6px_16px_rgba(0,0,0,0.2)] transition-all hover:scale-105 active:scale-95 cursor-pointer border-none outline-none group/play`,children:C?(0,T.jsx)(`svg`,{className:`w-6 h-6 md:w-7 md:h-7`,fill:`currentColor`,viewBox:`0 0 24 24`,children:(0,T.jsx)(`path`,{d:`M6 19h4V5H6v14zm8-14v14h4V5h-4z`})}):(0,T.jsx)(`svg`,{className:`w-6 h-6 md:w-7 md:h-7 ml-1`,fill:`currentColor`,viewBox:`0 0 24 24`,children:(0,T.jsx)(`path`,{d:`M8 5v14l11-7z`})})}),(0,T.jsxs)(`div`,{className:`flex-1 flex flex-col min-w-0`,children:[(0,T.jsxs)(`div`,{className:`flex items-center justify-between gap-4`,children:[i&&(0,T.jsx)(`p`,{className:`text-[10px] md:text-xs font-bold uppercase text-[var(--wf-artist-color,#6b7280)] opacity-60 tracking-[0.1em] line-clamp-1`,children:i}),(0,T.jsxs)(`div`,{className:`text-[10px] font-mono text-[var(--wf-time-color,#9ca3af)] tabular-nums flex-shrink-0`,children:[v(w),` / `,v(O)]})]}),r&&(0,T.jsx)(`h3`,{className:`text-lg md:text-xl font-black text-[var(--wf-title-color,#111827)] tracking-tight line-clamp-1 mt-0.5 leading-tight`,children:r})]})]}),(0,T.jsx)(`div`,{className:`mt-auto`,ref:N,children:(0,T.jsx)(D,{peaks:F,currentTime:w,duration:O,waveColor:I,progressColor:L,height:s,onSeek:b,resolution:d,barWidth:f,barGap:p})})]})]})});O.displayName=`WaveframePlayer`,exports.PeakAnalyzer=d,exports.PlayerCore=u,exports.WaveframeEngine=f,exports.WaveframePlayer=O,exports.formatTime=v,exports.generatePeaks=h,exports.highlightCode=b,exports.loadAudioToMemory=g,exports.resamplePeaks=y,exports.revokeAudioMemory=_,exports.useWaveframeStore=p;
@@ -1,3 +0,0 @@
1
- /*! tailwindcss v4.3.0 | MIT License | https://tailwindcss.com */
2
- @layer properties{@supports (((-webkit-hyphens:none)) and (not (margin-trim:inline))) or ((-moz-orient:inline) and (not (color:rgb(from red r g b)))){*,:before,:after,::backdrop{--tw-scale-x:1;--tw-scale-y:1;--tw-scale-z:1;--tw-border-style:solid;--tw-gradient-position:initial;--tw-gradient-from:#0000;--tw-gradient-via:#0000;--tw-gradient-to:#0000;--tw-gradient-stops:initial;--tw-gradient-via-stops:initial;--tw-gradient-from-position:0%;--tw-gradient-via-position:50%;--tw-gradient-to-position:100%;--tw-leading:initial;--tw-font-weight:initial;--tw-tracking:initial;--tw-ordinal:initial;--tw-slashed-zero:initial;--tw-numeric-figure:initial;--tw-numeric-spacing:initial;--tw-numeric-fraction:initial;--tw-shadow:0 0 #0000;--tw-shadow-color:initial;--tw-shadow-alpha:100%;--tw-inset-shadow:0 0 #0000;--tw-inset-shadow-color:initial;--tw-inset-shadow-alpha:100%;--tw-ring-color:initial;--tw-ring-shadow:0 0 #0000;--tw-inset-ring-color:initial;--tw-inset-ring-shadow:0 0 #0000;--tw-ring-inset:initial;--tw-ring-offset-width:0px;--tw-ring-offset-color:#fff;--tw-ring-offset-shadow:0 0 #0000;--tw-blur:initial;--tw-brightness:initial;--tw-contrast:initial;--tw-grayscale:initial;--tw-hue-rotate:initial;--tw-invert:initial;--tw-opacity:initial;--tw-saturate:initial;--tw-sepia:initial;--tw-drop-shadow:initial;--tw-drop-shadow-color:initial;--tw-drop-shadow-alpha:100%;--tw-drop-shadow-size:initial;--tw-backdrop-blur:initial;--tw-backdrop-brightness:initial;--tw-backdrop-contrast:initial;--tw-backdrop-grayscale:initial;--tw-backdrop-hue-rotate:initial;--tw-backdrop-invert:initial;--tw-backdrop-opacity:initial;--tw-backdrop-saturate:initial;--tw-backdrop-sepia:initial;--tw-duration:initial;--tw-ease:initial}}}@layer theme{:root,:host{--font-sans:ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji";--font-mono:ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace;--color-red-50:oklch(97.1% .013 17.38);--color-red-200:oklch(88.5% .062 18.334);--color-red-300:oklch(80.8% .114 19.571);--color-red-600:oklch(57.7% .245 27.325);--color-orange-50:oklch(98% .016 73.684);--color-orange-100:oklch(95.4% .038 75.164);--color-orange-200:oklch(90.1% .076 70.697);--color-orange-600:oklch(64.6% .222 41.116);--color-green-50:oklch(98.2% .018 155.826);--color-green-100:oklch(96.2% .044 156.743);--color-green-200:oklch(92.5% .084 155.995);--color-green-400:oklch(79.2% .209 151.711);--color-green-600:oklch(62.7% .194 149.214);--color-blue-50:oklch(97% .014 254.604);--color-blue-200:oklch(88.2% .059 254.128);--color-blue-300:oklch(80.9% .105 251.813);--color-blue-400:oklch(70.7% .165 254.624);--color-blue-500:oklch(62.3% .214 259.815);--color-blue-600:oklch(54.6% .245 262.881);--color-blue-700:oklch(48.8% .243 264.376);--color-gray-50:oklch(98.5% .002 247.839);--color-gray-100:oklch(96.7% .003 264.542);--color-gray-200:oklch(92.8% .006 264.531);--color-gray-300:oklch(87.2% .01 258.338);--color-gray-400:oklch(70.7% .022 261.325);--color-gray-500:oklch(55.1% .027 264.364);--color-gray-600:oklch(44.6% .03 256.802);--color-gray-700:oklch(37.3% .034 259.733);--color-gray-800:oklch(27.8% .033 256.848);--color-gray-900:oklch(21% .034 264.665);--color-black:#000;--color-white:#fff;--spacing:.25rem;--container-4xl:56rem;--container-5xl:64rem;--text-xs:.75rem;--text-xs--line-height:calc(1 / .75);--text-sm:.875rem;--text-sm--line-height:calc(1.25 / .875);--text-lg:1.125rem;--text-lg--line-height:calc(1.75 / 1.125);--text-xl:1.25rem;--text-xl--line-height:calc(1.75 / 1.25);--font-weight-medium:500;--font-weight-bold:700;--font-weight-black:900;--tracking-tighter:-.05em;--tracking-tight:-.025em;--tracking-wide:.025em;--tracking-widest:.1em;--leading-tight:1.25;--leading-relaxed:1.625;--radius-lg:.5rem;--radius-xl:.75rem;--ease-out:cubic-bezier(0, 0, .2, 1);--animate-spin:spin 1s linear infinite;--blur-md:12px;--blur-xl:24px;--default-transition-duration:.15s;--default-transition-timing-function:cubic-bezier(.4, 0, .2, 1);--default-font-family:var(--font-sans);--default-mono-font-family:var(--font-mono)}}@layer base{*,:after,:before,::backdrop{box-sizing:border-box;border:0 solid;margin:0;padding:0}::file-selector-button{box-sizing:border-box;border:0 solid;margin:0;padding:0}html,:host{-webkit-text-size-adjust:100%;tab-size:4;line-height:1.5;font-family:var(--default-font-family,ui-sans-serif, system-ui, sans-serif, "Apple Color Emoji", "Segoe UI Emoji", "Segoe UI Symbol", "Noto Color Emoji");font-feature-settings:var(--default-font-feature-settings,normal);font-variation-settings:var(--default-font-variation-settings,normal);-webkit-tap-highlight-color:transparent}hr{height:0;color:inherit;border-top-width:1px}abbr:where([title]){-webkit-text-decoration:underline dotted;text-decoration:underline dotted}h1,h2,h3,h4,h5,h6{font-size:inherit;font-weight:inherit}a{color:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;-webkit-text-decoration:inherit;text-decoration:inherit}b,strong{font-weight:bolder}code,kbd,samp,pre{font-family:var(--default-mono-font-family,ui-monospace, SFMono-Regular, Menlo, Monaco, Consolas, "Liberation Mono", "Courier New", monospace);font-feature-settings:var(--default-mono-font-feature-settings,normal);font-variation-settings:var(--default-mono-font-variation-settings,normal);font-size:1em}small{font-size:80%}sub,sup{vertical-align:baseline;font-size:75%;line-height:0;position:relative}sub{bottom:-.25em}sup{top:-.5em}table{text-indent:0;border-color:inherit;border-collapse:collapse}:-moz-focusring{outline:auto}progress{vertical-align:baseline}summary{display:list-item}ol,ul,menu{list-style:none}img,svg,video,canvas,audio,iframe,embed,object{vertical-align:middle;display:block}img,video{max-width:100%;height:auto}button,input,select,optgroup,textarea{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}::file-selector-button{font:inherit;font-feature-settings:inherit;font-variation-settings:inherit;letter-spacing:inherit;color:inherit;opacity:1;background-color:#0000;border-radius:0}:where(select:is([multiple],[size])) optgroup{font-weight:bolder}:where(select:is([multiple],[size])) optgroup option{padding-inline-start:20px}::file-selector-button{margin-inline-end:4px}::placeholder{opacity:1}@supports (not ((-webkit-appearance:-apple-pay-button))) or (contain-intrinsic-size:1px){::placeholder{color:currentColor}@supports (color:color-mix(in lab, red, red)){::placeholder{color:color-mix(in oklab, currentcolor 50%, transparent)}}}textarea{resize:vertical}::-webkit-search-decoration{-webkit-appearance:none}::-webkit-date-and-time-value{min-height:1lh;text-align:inherit}::-webkit-datetime-edit{display:inline-flex}::-webkit-datetime-edit-fields-wrapper{padding:0}::-webkit-datetime-edit{padding-block:0}::-webkit-datetime-edit-year-field{padding-block:0}::-webkit-datetime-edit-month-field{padding-block:0}::-webkit-datetime-edit-day-field{padding-block:0}::-webkit-datetime-edit-hour-field{padding-block:0}::-webkit-datetime-edit-minute-field{padding-block:0}::-webkit-datetime-edit-second-field{padding-block:0}::-webkit-datetime-edit-millisecond-field{padding-block:0}::-webkit-datetime-edit-meridiem-field{padding-block:0}::-webkit-calendar-picker-indicator{line-height:1}:-moz-ui-invalid{box-shadow:none}button,input:where([type=button],[type=reset],[type=submit]){appearance:button}::file-selector-button{appearance:button}::-webkit-inner-spin-button{height:auto}::-webkit-outer-spin-button{height:auto}[hidden]:where(:not([hidden=until-found])){display:none!important}}@layer components;@layer utilities{.pointer-events-none{pointer-events:none}.absolute{position:absolute}.fixed{position:fixed}.relative{position:relative}.inset-0{inset:calc(var(--spacing) * 0)}.-top-1\/2{top:-50%}.top-0{top:calc(var(--spacing) * 0)}.right-0{right:calc(var(--spacing) * 0)}.-left-1\/2{left:-50%}.left-0{left:calc(var(--spacing) * 0)}.z-20{z-index:20}.container{width:100%}@media (width>=40rem){.container{max-width:40rem}}@media (width>=48rem){.container{max-width:48rem}}@media (width>=64rem){.container{max-width:64rem}}@media (width>=80rem){.container{max-width:80rem}}@media (width>=96rem){.container{max-width:96rem}}.mx-4{margin-inline:calc(var(--spacing) * 4)}.mt-0\.5{margin-top:calc(var(--spacing) * .5)}.mt-2{margin-top:calc(var(--spacing) * 2)}.mt-4{margin-top:calc(var(--spacing) * 4)}.mt-32{margin-top:calc(var(--spacing) * 32)}.mt-auto{margin-top:auto}.mr-4{margin-right:calc(var(--spacing) * 4)}.mb-4{margin-bottom:calc(var(--spacing) * 4)}.mb-6{margin-bottom:calc(var(--spacing) * 6)}.ml-1{margin-left:calc(var(--spacing) * 1)}.line-clamp-1{-webkit-line-clamp:1;-webkit-box-orient:vertical;display:-webkit-box;overflow:hidden}.contents{display:contents}.flex{display:flex}.grid{display:grid}.hidden{display:none}.inline-block{display:inline-block}.h-1\.5{height:calc(var(--spacing) * 1.5)}.h-4{height:calc(var(--spacing) * 4)}.h-5{height:calc(var(--spacing) * 5)}.h-6{height:calc(var(--spacing) * 6)}.h-8{height:calc(var(--spacing) * 8)}.h-9{height:calc(var(--spacing) * 9)}.h-12{height:calc(var(--spacing) * 12)}.h-16{height:calc(var(--spacing) * 16)}.h-32{height:calc(var(--spacing) * 32)}.h-\[200\%\]{height:200%}.h-full{height:100%}.h-screen{height:100vh}.min-h-screen{min-height:100vh}.w-4{width:calc(var(--spacing) * 4)}.w-5{width:calc(var(--spacing) * 5)}.w-6{width:calc(var(--spacing) * 6)}.w-8{width:calc(var(--spacing) * 8)}.w-9{width:calc(var(--spacing) * 9)}.w-12{width:calc(var(--spacing) * 12)}.w-16{width:calc(var(--spacing) * 16)}.w-20{width:calc(var(--spacing) * 20)}.w-32{width:calc(var(--spacing) * 32)}.w-\[200\%\]{width:200%}.w-full{width:100%}.w-px{width:1px}.max-w-4xl{max-width:var(--container-4xl)}.max-w-5xl{max-width:var(--container-5xl)}.min-w-0{min-width:calc(var(--spacing) * 0)}.flex-1{flex:1}.flex-shrink{flex-shrink:1}.flex-shrink-0{flex-shrink:0}.flex-grow{flex-grow:1}.scale-110{--tw-scale-x:110%;--tw-scale-y:110%;--tw-scale-z:110%;scale:var(--tw-scale-x) var(--tw-scale-y)}.animate-spin{animation:var(--animate-spin)}.cursor-default{cursor:default}.cursor-not-allowed{cursor:not-allowed}.cursor-pointer{cursor:pointer}.appearance-none{appearance:none}.flex-col{flex-direction:column}.items-center{align-items:center}.items-stretch{align-items:stretch}.justify-between{justify-content:space-between}.justify-center{justify-content:center}.justify-start{justify-content:flex-start}.gap-1{gap:calc(var(--spacing) * 1)}.gap-2{gap:calc(var(--spacing) * 2)}.gap-3{gap:calc(var(--spacing) * 3)}.gap-4{gap:calc(var(--spacing) * 4)}.gap-5{gap:calc(var(--spacing) * 5)}.gap-6{gap:calc(var(--spacing) * 6)}.gap-8{gap:calc(var(--spacing) * 8)}.gap-12{gap:calc(var(--spacing) * 12)}.overflow-hidden{overflow:hidden}.overflow-x-auto{overflow-x:auto}.overflow-y-auto{overflow-y:auto}.rounded{border-radius:.25rem}.rounded-\[var\(--wf-artwork-rounded\,0\.75rem\)\]{border-radius:var(--wf-artwork-rounded,.75rem)}.rounded-\[var\(--wf-rounded\,1rem\)\]{border-radius:var(--wf-rounded,1rem)}.rounded-full{border-radius:3.40282e38px}.rounded-lg{border-radius:var(--radius-lg)}.rounded-xl{border-radius:var(--radius-xl)}.border{border-style:var(--tw-border-style);border-width:1px}.border-4{border-style:var(--tw-border-style);border-width:4px}.border-t{border-top-style:var(--tw-border-style);border-top-width:1px}.border-b{border-bottom-style:var(--tw-border-style);border-bottom-width:1px}.border-l{border-left-style:var(--tw-border-style);border-left-width:1px}.border-dashed{--tw-border-style:dashed;border-style:dashed}.border-none{--tw-border-style:none;border-style:none}.border-\[\#333\]{border-color:#333}.border-\[var\(--wf-border-color\,\#f3f4f6\)\]{border-color:var(--wf-border-color,#f3f4f6)}.border-blue-200{border-color:var(--color-blue-200)}.border-gray-100{border-color:var(--color-gray-100)}.border-gray-200{border-color:var(--color-gray-200)}.border-gray-200\/50{border-color:#e5e7eb80}@supports (color:color-mix(in lab, red, red)){.border-gray-200\/50{border-color:color-mix(in oklab, var(--color-gray-200) 50%, transparent)}}.border-gray-300{border-color:var(--color-gray-300)}.border-gray-900{border-color:var(--color-gray-900)}.border-green-200{border-color:var(--color-green-200)}.border-orange-200{border-color:var(--color-orange-200)}.border-red-200{border-color:var(--color-red-200)}.border-white\/30{border-color:#ffffff4d}@supports (color:color-mix(in lab, red, red)){.border-white\/30{border-color:color-mix(in oklab, var(--color-white) 30%, transparent)}}.border-t-white{border-top-color:var(--color-white)}.bg-\[\#1e1e1e\]{background-color:#1e1e1e}.bg-\[\#252526\]{background-color:#252526}.bg-\[var\(--wf-bg-color\,white\)\]{background-color:var(--wf-bg-color,white)}.bg-\[var\(--wf-play-btn-bg\,\#3b82f6\)\]{background-color:var(--wf-play-btn-bg,#3b82f6)}.bg-black\/10{background-color:#0000001a}@supports (color:color-mix(in lab, red, red)){.bg-black\/10{background-color:color-mix(in oklab, var(--color-black) 10%, transparent)}}.bg-blue-50{background-color:var(--color-blue-50)}.bg-blue-600{background-color:var(--color-blue-600)}.bg-gray-50{background-color:var(--color-gray-50)}.bg-gray-50\/50{background-color:#f9fafb80}@supports (color:color-mix(in lab, red, red)){.bg-gray-50\/50{background-color:color-mix(in oklab, var(--color-gray-50) 50%, transparent)}}.bg-gray-100{background-color:var(--color-gray-100)}.bg-gray-200{background-color:var(--color-gray-200)}.bg-gray-200\/60{background-color:#e5e7eb99}@supports (color:color-mix(in lab, red, red)){.bg-gray-200\/60{background-color:color-mix(in oklab, var(--color-gray-200) 60%, transparent)}}.bg-gray-800{background-color:var(--color-gray-800)}.bg-gray-900{background-color:var(--color-gray-900)}.bg-green-50{background-color:var(--color-green-50)}.bg-orange-50{background-color:var(--color-orange-50)}.bg-white{background-color:var(--color-white)}.bg-white\/70{background-color:#ffffffb3}@supports (color:color-mix(in lab, red, red)){.bg-white\/70{background-color:color-mix(in oklab, var(--color-white) 70%, transparent)}}.bg-gradient-to-br{--tw-gradient-position:to bottom right in oklab;background-image:linear-gradient(var(--tw-gradient-stops))}.from-\[var\(--wf-placeholder-from\,\#fb923c\)\]{--tw-gradient-from:var(--wf-placeholder-from,#fb923c);--tw-gradient-stops:var(--tw-gradient-via-stops,var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position))}.to-\[var\(--wf-placeholder-to\,\#ec4899\)\]{--tw-gradient-to:var(--wf-placeholder-to,#ec4899);--tw-gradient-stops:var(--tw-gradient-via-stops,var(--tw-gradient-position), var(--tw-gradient-from) var(--tw-gradient-from-position), var(--tw-gradient-to) var(--tw-gradient-to-position))}.object-cover{-o-object-fit:cover;object-fit:cover}.p-6{padding:calc(var(--spacing) * 6)}.p-8{padding:calc(var(--spacing) * 8)}.px-2{padding-inline:calc(var(--spacing) * 2)}.px-3{padding-inline:calc(var(--spacing) * 3)}.px-4{padding-inline:calc(var(--spacing) * 4)}.px-6{padding-inline:calc(var(--spacing) * 6)}.px-8{padding-inline:calc(var(--spacing) * 8)}.py-1{padding-block:calc(var(--spacing) * 1)}.py-2{padding-block:calc(var(--spacing) * 2)}.py-2\.5{padding-block:calc(var(--spacing) * 2.5)}.py-3{padding-block:calc(var(--spacing) * 3)}.pt-4{padding-top:calc(var(--spacing) * 4)}.pb-24{padding-bottom:calc(var(--spacing) * 24)}.text-center{text-align:center}.text-right{text-align:right}.font-mono{font-family:var(--font-mono)}.font-sans{font-family:var(--font-sans)}.text-lg{font-size:var(--text-lg);line-height:var(--tw-leading,var(--text-lg--line-height))}.text-sm{font-size:var(--text-sm);line-height:var(--tw-leading,var(--text-sm--line-height))}.text-xs{font-size:var(--text-xs);line-height:var(--tw-leading,var(--text-xs--line-height))}.text-\[8px\]{font-size:8px}.text-\[9px\]{font-size:9px}.text-\[10px\]{font-size:10px}.text-\[13px\]{font-size:13px}.leading-relaxed{--tw-leading:var(--leading-relaxed);line-height:var(--leading-relaxed)}.leading-tight{--tw-leading:var(--leading-tight);line-height:var(--leading-tight)}.font-black{--tw-font-weight:var(--font-weight-black);font-weight:var(--font-weight-black)}.font-bold{--tw-font-weight:var(--font-weight-bold);font-weight:var(--font-weight-bold)}.font-medium{--tw-font-weight:var(--font-weight-medium);font-weight:var(--font-weight-medium)}.tracking-\[0\.1em\]{--tw-tracking:.1em;letter-spacing:.1em}.tracking-\[0\.2em\]{--tw-tracking:.2em;letter-spacing:.2em}.tracking-tight{--tw-tracking:var(--tracking-tight);letter-spacing:var(--tracking-tight)}.tracking-tighter{--tw-tracking:var(--tracking-tighter);letter-spacing:var(--tracking-tighter)}.tracking-wide{--tw-tracking:var(--tracking-wide);letter-spacing:var(--tracking-wide)}.tracking-widest{--tw-tracking:var(--tracking-widest);letter-spacing:var(--tracking-widest)}.whitespace-pre{white-space:pre}.text-\[\#4ec9b0\]{color:#4ec9b0}.text-\[\#9cdcfe\]{color:#9cdcfe}.text-\[\#b5cea8\]{color:#b5cea8}.text-\[\#ce9178\]{color:#ce9178}.text-\[var\(--wf-artist-color\,\#6b7280\)\]{color:var(--wf-artist-color,#6b7280)}.text-\[var\(--wf-time-color\,\#9ca3af\)\]{color:var(--wf-time-color,#9ca3af)}.text-\[var\(--wf-title-color\,\#111827\)\]{color:var(--wf-title-color,#111827)}.text-blue-400{color:var(--color-blue-400)}.text-blue-500\/80{color:#3080ffcc}@supports (color:color-mix(in lab, red, red)){.text-blue-500\/80{color:color-mix(in oklab, var(--color-blue-500) 80%, transparent)}}.text-blue-600{color:var(--color-blue-600)}.text-gray-300{color:var(--color-gray-300)}.text-gray-400{color:var(--color-gray-400)}.text-gray-500{color:var(--color-gray-500)}.text-gray-600{color:var(--color-gray-600)}.text-gray-700{color:var(--color-gray-700)}.text-gray-900{color:var(--color-gray-900)}.text-green-400{color:var(--color-green-400)}.text-green-600{color:var(--color-green-600)}.text-orange-600{color:var(--color-orange-600)}.text-red-600{color:var(--color-red-600)}.text-white{color:var(--color-white)}.uppercase{text-transform:uppercase}.tabular-nums{--tw-numeric-spacing:tabular-nums;font-variant-numeric:var(--tw-ordinal,) var(--tw-slashed-zero,) var(--tw-numeric-figure,) var(--tw-numeric-spacing,) var(--tw-numeric-fraction,)}.accent-blue-600{accent-color:var(--color-blue-600)}.opacity-50{opacity:.5}.opacity-60{opacity:.6}.shadow-2xl{--tw-shadow:0 25px 50px -12px var(--tw-shadow-color,#00000040);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-\[0_4px_12px_rgba\(0\,0\,0\,0\.15\)\]{--tw-shadow:0 4px 12px var(--tw-shadow-color,#00000026);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-lg{--tw-shadow:0 10px 15px -3px var(--tw-shadow-color,#0000001a), 0 4px 6px -4px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-sm{--tw-shadow:0 1px 3px 0 var(--tw-shadow-color,#0000001a), 0 1px 2px -1px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-xl{--tw-shadow:0 20px 25px -5px var(--tw-shadow-color,#0000001a), 0 8px 10px -6px var(--tw-shadow-color,#0000001a);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.shadow-blue-500\/30{--tw-shadow-color:#3080ff4d}@supports (color:color-mix(in lab, red, red)){.shadow-blue-500\/30{--tw-shadow-color:color-mix(in oklab, color-mix(in oklab, var(--color-blue-500) 30%, transparent) var(--tw-shadow-alpha), transparent)}}.blur{--tw-blur:blur(8px);filter:var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,)}.blur-md{--tw-blur:blur(var(--blur-md));filter:var(--tw-blur,) var(--tw-brightness,) var(--tw-contrast,) var(--tw-grayscale,) var(--tw-hue-rotate,) var(--tw-invert,) var(--tw-saturate,) var(--tw-sepia,) var(--tw-drop-shadow,)}.backdrop-blur-\[1px\]{--tw-backdrop-blur:blur(1px);-webkit-backdrop-filter:var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);backdrop-filter:var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,)}.backdrop-blur-xl{--tw-backdrop-blur:blur(var(--blur-xl));-webkit-backdrop-filter:var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,);backdrop-filter:var(--tw-backdrop-blur,) var(--tw-backdrop-brightness,) var(--tw-backdrop-contrast,) var(--tw-backdrop-grayscale,) var(--tw-backdrop-hue-rotate,) var(--tw-backdrop-invert,) var(--tw-backdrop-opacity,) var(--tw-backdrop-saturate,) var(--tw-backdrop-sepia,)}.transition-\[width\]{transition-property:width;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-all{transition-property:all;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-colors{transition-property:color,background-color,border-color,outline-color,text-decoration-color,fill,stroke,--tw-gradient-from,--tw-gradient-via,--tw-gradient-to;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.transition-transform{transition-property:transform,translate,scale,rotate;transition-timing-function:var(--tw-ease,var(--default-transition-timing-function));transition-duration:var(--tw-duration,var(--default-transition-duration))}.duration-100{--tw-duration:.1s;transition-duration:.1s}.duration-300{--tw-duration:.3s;transition-duration:.3s}.duration-500{--tw-duration:.5s;transition-duration:.5s}.duration-700{--tw-duration:.7s;transition-duration:.7s}.ease-linear{--tw-ease:linear;transition-timing-function:linear}.ease-out{--tw-ease:var(--ease-out);transition-timing-function:var(--ease-out)}.outline-none{--tw-outline-style:none;outline-style:none}.select-none{-webkit-user-select:none;user-select:none}@media (hover:hover){.group-hover\:text-gray-600:is(:where(.group):hover *){color:var(--color-gray-600)}.group-hover\/artwork\:scale-110:is(:where(.group\/artwork):hover *){--tw-scale-x:110%;--tw-scale-y:110%;--tw-scale-z:110%;scale:var(--tw-scale-x) var(--tw-scale-y)}.hover\:scale-105:hover{--tw-scale-x:105%;--tw-scale-y:105%;--tw-scale-z:105%;scale:var(--tw-scale-x) var(--tw-scale-y)}.hover\:scale-110:hover{--tw-scale-x:110%;--tw-scale-y:110%;--tw-scale-z:110%;scale:var(--tw-scale-x) var(--tw-scale-y)}.hover\:border-gray-300:hover{border-color:var(--color-gray-300)}.hover\:border-red-300:hover{border-color:var(--color-red-300)}.hover\:bg-blue-700:hover{background-color:var(--color-blue-700)}.hover\:bg-gray-50:hover{background-color:var(--color-gray-50)}.hover\:bg-gray-100:hover{background-color:var(--color-gray-100)}.hover\:bg-green-100:hover{background-color:var(--color-green-100)}.hover\:bg-orange-100:hover{background-color:var(--color-orange-100)}.hover\:bg-red-50:hover{background-color:var(--color-red-50)}.hover\:text-blue-300:hover{color:var(--color-blue-300)}.hover\:text-blue-600:hover{color:var(--color-blue-600)}.hover\:text-gray-900:hover{color:var(--color-gray-900)}.hover\:shadow-2xl:hover{--tw-shadow:0 25px 50px -12px var(--tw-shadow-color,#00000040);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.hover\:shadow-\[0_6px_16px_rgba\(0\,0\,0\,0\.2\)\]:hover{--tw-shadow:0 6px 16px var(--tw-shadow-color,#0003);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.hover\:ring-2:hover{--tw-ring-shadow:var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color,currentcolor);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.hover\:ring-blue-500\/20:hover{--tw-ring-color:#3080ff33}@supports (color:color-mix(in lab, red, red)){.hover\:ring-blue-500\/20:hover{--tw-ring-color:color-mix(in oklab, var(--color-blue-500) 20%, transparent)}}}.focus\:border-blue-200:focus{border-color:var(--color-blue-200)}.focus\:border-blue-500:focus{border-color:var(--color-blue-500)}.focus\:bg-white:focus{background-color:var(--color-white)}.focus\:ring-2:focus{--tw-ring-shadow:var(--tw-ring-inset,) 0 0 0 calc(2px + var(--tw-ring-offset-width)) var(--tw-ring-color,currentcolor);box-shadow:var(--tw-inset-shadow), var(--tw-inset-ring-shadow), var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow)}.focus\:ring-blue-500\/20:focus{--tw-ring-color:#3080ff33}@supports (color:color-mix(in lab, red, red)){.focus\:ring-blue-500\/20:focus{--tw-ring-color:color-mix(in oklab, var(--color-blue-500) 20%, transparent)}}.active\:scale-90:active{--tw-scale-x:90%;--tw-scale-y:90%;--tw-scale-z:90%;scale:var(--tw-scale-x) var(--tw-scale-y)}.active\:scale-95:active{--tw-scale-x:95%;--tw-scale-y:95%;--tw-scale-z:95%;scale:var(--tw-scale-x) var(--tw-scale-y)}.active\:scale-\[0\.98\]:active{scale:.98}@media (width>=48rem){.md\:h-7{height:calc(var(--spacing) * 7)}.md\:h-14{height:calc(var(--spacing) * 14)}.md\:h-40{height:calc(var(--spacing) * 40)}.md\:w-7{width:calc(var(--spacing) * 7)}.md\:w-14{width:calc(var(--spacing) * 14)}.md\:w-40{width:calc(var(--spacing) * 40)}.md\:flex-row{flex-direction:row}.md\:text-xl{font-size:var(--text-xl);line-height:var(--tw-leading,var(--text-xl--line-height))}.md\:text-xs{font-size:var(--text-xs);line-height:var(--tw-leading,var(--text-xs--line-height))}}@media (width>=64rem){.lg\:w-96{width:calc(var(--spacing) * 96)}.lg\:flex-row{flex-direction:row}}}@property --tw-scale-x{syntax:"*";inherits:false;initial-value:1}@property --tw-scale-y{syntax:"*";inherits:false;initial-value:1}@property --tw-scale-z{syntax:"*";inherits:false;initial-value:1}@property --tw-border-style{syntax:"*";inherits:false;initial-value:solid}@property --tw-gradient-position{syntax:"*";inherits:false}@property --tw-gradient-from{syntax:"<color>";inherits:false;initial-value:#0000}@property --tw-gradient-via{syntax:"<color>";inherits:false;initial-value:#0000}@property --tw-gradient-to{syntax:"<color>";inherits:false;initial-value:#0000}@property --tw-gradient-stops{syntax:"*";inherits:false}@property --tw-gradient-via-stops{syntax:"*";inherits:false}@property --tw-gradient-from-position{syntax:"<length-percentage>";inherits:false;initial-value:0%}@property --tw-gradient-via-position{syntax:"<length-percentage>";inherits:false;initial-value:50%}@property --tw-gradient-to-position{syntax:"<length-percentage>";inherits:false;initial-value:100%}@property --tw-leading{syntax:"*";inherits:false}@property --tw-font-weight{syntax:"*";inherits:false}@property --tw-tracking{syntax:"*";inherits:false}@property --tw-ordinal{syntax:"*";inherits:false}@property --tw-slashed-zero{syntax:"*";inherits:false}@property --tw-numeric-figure{syntax:"*";inherits:false}@property --tw-numeric-spacing{syntax:"*";inherits:false}@property --tw-numeric-fraction{syntax:"*";inherits:false}@property --tw-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-shadow-color{syntax:"*";inherits:false}@property --tw-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-inset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-shadow-color{syntax:"*";inherits:false}@property --tw-inset-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-ring-color{syntax:"*";inherits:false}@property --tw-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-inset-ring-color{syntax:"*";inherits:false}@property --tw-inset-ring-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-ring-inset{syntax:"*";inherits:false}@property --tw-ring-offset-width{syntax:"<length>";inherits:false;initial-value:0}@property --tw-ring-offset-color{syntax:"*";inherits:false;initial-value:#fff}@property --tw-ring-offset-shadow{syntax:"*";inherits:false;initial-value:0 0 #0000}@property --tw-blur{syntax:"*";inherits:false}@property --tw-brightness{syntax:"*";inherits:false}@property --tw-contrast{syntax:"*";inherits:false}@property --tw-grayscale{syntax:"*";inherits:false}@property --tw-hue-rotate{syntax:"*";inherits:false}@property --tw-invert{syntax:"*";inherits:false}@property --tw-opacity{syntax:"*";inherits:false}@property --tw-saturate{syntax:"*";inherits:false}@property --tw-sepia{syntax:"*";inherits:false}@property --tw-drop-shadow{syntax:"*";inherits:false}@property --tw-drop-shadow-color{syntax:"*";inherits:false}@property --tw-drop-shadow-alpha{syntax:"<percentage>";inherits:false;initial-value:100%}@property --tw-drop-shadow-size{syntax:"*";inherits:false}@property --tw-backdrop-blur{syntax:"*";inherits:false}@property --tw-backdrop-brightness{syntax:"*";inherits:false}@property --tw-backdrop-contrast{syntax:"*";inherits:false}@property --tw-backdrop-grayscale{syntax:"*";inherits:false}@property --tw-backdrop-hue-rotate{syntax:"*";inherits:false}@property --tw-backdrop-invert{syntax:"*";inherits:false}@property --tw-backdrop-opacity{syntax:"*";inherits:false}@property --tw-backdrop-saturate{syntax:"*";inherits:false}@property --tw-backdrop-sepia{syntax:"*";inherits:false}@property --tw-duration{syntax:"*";inherits:false}@property --tw-ease{syntax:"*";inherits:false}@keyframes spin{to{transform:rotate(360deg)}}
3
- /*$vite$:1*/