Limeplay - Open Source Video Player UI ComponentsLimeplay

Timeline Labels

Timeline Labels provide semantic time display components for media players. These components automatically format time based on duration and provide proper accessibility attributes.

Installation

Install the component

npx shadcn add @limeplay/timeline-labels

Add Event & Action Bridge

Import the useTimelineStates hook in your existing PlayerHooks component.

components/limeplay/player-hooks.tsx
import React from "react"

import { useShakaPlayer } from "@/hooks/limeplay/use-shaka-player"
import { useTimelineStates } from "@/hooks/limeplay/use-timeline"

export const PlayerHooks = React.memo(() => {
  useShakaPlayer()
  useTimelineStates() 

  return null
})

Add the Store States

lib/create-media-store.ts
import {
  createPlayerStore,
  PlayerStore,
} from "@/hooks/limeplay/use-player"
import {
  createTimelineStore,
  TimelineStore,
} from "@/hooks/limeplay/use-timeline"

export type TypeMediaStore = PlayerStore &
  TimelineStore & {} 

export function createMediaStore(initProps?: Partial<CreateMediaStoreProps>) {
  const mediaStore = create<TypeMediaStore>()((...etc) => ({
    ...createPlayerStore(...etc),
    ...createTimelineStore(...etc),
    ...initProps,
  }))
  return mediaStore
}

Usage

  1. Compose the labels
components/player/timeline-control.tsx
"use client"

import { useState } from "react"

import { useMediaStore } from "@/components/limeplay/media-provider"
import { Duration, Elapsed, HoverTime, LiveLatency, Remaining } from "@/components/limeplay/timeline-labels"

export function TimelineSliderControl() {
  const [showRemaining, setShowRemaining] = useState(false)
  const isLive = useMediaStore((state) => state.isLive)

  return (
    <div className="my-auto flex grow items-center gap-3 select-none">
      {!isLive && <Elapsed className="text-xs font-medium" />}
      {!isLive && (
        <Button
          size="icon"
          onClick={() => { setShowRemaining(!showRemaining) }}
          aria-label={showRemaining ? "Show total duration" : "Show remaining time"}
          aria-pressed={showRemaining}
        >
          {showRemaining ? (
            <Remaining className="text-xs font-medium" />
          ) : (
            <Duration className="text-xs font-medium" />
          )}
        </Button>
      )}
    </div>
  )
}

Understanding

  • <Elapsed /> component shows current playback time
  • <Remaining /> component shows remaining time (with minus sign)
  • <Duration /> component shows total media duration
  • <HoverTime /> component shows time at hover position on timeline