type detail and shared ui
This commit is contained in:
@@ -277,7 +277,7 @@ export default function DetailHero({
|
|||||||
<RequestButton
|
<RequestButton
|
||||||
tmdbId={Number(tmdbId)}
|
tmdbId={Number(tmdbId)}
|
||||||
kind={item.Type === 'Movie' ? 'movie' : 'tv'}
|
kind={item.Type === 'Movie' ? 'movie' : 'tv'}
|
||||||
tmdbData={tmdbData as any}
|
tmdbData={tmdbData}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
@@ -337,7 +337,7 @@ export default function DetailHero({
|
|||||||
tmdbId={tmdbId}
|
tmdbId={tmdbId}
|
||||||
type={itemType === 'Series' ? 'tv' : 'movie'}
|
type={itemType === 'Series' ? 'tv' : 'movie'}
|
||||||
ids={tmdbData?.external_ids}
|
ids={tmdbData?.external_ids}
|
||||||
jellyfinExternalUrls={item.ExternalUrls as any}
|
jellyfinExternalUrls={item.ExternalUrls}
|
||||||
/>
|
/>
|
||||||
|
|
||||||
{progress != null && progress > 0 && (
|
{progress != null && progress > 0 && (
|
||||||
|
|||||||
@@ -206,14 +206,14 @@ export default function DetailMainSections({
|
|||||||
<div className="grid grid-cols-1 lg:grid-cols-2 gap-x-8 gap-y-10">
|
<div className="grid grid-cols-1 lg:grid-cols-2 gap-x-8 gap-y-10">
|
||||||
{cast.length > 0 && (
|
{cast.length > 0 && (
|
||||||
<Section label="Cast" id="detail-cast">
|
<Section label="Cast" id="detail-cast">
|
||||||
<CastList cast={cast as any[]} fallbackPeople={item.People} />
|
<CastList cast={cast} fallbackPeople={item.People} />
|
||||||
</Section>
|
</Section>
|
||||||
)}
|
)}
|
||||||
{crew.length > 0 && (
|
{crew.length > 0 && (
|
||||||
<Section label="Crew">
|
<Section label="Crew">
|
||||||
<CrewGrid crew={crew as any[]} />
|
<CrewGrid crew={crew} />
|
||||||
<div className="mt-3">
|
<div className="mt-3">
|
||||||
<ComposerBlock crew={crew as any[]} />
|
<ComposerBlock crew={crew} />
|
||||||
</div>
|
</div>
|
||||||
</Section>
|
</Section>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ interface Props {
|
|||||||
}
|
}
|
||||||
|
|
||||||
export default function VersionsSelector({ item, selectedSourceId, onChange }: Props) {
|
export default function VersionsSelector({ item, selectedSourceId, onChange }: Props) {
|
||||||
const sources = (item.MediaSources || []) as any[]
|
const sources = item.MediaSources || []
|
||||||
if (sources.length <= 1) return null
|
if (sources.length <= 1) return null
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -164,7 +164,7 @@ export default function RequestModal({ open, onClose, tmdbId, kind, tmdbData }:
|
|||||||
monitored,
|
monitored,
|
||||||
searchOnAdd,
|
searchOnAdd,
|
||||||
title: match.title,
|
title: match.title,
|
||||||
titleSlug: (match as any).titleSlug || '',
|
titleSlug: match.titleSlug || '',
|
||||||
year: match.year || 0,
|
year: match.year || 0,
|
||||||
images: match.images,
|
images: match.images,
|
||||||
minimumAvailability: 'released',
|
minimumAvailability: 'released',
|
||||||
@@ -195,7 +195,7 @@ export default function RequestModal({ open, onClose, tmdbId, kind, tmdbData }:
|
|||||||
monitored,
|
monitored,
|
||||||
searchOnAdd,
|
searchOnAdd,
|
||||||
title: match.title,
|
title: match.title,
|
||||||
titleSlug: (match as any).titleSlug || '',
|
titleSlug: match.titleSlug || '',
|
||||||
year: match.year || 0,
|
year: match.year || 0,
|
||||||
images: match.images,
|
images: match.images,
|
||||||
seasons,
|
seasons,
|
||||||
|
|||||||
@@ -273,7 +273,7 @@ function ListRowCard({ item, index }: { item: BaseItemDto; index: number }) {
|
|||||||
const thumb =
|
const thumb =
|
||||||
getBestImage(serverUrl, item, 'thumb', 240) ||
|
getBestImage(serverUrl, item, 'thumb', 240) ||
|
||||||
getBestImage(serverUrl, item, 'primary', 200) ||
|
getBestImage(serverUrl, item, 'primary', 200) ||
|
||||||
(item as any)._tmdbPoster ||
|
item._tmdbPoster ||
|
||||||
null
|
null
|
||||||
const subtitle = [
|
const subtitle = [
|
||||||
item.ProductionYear,
|
item.ProductionYear,
|
||||||
|
|||||||
@@ -113,7 +113,7 @@ function Mounted({ saved }: Props) {
|
|||||||
}
|
}
|
||||||
if (items.length === 0) return null
|
if (items.length === 0) return null
|
||||||
|
|
||||||
const matched = items.filter(i => (i as any)._inLibrary).length
|
const matched = items.filter(i => i._inLibrary).length
|
||||||
const subtitle = `${matched} of ${items.length} in your library · from Letterboxd`
|
const subtitle = `${matched} of ${items.length} in your library · from Letterboxd`
|
||||||
|
|
||||||
return (
|
return (
|
||||||
|
|||||||
@@ -45,7 +45,7 @@ export default function PersonSpotlightRow({ personId, name, role, profilePath,
|
|||||||
? (credits.crew || []).filter(c => c.job === 'Director')
|
? (credits.crew || []).filter(c => c.job === 'Director')
|
||||||
: (credits.cast || [])
|
: (credits.cast || [])
|
||||||
// Drop trivia / archival appearances and ultra-deep cuts.
|
// Drop trivia / archival appearances and ultra-deep cuts.
|
||||||
.filter(c => COMMERCIAL_DEPARTMENTS.includes((c as any).department || 'Acting'))
|
.filter(c => COMMERCIAL_DEPARTMENTS.includes(c.department || 'Acting'))
|
||||||
|
|
||||||
// De-dupe by id (a director may have multiple crew credits on one film
|
// De-dupe by id (a director may have multiple crew credits on one film
|
||||||
// when they're also writer; a cast member may appear twice for episodic
|
// when they're also writer; a cast member may appear twice for episodic
|
||||||
|
|||||||
@@ -205,7 +205,7 @@ export default function QuickLookModal() {
|
|||||||
<RequestButton
|
<RequestButton
|
||||||
tmdbId={numericTmdb}
|
tmdbId={numericTmdb}
|
||||||
kind={item.Type === 'Movie' ? 'movie' : 'tv'}
|
kind={item.Type === 'Movie' ? 'movie' : 'tv'}
|
||||||
tmdbData={tmdbData as any}
|
tmdbData={tmdbData}
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -92,7 +92,7 @@ export default function SmartShelfWizard({ open, onClose }: Props) {
|
|||||||
<Field label="Type">
|
<Field label="Type">
|
||||||
<Segmented
|
<Segmented
|
||||||
value={draft.type}
|
value={draft.type}
|
||||||
onChange={v => setDraft(d => ({ ...d, type: v as any }))}
|
onChange={v => setDraft(d => ({ ...d, type: v }))}
|
||||||
options={[
|
options={[
|
||||||
{ value: 'any', label: 'Any' },
|
{ value: 'any', label: 'Any' },
|
||||||
{ value: 'movie', label: 'Movies' },
|
{ value: 'movie', label: 'Movies' },
|
||||||
@@ -155,7 +155,7 @@ export default function SmartShelfWizard({ open, onClose }: Props) {
|
|||||||
<Field label="Watched">
|
<Field label="Watched">
|
||||||
<Segmented
|
<Segmented
|
||||||
value={draft.watched}
|
value={draft.watched}
|
||||||
onChange={v => setDraft(d => ({ ...d, watched: v as any }))}
|
onChange={v => setDraft(d => ({ ...d, watched: v }))}
|
||||||
options={[
|
options={[
|
||||||
{ value: 'any', label: 'Any' },
|
{ value: 'any', label: 'Any' },
|
||||||
{ value: 'unplayed', label: 'Unwatched' },
|
{ value: 'unplayed', label: 'Unwatched' },
|
||||||
@@ -185,7 +185,7 @@ export default function SmartShelfWizard({ open, onClose }: Props) {
|
|||||||
<Field label="Sort">
|
<Field label="Sort">
|
||||||
<Segmented
|
<Segmented
|
||||||
value={draft.sortBy}
|
value={draft.sortBy}
|
||||||
onChange={v => setDraft(d => ({ ...d, sortBy: v as any }))}
|
onChange={v => setDraft(d => ({ ...d, sortBy: v }))}
|
||||||
options={[
|
options={[
|
||||||
{ value: 'random', label: 'Random' },
|
{ value: 'random', label: 'Random' },
|
||||||
{ value: 'recent', label: 'Recent' },
|
{ value: 'recent', label: 'Recent' },
|
||||||
|
|||||||
Reference in New Issue
Block a user