diff --git a/app/(auth)/(tabs)/(home,libraries,search,favorites)/items/page.tsx b/app/(auth)/(tabs)/(home,libraries,search,favorites)/items/page.tsx
index f0bb2a46..b3d905fa 100644
--- a/app/(auth)/(tabs)/(home,libraries,search,favorites)/items/page.tsx
+++ b/app/(auth)/(tabs)/(home,libraries,search,favorites)/items/page.tsx
@@ -27,8 +27,8 @@ const Page: React.FC = () => {
ItemFields.MediaStreams,
]);
- // preload media sources in background
- useItemQuery(id, false, undefined, []);
+ // preload media sources
+ const { data: itemWithSources } = useItemQuery(id, false, undefined, []);
const opacity = useSharedValue(1);
const animatedStyle = useAnimatedStyle(() => {
@@ -98,7 +98,13 @@ const Page: React.FC = () => {
- {item && }
+ {item && (
+
+ )}
);
};
diff --git a/components/ItemContent.tsx b/components/ItemContent.tsx
index 783371ec..6b8f1bba 100644
--- a/components/ItemContent.tsx
+++ b/components/ItemContent.tsx
@@ -46,10 +46,11 @@ export type SelectedOptions = {
interface ItemContentProps {
item: BaseItemDto;
isOffline: boolean;
+ itemWithSources?: BaseItemDto | null;
}
export const ItemContent: React.FC = React.memo(
- ({ item, isOffline }) => {
+ ({ item, isOffline, itemWithSources }) => {
const [api] = useAtom(apiAtom);
const { settings } = useSettings();
const { orientation } = useOrientation();
@@ -98,7 +99,7 @@ export const ItemContent: React.FC = React.memo(
]);
useEffect(() => {
- if (!Platform.isTV) {
+ if (!Platform.isTV && itemWithSources) {
navigation.setOptions({
headerRight: () =>
item &&
@@ -108,7 +109,7 @@ export const ItemContent: React.FC = React.memo(
{item.Type !== "Program" && (
{!Platform.isTV && (
-
+
)}
{user?.Policy?.IsAdministrator && (
@@ -125,7 +126,7 @@ export const ItemContent: React.FC = React.memo(
{item.Type !== "Program" && (
{!Platform.isTV && (
-
+
)}
{user?.Policy?.IsAdministrator && (
@@ -139,7 +140,7 @@ export const ItemContent: React.FC = React.memo(
)),
});
}
- }, [item, navigation, user]);
+ }, [item, navigation, user, itemWithSources]);
useEffect(() => {
if (item) {
@@ -212,7 +213,7 @@ export const ItemContent: React.FC = React.memo(
)}
diff --git a/components/MediaSourceButton.tsx b/components/MediaSourceButton.tsx
index fcef6b8f..05847f35 100644
--- a/components/MediaSourceButton.tsx
+++ b/components/MediaSourceButton.tsx
@@ -7,13 +7,12 @@ import { useCallback, useEffect, useMemo, useState } from "react";
import { useTranslation } from "react-i18next";
import { ActivityIndicator, TouchableOpacity, View } from "react-native";
import type { ThemeColors } from "@/hooks/useImageColorsReturn";
-import { useItemQuery } from "@/hooks/useItemQuery";
import { BITRATES } from "./BitRateSheet";
import type { SelectedOptions } from "./ItemContent";
import { type OptionGroup, PlatformDropdown } from "./PlatformDropdown";
interface Props extends React.ComponentProps {
- item: BaseItemDto;
+ item?: BaseItemDto | null;
selectedOptions: SelectedOptions;
setSelectedOptions: React.Dispatch<
React.SetStateAction
@@ -29,12 +28,6 @@ export const MediaSourceButton: React.FC = ({
}: Props) => {
const { t } = useTranslation();
const [open, setOpen] = useState(false);
- const { data: itemWithSources, isLoading } = useItemQuery(
- item.Id,
- false,
- undefined,
- [],
- );
const effectiveColors = colors || {
primary: "#7c3aed",
@@ -42,7 +35,7 @@ export const MediaSourceButton: React.FC = ({
};
useEffect(() => {
- const firstMediaSource = itemWithSources?.MediaSources?.[0];
+ const firstMediaSource = item?.MediaSources?.[0];
if (!firstMediaSource) return;
setSelectedOptions((prev) => {
if (!prev) return prev;
@@ -51,7 +44,7 @@ export const MediaSourceButton: React.FC = ({
mediaSource: firstMediaSource,
};
});
- }, [itemWithSources, setSelectedOptions]);
+ }, [item, setSelectedOptions]);
const getMediaSourceDisplayName = useCallback((source: MediaSourceInfo) => {
const videoStream = source.MediaStreams?.find((x) => x.Type === "Video");
@@ -93,13 +86,10 @@ export const MediaSourceButton: React.FC = ({
});
// Media Source group (only if multiple sources)
- if (
- itemWithSources?.MediaSources &&
- itemWithSources.MediaSources.length > 1
- ) {
+ if (item?.MediaSources && item.MediaSources.length > 1) {
groups.push({
title: t("item_card.video"),
- options: itemWithSources.MediaSources.map((source) => ({
+ options: item.MediaSources.map((source) => ({
type: "radio" as const,
label: getMediaSourceDisplayName(source),
value: source,
@@ -159,7 +149,7 @@ export const MediaSourceButton: React.FC = ({
return groups;
}, [
- itemWithSources,
+ item,
selectedOptions,
audioStreams,
subtitleStreams,
@@ -170,7 +160,7 @@ export const MediaSourceButton: React.FC = ({
const trigger = (
setOpen(true)}
className='relative'
>
@@ -179,7 +169,7 @@ export const MediaSourceButton: React.FC = ({
className='absolute w-12 h-12 rounded-full'
/>
- {isLoading ? (
+ {!item ? (
) : (