Skip to content

Commit 482bbe0

Browse files
committed
feat: start of re-write for sounder 2.0.0
1 parent 8c7c8b7 commit 482bbe0

13 files changed

Lines changed: 234 additions & 206 deletions

app/lib/broadcast.server.ts

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -3,27 +3,25 @@ import {asyncForEach} from '@arcath/utils'
33
import {getPrisma} from './prisma.server'
44
import {addJob} from './queues.server'
55

6-
export const broadcast = async (
7-
zone: string,
8-
sound: string,
9-
times: number = 1
10-
) => {
6+
/**
7+
*
8+
* @param zone The ID of the Zone to broadcase to
9+
* @param sounds An array as a JSON string of IDS to play.
10+
* @returns
11+
*/
12+
export const broadcast = async (zone: string, sounds: string) => {
1113
const prisma = getPrisma()
1214

1315
const z = await prisma.zone.findFirstOrThrow({
1416
where: {id: zone},
1517
include: {sounders: {include: {sounder: true}}}
1618
})
1719

18-
const audio = await prisma.audio.findFirstOrThrow({where: {id: sound}})
19-
2020
return asyncForEach(z.sounders, async ({sounder}) => {
2121
await addJob('broadcast', {
2222
ip: sounder.ip,
2323
key: sounder.key,
24-
fileName: audio.fileName,
25-
ringerWire: audio.ringerWire,
26-
times
24+
sounds
2725
})
2826
})
2927
}

app/lib/hooks/use-local-storage.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,3 +31,7 @@ export const useStatefulLocalStorage = <ValueType extends string>(
3131

3232
return [value, set] as const
3333
}
34+
35+
export const clearLocalStorage = (key: string) => {
36+
localStorage.removeItem(key)
37+
}

app/lib/queues.server.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,9 +9,7 @@ export type Jobs = {
99
broadcast: {
1010
ip: string
1111
key: string
12-
fileName: string
13-
ringerWire: string
14-
times: number
12+
sounds: string
1513
}
1614
lockdown: {ip: string; key: string}
1715
outboundWebhook: {target: string; key: string}

app/routes/broadcast._index.tsx

Lines changed: 2 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -43,14 +43,9 @@ const Broadcast = () => {
4343
<Actions
4444
actions={[
4545
{
46-
label: 'Existing Sound',
46+
label: 'Build Broadcast',
4747
color: 'bg-blue-300',
48-
onClick: () => navigate('/broadcast/sound')
49-
},
50-
{
51-
label: 'New Text to Speech',
52-
color: 'bg-blue-300',
53-
onClick: () => navigate('/broadcast/tts')
48+
onClick: () => navigate('/broadcast/builder')
5449
}
5550
]}
5651
/>

app/routes/broadcast.builder.tsx

Lines changed: 153 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,153 @@
1+
import {
2+
type LoaderFunctionArgs,
3+
type MetaFunction,
4+
redirect
5+
} from '@remix-run/node'
6+
import {useNavigate, useLoaderData, useSearchParams} from '@remix-run/react'
7+
import {useState, useEffect} from 'react'
8+
9+
import {getPrisma} from '~/lib/prisma.server'
10+
import {pageTitle, INPUT_CLASSES} from '~/lib/utils'
11+
import {checkSession} from '~/lib/session'
12+
import {Actions, Page, FormElement} from '~/lib/ui'
13+
import {
14+
useStatefulLocalStorage,
15+
clearLocalStorage
16+
} from '~/lib/hooks/use-local-storage'
17+
18+
export const meta: MetaFunction = () => {
19+
return [{title: pageTitle('Broadcast', 'Sound')}]
20+
}
21+
22+
export const loader = async ({request}: LoaderFunctionArgs) => {
23+
const result = await checkSession(request)
24+
25+
if (!result) {
26+
return redirect('/login')
27+
}
28+
29+
const prisma = getPrisma()
30+
31+
const sounds = await prisma.audio.findMany({orderBy: {name: 'asc'}})
32+
33+
return {sounds}
34+
}
35+
36+
const BroadcastSound = () => {
37+
const {sounds} = useLoaderData<typeof loader>()
38+
const navigate = useNavigate()
39+
const [LSqueue, setLSQueue] = useStatefulLocalStorage('broadcast-queue', '[]')
40+
const [selectedSound, setSelectedSound] = useState(sounds[0].id)
41+
const [searchParams] = useSearchParams()
42+
43+
const queue = JSON.parse(LSqueue) as string[]
44+
45+
const setQueue = (array: string[]) => {
46+
setLSQueue(JSON.stringify(array) as any)
47+
}
48+
49+
useEffect(() => {
50+
if (searchParams.get('tts') !== null) {
51+
setQueue([...queue, searchParams.get('tts')!])
52+
}
53+
}, [searchParams])
54+
55+
return (
56+
<Page title="Broadcast Builder">
57+
<div className="w-full bg-gray-100 rounded-3xl h-1.5 my-4 ">
58+
<div
59+
role="progressbar"
60+
className="bg-indigo-600 h-1.5 rounded-3xl"
61+
style={{width: `25%`}}
62+
/>
63+
</div>
64+
<form method="post" action="/broadcast/zone">
65+
<FormElement label="Sound" helperText="The sound to add to the queue.">
66+
<select
67+
name="sound"
68+
className={INPUT_CLASSES}
69+
defaultValue={sounds[0].id}
70+
onChange={e => {
71+
setSelectedSound(e.target.value)
72+
}}
73+
>
74+
{sounds.map(({id, name}) => {
75+
return (
76+
<option key={id} value={id}>
77+
{name}
78+
</option>
79+
)
80+
})}
81+
</select>
82+
</FormElement>
83+
<input type="hidden" name="queue" value={LSqueue} />
84+
<div>
85+
{queue.map((queuedId, i) => {
86+
const sound = sounds.filter(({id}) => {
87+
return id === queuedId
88+
})[0]
89+
90+
return (
91+
<div
92+
key={`${sound.id}-${i}`}
93+
className="border-b border-b-stone-100 mb-2 pb-2"
94+
>
95+
{sound.name}{' '}
96+
<button
97+
className="cursor-pointer"
98+
onClick={e => {
99+
e.preventDefault()
100+
setQueue([
101+
...queue.filter((v, di) => {
102+
return di !== i
103+
})
104+
])
105+
}}
106+
>
107+
108+
</button>
109+
</div>
110+
)
111+
})}
112+
</div>
113+
<Actions
114+
actions={[
115+
{
116+
label: 'Back',
117+
color: 'bg-stone-200',
118+
onClick: e => {
119+
e.preventDefault()
120+
navigate('/broadcast')
121+
}
122+
},
123+
{
124+
label: 'Add',
125+
color: 'bg-green-300',
126+
onClick: e => {
127+
e.preventDefault()
128+
setQueue([...queue, selectedSound])
129+
}
130+
},
131+
{
132+
label: 'Create new TTS',
133+
color: 'bg-green-300',
134+
onClick: e => {
135+
e.preventDefault()
136+
navigate('/broadcast/tts')
137+
}
138+
},
139+
{
140+
label: 'Next',
141+
color: 'bg-blue-300',
142+
onClick: () => {
143+
clearLocalStorage('broadcast-queue')
144+
}
145+
}
146+
]}
147+
/>
148+
</form>
149+
</Page>
150+
)
151+
}
152+
153+
export default BroadcastSound

app/routes/broadcast.finish.tsx

Lines changed: 8 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -27,20 +27,18 @@ export const action = async ({request}: ActionFunctionArgs) => {
2727

2828
const formData = await request.formData()
2929

30-
const sound = formData.get('sound') as string | undefined
30+
const queue = formData.get('queue') as string | undefined
3131
const zone = formData.get('zone') as string | undefined
3232
const desktopGroup = formData.get('desktopGroup') as string | undefined
33-
const count = formData.get('count') as string | undefined
3433

35-
invariant(sound)
34+
invariant(queue)
3635
invariant(zone)
3736
invariant(desktopGroup)
38-
invariant(count)
3937

4038
if (zone !== '_') {
41-
await broadcast(zone, sound, parseInt(count))
39+
await broadcast(zone, queue)
4240
}
43-
if (desktopGroup !== '_') {
41+
/*if (desktopGroup !== '_') {
4442
const audio = await prisma.audio.findFirstOrThrow({where: {id: sound}})
4543
4644
const playData = JSON.stringify({
@@ -53,9 +51,9 @@ export const action = async ({request}: ActionFunctionArgs) => {
5351
where: {id: desktopGroup},
5452
data: {playData}
5553
})
56-
}
54+
}*/
5755

58-
return {sound, zone, desktopGroup, count}
56+
return {queue, zone, desktopGroup}
5957
}
6058

6159
const BroadcastFinish = () => {
@@ -66,16 +64,15 @@ const BroadcastFinish = () => {
6664
return <div>Error</div>
6765
}
6866

69-
const {sound, zone, desktopGroup, count} = data
67+
const {queue, zone, desktopGroup} = data
7068

7169
return (
7270
<Page title="Broadcast">
7371
<div className="box mb-4">Broadcast Sent!</div>
7472
<form method="post">
75-
<input type="hidden" name="sound" value={sound} />
73+
<input type="hidden" name="queue" value={queue} />
7674
<input type="hidden" name="zone" value={zone} />
7775
<input type="hidden" name="desktopGroup" value={desktopGroup} />
78-
<input type="hidden" name="count" value={count} />
7976
<Actions
8077
actions={[
8178
{

app/routes/broadcast.sound.tsx

Lines changed: 0 additions & 92 deletions
This file was deleted.

0 commit comments

Comments
 (0)