From c746ce1b7c3f80e5a8742b94392042a3f136e2c3 Mon Sep 17 00:00:00 2001 From: lashman Date: Sat, 25 Apr 2026 20:04:13 +0300 Subject: [PATCH] TmdbDiscoverItem type + browser api types --- src/api/tmdb.ts | 7 +++++ src/lib/tmdb-mapping.ts | 5 ++-- src/vite-env.d.ts | 58 +++++++++++++++++++++++++++++++++++++++++ 3 files changed, 68 insertions(+), 2 deletions(-) diff --git a/src/api/tmdb.ts b/src/api/tmdb.ts index d43a778..6eb5d6b 100644 --- a/src/api/tmdb.ts +++ b/src/api/tmdb.ts @@ -461,6 +461,13 @@ export interface TmdbSearchMultiResult extends TmdbMovie { known_for?: any[] } +/** TMDB discover result - union of movie and tv with optional media_type. */ +export type TmdbDiscoverItem = + | TmdbMovie + | TmdbTvShow + | (TmdbMovie & { media_type: string }) + | (TmdbTvShow & { media_type: string }) + /* ────────────────────────────────────────────────────────────── */ /* Fetcher */ /* ────────────────────────────────────────────────────────────── */ diff --git a/src/lib/tmdb-mapping.ts b/src/lib/tmdb-mapping.ts index ad37724..e871060 100644 --- a/src/lib/tmdb-mapping.ts +++ b/src/lib/tmdb-mapping.ts @@ -1,5 +1,6 @@ import { getTmdbImageUrl } from '../api/tmdb' import type { BaseItemDto } from '../api/types' +import type { TmdbDiscoverItem } from '../api/tmdb' /** * Convert a TMDB result row (movie / tv / multi) into a synthetic @@ -10,7 +11,7 @@ import type { BaseItemDto } from '../api/types' * clicking opens the existing detail page instead of the synthetic one. */ export function mapTmdbToJf( - items: any[], + items: TmdbDiscoverItem[], libraryMap?: Map, ): BaseItemDto[] { return items.map(m => { @@ -37,7 +38,7 @@ export function mapTmdbToJf( _tmdbBackdrop: m.backdrop_path ? getTmdbImageUrl(m.backdrop_path, 'w780') : undefined, _inLibrary: !!local, _tmdbId: String(m.id), - } as any as BaseItemDto + } as unknown as BaseItemDto }) } diff --git a/src/vite-env.d.ts b/src/vite-env.d.ts index 5cd211b..15022d8 100644 --- a/src/vite-env.d.ts +++ b/src/vite-env.d.ts @@ -8,3 +8,61 @@ interface ImportMetaEnv { interface ImportMeta { readonly env: ImportMetaEnv } + +/* ── Browser API extensions ── */ + +interface Navigator { + mediaCapabilities?: { + decodingInfo(configuration: unknown): Promise + } +} + +interface VideoPlaybackQuality { + droppedVideoFrames: number +} + +interface HTMLVideoElement { + getVideoPlaybackQuality?(): VideoPlaybackQuality + audioTracks?: { length: number; [i: number]: { enabled: boolean } } + mozPreservesPitch?: boolean + webkitPreservesPitch?: boolean +} + +interface Document { + pictureInPictureElement?: Element | null + exitPictureInPicture?(): Promise +} + +interface Window { + webkitAudioContext?: typeof AudioContext + SubtitlesOctopus?: unknown +} + +/* eslint-disable @typescript-eslint/no-empty-object-type */ +declare module 'react' { + interface CSSProperties { + WebkitUserSelect?: string + } +} + +/* ── Extended Jellyfin item with synthetic TMDB fields ── */ + +import type { BaseItemDto } from '@jellyfin/sdk/lib/generated-client/models' + +type SyntheticBaseItemDto = BaseItemDto & { + _tmdbPoster?: string + _tmdbBackdrop?: string + _inLibrary?: boolean + _tmdbId?: string + _kind?: string +} + +declare module '@jellyfin/sdk/lib/generated-client/models' { + interface BaseItemDto { + _tmdbPoster?: string + _tmdbBackdrop?: string + _inLibrary?: boolean + _tmdbId?: string + _kind?: string + } +}