diff --git a/components/Global/card.tsx b/components/Global/card.tsx
index 03185ace..7a1fa471 100644
--- a/components/Global/card.tsx
+++ b/components/Global/card.tsx
@@ -55,6 +55,7 @@ export function Card(props: CardProps) {
{props.blurhash && !imageLoaded && (
)}
diff --git a/components/Home/helpers/recently-played.tsx b/components/Home/helpers/recently-played.tsx
index a6f5d946..28061679 100644
--- a/components/Home/helpers/recently-played.tsx
+++ b/components/Home/helpers/recently-played.tsx
@@ -10,8 +10,8 @@ import { usePlayerContext } from "../../../player/provider";
export default function RecentlyPlayed(): React.JSX.Element {
- const { resetQueue: clearQueue, addToQueue } = usePlayerContext();
- const { apiClient } = useApiClientContext();
+ const { addToQueue, resetQueue } = usePlayerContext();
+ const { apiClient, sessionId } = useApiClientContext();
const { recentTracks } = useHomeContext();
useEffect(() => {
@@ -37,8 +37,8 @@ export default function RecentlyPlayed(): React.JSX.Element {
itemId={recentlyPlayedTrack.AlbumId!}
marginRight={20}
onPress={async () => {
- await clearQueue();
- await addToQueue([mapDtoToTrack(apiClient!, recentlyPlayedTrack)])
+ await resetQueue(false);
+ await addToQueue([mapDtoToTrack(apiClient!, sessionId, recentlyPlayedTrack)])
play();
}}
>
diff --git a/components/Player/mini-player.tsx b/components/Player/mini-player.tsx
index ff721ec3..7145d6e2 100644
--- a/components/Player/mini-player.tsx
+++ b/components/Player/mini-player.tsx
@@ -6,7 +6,6 @@ import { usePlayerContext } from "../../player/provider";
import { BottomTabNavigationEventMap, BottomTabNavigationProp } from "@react-navigation/bottom-tabs";
import { NavigationHelpers, ParamListBase } from "@react-navigation/native";
import { BlurView } from "@react-native-community/blur";
-import { pause, play, skipToNext } from "react-native-track-player/lib/src/trackPlayer";
import Icon from "../Global/icon";
import { Text } from "../Global/text";
import { Colors } from "../../enums/colors";
@@ -15,10 +14,10 @@ export function Miniplayer({ navigation }: { navigation : NavigationHelpers
navigation.navigate("Player")}>
@@ -45,7 +44,6 @@ export function Miniplayer({ navigation }: { navigation : NavigationHelpers skipToNext()}
/>
diff --git a/components/jellyfin-api-provider.tsx b/components/jellyfin-api-provider.tsx
index ae89446f..d207efc1 100644
--- a/components/jellyfin-api-provider.tsx
+++ b/components/jellyfin-api-provider.tsx
@@ -2,16 +2,17 @@ import { Api } from '@jellyfin/sdk';
import React, { createContext, ReactNode, SetStateAction, useContext, useEffect, useState } from 'react';
import { useApi } from '../api/queries';
import _ from 'lodash';
-import { QueryObserverResult, RefetchOptions } from '@tanstack/react-query';
import { storage } from '../constants/storage';
import { MMKVStorageKeys } from '../enums/mmkv-storage-keys';
import { JellifyServer } from '../types/JellifyServer';
import { JellifyLibrary } from '../types/JellifyLibrary';
import { JellifyUser } from '../types/JellifyUser';
+import { uuid } from "uuidv4";
interface JellyfinApiClientContext {
apiClient: Api | undefined;
apiPending: boolean;
+ sessionId: string;
server: JellifyServer | undefined;
setServer: React.Dispatch>;
user: JellifyUser | undefined;
@@ -27,6 +28,7 @@ const JellyfinApiClientContextInitializer = () => {
const serverJson = storage.getString(MMKVStorageKeys.Server);
const libraryJson = storage.getString(MMKVStorageKeys.Library);
+ const [sessionId, setSessionId] = useState(uuid())
const [user, setUser] = useState(userJson ? (JSON.parse(userJson) as JellifyUser) : undefined);
const [server, setServer] = useState(serverJson ? (JSON.parse(serverJson) as JellifyServer) : undefined);
const [library, setLibrary] = useState(libraryJson ? (JSON.parse(libraryJson) as JellifyLibrary) : undefined);
@@ -96,6 +98,7 @@ const JellyfinApiClientContextInitializer = () => {
return {
apiClient,
apiPending,
+ sessionId,
server,
setServer,
user,
@@ -110,6 +113,7 @@ export const JellyfinApiClientContext =
createContext({
apiClient: undefined,
apiPending: true,
+ sessionId: "",
server: undefined,
setServer: () => {},
user: undefined,
@@ -125,6 +129,7 @@ export const JellyfinApiClientProvider: ({ children }: {
const {
apiClient,
apiPending,
+ sessionId,
server,
setServer,
user,
@@ -140,6 +145,7 @@ export const JellyfinApiClientProvider: ({ children }: {
>;
queue: JellifyTrack[];
+ play: () => Promise,
+ pause: () => Promise,
resetQueue: (hideMiniplayer : boolean | undefined) => Promise;
addToQueue: (tracks: JellifyTrack[]) => Promise;
setPlayerState: React.Dispatch>;
@@ -21,10 +25,15 @@ interface PlayerContext {
const PlayerContextInitializer = () => {
const queueJson = storage.getString(MMKVStorageKeys.PlayQueue);
+
+ const { apiClient, sessionId } = useApiClientContext();
+ const playStateApi = getPlaystateApi(apiClient!)
+ //#region State
const [showPlayer, setShowPlayer] = useState(false);
const [showMiniplayer, setShowMiniplayer] = useState(false);
const [queue, setQueue] = useState(queueJson ? JSON.parse(queueJson) : []);
+ //#endregion State
//#region RNTP Setup
setupPlayer().then(() => console.debug("Player setup successfully"));
@@ -32,6 +41,31 @@ const PlayerContextInitializer = () => {
const [playerState, setPlayerState] = useState(null);
//#endregion RNTP Setup
+ //#region Functions
+ const play = async () => {
+ rntpPlay();
+
+ const activeTrack = await getActiveTrack() as JellifyTrack;
+ playStateApi.reportPlaybackStart({
+ playbackStartInfo: {
+ SessionId: sessionId,
+ ItemId: activeTrack.ItemId
+ }
+ })
+ }
+
+ const pause = async () => {
+ rntpPause();
+
+ const activeTrack = await getActiveTrack() as JellifyTrack;
+ playStateApi.reportPlaybackStopped({
+ playbackStopInfo: {
+ SessionId: sessionId,
+ ItemId: activeTrack.ItemId
+ }
+ })
+ }
+
const resetQueue = async (hideMiniplayer: boolean | undefined) => {
console.debug("Clearing queue")
await reset();
@@ -50,6 +84,7 @@ const PlayerContextInitializer = () => {
setShowMiniplayer(true);
}
+ //#endregion Functions
return {
showPlayer,
@@ -57,6 +92,8 @@ const PlayerContextInitializer = () => {
showMiniplayer,
setShowMiniplayer,
queue,
+ play,
+ pause,
addToQueue,
resetQueue,
setPlayerState,
@@ -69,6 +106,8 @@ export const PlayerContext = createContext({
showMiniplayer: false,
setShowMiniplayer: () => {},
queue: [],
+ play: async () => {},
+ pause: async () => {},
resetQueue: async () => {},
addToQueue: async ([]) => {},
setPlayerState: () => {},
@@ -81,6 +120,8 @@ export const PlayerProvider: ({ children }: { children: ReactNode }) => React.JS
showMiniplayer,
setShowMiniplayer,
queue,
+ play,
+ pause,
resetQueue,
addToQueue,
setPlayerState,
@@ -92,6 +133,8 @@ export const PlayerProvider: ({ children }: { children: ReactNode }) => React.JS
showMiniplayer,
setShowMiniplayer,
queue,
+ play,
+ pause,
resetQueue,
addToQueue,
setPlayerState,
diff --git a/types/JellifyTrack.ts b/types/JellifyTrack.ts
index 3bb89f12..d662be9f 100644
--- a/types/JellifyTrack.ts
+++ b/types/JellifyTrack.ts
@@ -20,6 +20,7 @@ export interface JellifyTrack extends Track {
rating?: RatingType | undefined;
isLiveStream?: boolean | undefined;
+ ItemId: string | undefined;
Year?: number | null | undefined;
IndexNumber?: number | null | undefined;
ParentIndexNumber?: number | null | undefined;