// Hand-written declarations for the vendored `hls.mjs`.
//
// Deliberately narrow: it declares the API this player actually calls, not hls.js's full surface. The upstream
// `.d.ts` is not vendored because it pulls in a tree of internal type modules, and the point of vendoring was
// to have ONE reviewable file. Anything added to the player that hls.js supports but this file does not gets
// declared here, in the open, rather than cast away at the call site.

export type HlsErrorData = {
  fatal: boolean;
  type: string;
  details: string;
  reason?: string;
  error?: Error;
};

export type HlsLevel = { height?: number; width?: number; bitrate?: number };

export type HlsConfig = {
  /** Where playback begins, in seconds. -1 means "the start", which is not the same as 0 for a live edge. */
  startPosition?: number;
  /** Called before `xhr.open`, so it may open the request itself and then set headers on it. */
  xhrSetup?: (xhr: XMLHttpRequest, url: string) => void;
  enableWorker?: boolean;
  lowLatencyMode?: boolean;
  maxBufferLength?: number;
  maxMaxBufferLength?: number;
  backBufferLength?: number;
};

declare class Hls {
  constructor(config?: HlsConfig);

  static isSupported(): boolean;
  static readonly Events: {
    MANIFEST_PARSED: string;
    LEVEL_LOADED: string;
    ERROR: string;
    MEDIA_ATTACHED: string;
  };
  static readonly ErrorTypes: {
    NETWORK_ERROR: string;
    MEDIA_ERROR: string;
    KEY_SYSTEM_ERROR: string;
    MUX_ERROR: string;
    OTHER_ERROR: string;
  };

  loadSource(url: string): void;
  attachMedia(media: HTMLMediaElement): void;
  detachMedia(): void;
  startLoad(startPosition?: number): void;
  stopLoad(): void;
  recoverMediaError(): void;
  destroy(): void;

  on(event: string, listener: (event: string, data: HlsErrorData) => void): void;
  off(event: string, listener?: (event: string, data: HlsErrorData) => void): void;

  readonly levels: HlsLevel[];
  currentLevel: number;
}

export default Hls;
