fix: make timeline activation durable and visible
This commit is contained in:
@@ -62,6 +62,10 @@ export function SignageDashboard({
|
||||
|
||||
const selectedGroupId =
|
||||
groupId ?? (groups.state.status === "ready" ? groups.state.value?.groups[0]?.id : undefined);
|
||||
const selectedGroup =
|
||||
groups.state.status === "ready"
|
||||
? groups.state.value?.groups.find((candidate) => candidate.id === selectedGroupId)
|
||||
: undefined;
|
||||
|
||||
return (
|
||||
<>
|
||||
@@ -93,18 +97,23 @@ export function SignageDashboard({
|
||||
{
|
||||
content: (
|
||||
<TimelinesPanel
|
||||
{...(selectedGroup
|
||||
? {
|
||||
activeGroupName: selectedGroup.name,
|
||||
activeTimelineId: selectedGroup.playback.activeTimelineId,
|
||||
}
|
||||
: {})}
|
||||
api={api}
|
||||
canManage={mayManageTimelines}
|
||||
onActivate={
|
||||
mayControl && selectedGroupId !== undefined
|
||||
? (timelineId) => {
|
||||
void api
|
||||
.send("POST", `playback/${selectedGroupId}/activate`, {
|
||||
timelineId,
|
||||
when: "now",
|
||||
})
|
||||
.then(() => setTab("playback"))
|
||||
.catch(() => setTab("playback"));
|
||||
? async (timelineId) => {
|
||||
await api.send("POST", `playback/${selectedGroupId}/activate`, {
|
||||
timelineId,
|
||||
when: "now",
|
||||
});
|
||||
groups.reload();
|
||||
setTab("playback");
|
||||
}
|
||||
: undefined
|
||||
}
|
||||
|
||||
@@ -70,6 +70,16 @@ export function PlaybackPanel({
|
||||
command.run(() => api.send("POST", `playback/${groupId}/${path}`, body));
|
||||
}
|
||||
|
||||
function timelineLabel(timelineId: string): string {
|
||||
if (timelines.state.status !== "ready") {
|
||||
return timelineId;
|
||||
}
|
||||
return (
|
||||
timelines.state.value.timelines.find((timeline) => timeline.id === timelineId)?.name ??
|
||||
timelineId
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="signage-columns">
|
||||
<Panel
|
||||
@@ -108,6 +118,11 @@ export function PlaybackPanel({
|
||||
) : (
|
||||
<div className="signage-playback" data-testid="signage-playback">
|
||||
<div className="signage-playback__status">
|
||||
{value.snapshot.activeTimelineId === null ? undefined : (
|
||||
<Badge tone="success">
|
||||
{`Active: ${timelineLabel(value.snapshot.activeTimelineId)}`}
|
||||
</Badge>
|
||||
)}
|
||||
<Badge
|
||||
tone={
|
||||
value.snapshot.transport === "playing"
|
||||
|
||||
@@ -42,11 +42,15 @@ export function TimelinesPanel({
|
||||
settings,
|
||||
canManage,
|
||||
onActivate,
|
||||
activeTimelineId,
|
||||
activeGroupName,
|
||||
}: {
|
||||
readonly api: SignageApi;
|
||||
readonly settings: SettingsResponse;
|
||||
readonly canManage: boolean;
|
||||
readonly onActivate: ((timelineId: string) => void) | undefined;
|
||||
readonly onActivate: ((timelineId: string) => Promise<void>) | undefined;
|
||||
readonly activeTimelineId?: string | null;
|
||||
readonly activeGroupName?: string;
|
||||
}): ReactElement {
|
||||
const timelines = useResource(
|
||||
() => api.get<{ timelines: readonly TimelineSummary[] }>("timelines"),
|
||||
@@ -62,6 +66,7 @@ export function TimelinesPanel({
|
||||
setNewName("");
|
||||
timelines.reload();
|
||||
});
|
||||
const activation = useAction();
|
||||
|
||||
return (
|
||||
<div className="signage-columns">
|
||||
@@ -117,6 +122,11 @@ export function TimelinesPanel({
|
||||
<TableRow key={timeline.id} selected={timeline.id === selectedId}>
|
||||
<TableCell>
|
||||
<Button onClick={() => setSelectedId(timeline.id)}>{timeline.name}</Button>
|
||||
{timeline.id === activeTimelineId ? (
|
||||
<Badge tone="success">
|
||||
{activeGroupName ? `Active in ${activeGroupName}` : "Active"}
|
||||
</Badge>
|
||||
) : undefined}
|
||||
</TableCell>
|
||||
<TableCell>
|
||||
{timeline.eligibleFrom === null && timeline.eligibleUntil === null
|
||||
@@ -126,8 +136,12 @@ export function TimelinesPanel({
|
||||
<TableCell>{timeline.revision}</TableCell>
|
||||
<TableCell>
|
||||
{onActivate === undefined ? undefined : (
|
||||
<Button onClick={() => onActivate(timeline.id)} variant="primary">
|
||||
Activate
|
||||
<Button
|
||||
disabled={activation.pending || timeline.id === activeTimelineId}
|
||||
onClick={() => activation.run(() => onActivate(timeline.id))}
|
||||
variant="primary"
|
||||
>
|
||||
{timeline.id === activeTimelineId ? "Active" : "Activate"}
|
||||
</Button>
|
||||
)}
|
||||
</TableCell>
|
||||
@@ -139,6 +153,7 @@ export function TimelinesPanel({
|
||||
{ label: "Loading timelines…", onRetry: timelines.reload },
|
||||
)}
|
||||
<FailureNote failure={create.failure} />
|
||||
<FailureNote failure={activation.failure} />
|
||||
</Panel>
|
||||
|
||||
{selectedId === undefined ? undefined : (
|
||||
|
||||
Reference in New Issue
Block a user