fix(player): return from background audio onto the episode it advanced to
An episode that ends while backgrounded in audio-only mode advances in the
backend, but player_exit_background_audio returned only a position, so the
video page reloaded the episode it was mounted with -- the previous one, at
the new episode's timestamp.
The command now returns BackgroundAudioResume { itemId, positionSeconds }.
planHandoffReturn yields "other-item" when the id differs from the mounted
one, and the player page navigates to that episode with resumeAt=<seconds>,
marking the outgoing episode watched and suppressing its stale stop report.
TRACES: UR-040, UR-023 | DR-296 | UT-265, UT-266
This commit is contained in:
@@ -77,8 +77,14 @@ export function shouldResumeOnForeground(
|
||||
|
||||
/** What has to be restarted to put picture back on screen, and how. */
|
||||
export interface HandoffReturn {
|
||||
/** Which renderer must be brought back. */
|
||||
target: "html5-element" | "native-backend";
|
||||
/**
|
||||
* Which renderer must be brought back — or `other-item` when the backend is
|
||||
* no longer on the item this player was mounted with, so the player must
|
||||
* switch to `itemId` instead of reloading itself.
|
||||
*/
|
||||
target: "html5-element" | "native-backend" | "other-item";
|
||||
/** The item to switch to; set only for `other-item`. */
|
||||
itemId?: string;
|
||||
/** Absolute position the background audio reached. */
|
||||
position: number;
|
||||
/** Whether playback should be running once it is back. */
|
||||
@@ -107,18 +113,31 @@ export interface HandoffReturn {
|
||||
* `shouldPlay` folds in [shouldResumeOnForeground], so a lockscreen pause during
|
||||
* the handoff still wins over the snapshot taken on the way out.
|
||||
*
|
||||
* TRACES: UR-040, UR-003 | DR-196 | UT-060
|
||||
* An episode that ends while backgrounded advances in the backend, so the item
|
||||
* the native player returns on (`resumeItemId`) can differ from the one this
|
||||
* player was mounted with. Reloading the mounted one brought back the previous
|
||||
* episode at the new one's timestamp; in that case the plan is `other-item`.
|
||||
* A missing `resumeItemId` (queue emptied) keeps the in-place reload.
|
||||
*
|
||||
* TRACES: UR-040, UR-003, UR-023 | DR-196, DR-296 | UT-060, UT-265
|
||||
*/
|
||||
export function planHandoffReturn(opts: {
|
||||
useHtml5Element: boolean;
|
||||
position: number;
|
||||
wasPlaying: boolean;
|
||||
nativeStateKind: string | undefined;
|
||||
mountedItemId?: string | null;
|
||||
resumeItemId?: string | null;
|
||||
}): HandoffReturn {
|
||||
const position = opts.position > 0 ? opts.position : 0;
|
||||
const shouldPlay = shouldResumeOnForeground(opts.wasPlaying, opts.nativeStateKind);
|
||||
if (opts.resumeItemId && opts.resumeItemId !== opts.mountedItemId) {
|
||||
return { target: "other-item", itemId: opts.resumeItemId, position, shouldPlay };
|
||||
}
|
||||
return {
|
||||
target: opts.useHtml5Element ? "html5-element" : "native-backend",
|
||||
position: opts.position > 0 ? opts.position : 0,
|
||||
shouldPlay: shouldResumeOnForeground(opts.wasPlaying, opts.nativeStateKind),
|
||||
position,
|
||||
shouldPlay,
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user