Skip to content

Commit fcb93c0

Browse files
authored
Merge pull request #20 from stagas/dsp
feat: dsp
2 parents c17bfa0 + 58a7cd2 commit fcb93c0

File tree

181 files changed

+10128
-193
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

181 files changed

+10128
-193
lines changed

.github/workflows/deploy.yml

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,8 +31,14 @@ jobs:
3131
with:
3232
node-version: 22.x
3333

34+
- name: Uninstall dev deps with scripts
35+
run: npm remove @vite-pwa/assets-generator --force --ignore-scripts=true
36+
3437
- name: Install dependencies
35-
run: npm install --ignore-scripts --force
38+
run: npm i --force --ignore-scripts=true
39+
40+
- name: Install dev deps with scripts
41+
run: npm i @vite-pwa/assets-generator -D --force
3642

3743
- name: Build
3844
run: bun run build

.github/workflows/preview.yml

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -51,8 +51,14 @@ jobs:
5151
with:
5252
node-version: 22.x
5353

54+
- name: Uninstall dev deps with scripts
55+
run: npm remove @vite-pwa/assets-generator --force --ignore-scripts=true
56+
5457
- name: Install dependencies
55-
run: npm install --ignore-scripts --force
58+
run: npm i --force --ignore-scripts=true
59+
60+
- name: Install dev deps with scripts
61+
run: npm i @vite-pwa/assets-generator -D --force
5662

5763
- name: Build
5864
run: bun run build

admin/client.tsx

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,11 @@
1+
import '~/lib/watcher.ts'
2+
13
import { cleanup, hmr, mount } from 'sigui'
24
import { Admin } from '~/admin/Admin.tsx'
35
import { setState, state } from '~/src/state.ts'
46

57
export const start = mount('#container', target => {
6-
target.replaceChildren(<Admin />)
8+
target.replaceChildren(<Admin /> as HTMLElement)
79
return cleanup
810
})
911

admin/index.html

Lines changed: 1 addition & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -9,12 +9,8 @@
99
<title>Vasi - Admin</title>
1010
</head>
1111
<body>
12-
<script type="module">
13-
// KEEP: required for AssemblyScript interop.
14-
globalThis.unmanaged = () => {};
15-
</script>
1612
<div id="container"></div>
13+
<script src="/as-interop.js"></script>
1714
<script src="./client.tsx" type="module"></script>
18-
<script src="../lib/watcher.ts" type="module"></script>
1915
</body>
2016
</html>

api/auth/actions.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
// deno-lint-ignore-file require-await
22
import { hash } from 'jsr:@denorg/[email protected]'
3-
import { createCookie, randomHash, timeout } from 'utils'
3+
import { createCookie, timeout } from 'utils'
44
import { ADMINS } from '~/api/admin/actions.ts'
55
import { UserLogin, UserRegister, UserSession } from "~/api/auth/types.ts"
66
import { kv } from '~/api/core/app.ts'
@@ -60,7 +60,7 @@ export async function getUser(nickOrEmail: string) {
6060
export async function loginUser(ctx: Context, nick: string) {
6161
ctx.log('Login:', nick)
6262

63-
const sessionId = randomHash()
63+
const sessionId = crypto.randomUUID()
6464
const sessionKey = ['session', sessionId]
6565

6666
const now = new Date()
@@ -90,7 +90,7 @@ export async function loginUser(ctx: Context, nick: string) {
9090
}
9191

9292
async function generateEmailVerificationToken(email: string) {
93-
const token = randomHash()
93+
const token = crypto.randomUUID()
9494
const now = new Date()
9595
const expires = new Date(now)
9696
const expireAfterHours = 3 * 24 // 3 days
@@ -264,7 +264,7 @@ export async function forgotPassword(ctx: Context, email: string) {
264264
return
265265
}
266266

267-
const token = randomHash()
267+
const token = crypto.randomUUID()
268268
const now = new Date()
269269
const expires = new Date(now)
270270
const expireAfterMinutes = 15

api/oauth/routes/common.ts

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import { randomHash } from 'utils'
21
import { z } from 'zod'
32
import { kv } from '~/api/core/app.ts'
43
import { Router } from '~/api/core/router.ts'
@@ -30,7 +29,7 @@ export function mount(app: Router) {
3029
provider,
3130
})
3231

33-
const oauthStateId = randomHash()
32+
const oauthStateId = crypto.randomUUID()
3433
await kv.set(['oauthState', oauthStateId], state, {
3534
expireIn: 30 * 60 * 1000
3635
})

api/oauth/routes/github.ts

Lines changed: 2 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,3 @@
1-
import { randomHash } from 'utils'
21
import { z } from 'zod'
32
import { getUserByEmail, loginUser } from '~/api/auth/actions.ts'
43
import { kv } from '~/api/core/app.ts'
@@ -49,7 +48,7 @@ const OAuthUser = z.union([
4948

5049
const headers = {
5150
'content-type': 'application/json',
52-
'user-agent': 'cfw-oauth-login',
51+
'user-agent': 'oauth-login',
5352
accept: 'application/json',
5453
}
5554

@@ -104,7 +103,7 @@ export function mount(app: Router) {
104103
}
105104

106105
// create oauth session
107-
const id = randomHash()
106+
const id = crypto.randomUUID()
108107
const now = new Date()
109108
const expires = new Date(now)
110109
expires.setMinutes(expires.getMinutes() + 30)
@@ -122,15 +121,6 @@ export function mount(app: Router) {
122121
url.searchParams.set('id', id)
123122
const res = ctx.redirect(302, url.href)
124123

125-
// res.headers.set('set-cookie', createCookie(
126-
// 'oauth',
127-
// id,
128-
// expires,
129-
// 'HttpOnly',
130-
// 'Secure',
131-
// 'SameSite=Strict'
132-
// ))
133-
134124
return res
135125
}])
136126
}

as/assembly/common/env.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
// @ts-ignore
2+
@external('env', 'log')
3+
export declare function log(x: i32): void

as/assembly/dsp/constants.ts

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
export const BUFFER_SIZE = 2048
2+
export const MAX_AUDIOS = 1024
3+
export const MAX_FLOATS = 4096
4+
export const MAX_LISTS = 4096
5+
export const MAX_LITERALS = 4096
6+
export const MAX_OPS = 4096
7+
export const MAX_RMSS = 1024
8+
export const MAX_SCALARS = 4096
9+
export const MAX_SOUNDS = 16
10+
export const MAX_TRACKS = 16
11+
export const MAX_VALUES = 1024
Lines changed: 155 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,155 @@
1+
import { nextPowerOfTwo } from '../../util'
2+
import { ANTIALIAS_WAVETABLE_OVERSAMPLING, WAVETABLE_SIZE } from './constants'
3+
import { fft } from './fft'
4+
5+
class Real {
6+
@inline static saw(real: StaticArray<f32>, i: u32, j: u32): void {
7+
const temp: f32 = -1.0 / f32(i)
8+
real[i] = temp
9+
real[j] = -temp
10+
}
11+
12+
@inline static ramp(real: StaticArray<f32>, i: u32, j: u32): void {
13+
const temp: f32 = -1.0 / f32(i)
14+
real[i] = -temp
15+
real[j] = temp
16+
}
17+
18+
@inline static sqr(real: StaticArray<f32>, i: u32, j: u32): void {
19+
const temp: f32 = i & 0x01 ? 1.0 / f32(i) : 0.0
20+
real[i] = -temp
21+
real[j] = temp
22+
}
23+
24+
static sign: f32 = 1.0
25+
@inline static tri(real: StaticArray<f32>, i: u32, j: u32): void {
26+
const temp: f32 = i & 0x01 ? 1.0 / f32(i * i) * (this.sign = -this.sign) : 0.0
27+
real[i] = temp
28+
real[j] = -temp
29+
}
30+
}
31+
32+
export class AntialiasWavetable {
33+
real: StaticArray<f32>
34+
imag: StaticArray<f32>
35+
freqs: StaticArray<f32>
36+
topFreq: f64
37+
maxHarms: u32
38+
numOfTables: u32
39+
tableLength: u32
40+
tableMask: u32
41+
tableIndex: u32 = 0
42+
stepShift: i32 = 0
43+
sampleRate: u32
44+
45+
saw: StaticArray<StaticArray<f32>>
46+
ramp: StaticArray<StaticArray<f32>>
47+
sqr: StaticArray<StaticArray<f32>>
48+
tri: StaticArray<StaticArray<f32>>
49+
50+
constructor(sampleRate: u32) {
51+
let topFreq: f64 = 10
52+
let maxHarms: u32 = u32(f64(sampleRate) / (3.0 * topFreq) + 0.5)
53+
const tableLength: u32 = nextPowerOfTwo(maxHarms) * 2 * ANTIALIAS_WAVETABLE_OVERSAMPLING
54+
const tableMask: u32 = (tableLength - 1) << 2
55+
const numOfTables: u32 = u32(Math.log2(f64(maxHarms)) + 1)
56+
57+
// logi(tableLength)
58+
const saw = new StaticArray<StaticArray<f32>>(numOfTables)
59+
const ramp = new StaticArray<StaticArray<f32>>(numOfTables)
60+
const sqr = new StaticArray<StaticArray<f32>>(numOfTables)
61+
const tri = new StaticArray<StaticArray<f32>>(numOfTables)
62+
for (let i: u32 = 0; i < numOfTables; i++) {
63+
saw[i] = new StaticArray<f32>(tableLength)
64+
ramp[i] = new StaticArray<f32>(tableLength)
65+
sqr[i] = new StaticArray<f32>(tableLength)
66+
tri[i] = new StaticArray<f32>(tableLength)
67+
}
68+
69+
const freqs = new StaticArray<f32>(numOfTables)
70+
const real = new StaticArray<f32>(tableLength)
71+
const imag = new StaticArray<f32>(tableLength)
72+
73+
this.real = real
74+
this.imag = imag
75+
this.freqs = freqs
76+
77+
this.saw = saw
78+
this.ramp = ramp
79+
this.sqr = sqr
80+
this.tri = tri
81+
82+
this.sampleRate = sampleRate
83+
this.topFreq = topFreq
84+
this.maxHarms = maxHarms
85+
this.numOfTables = numOfTables
86+
this.tableLength = tableLength
87+
this.tableMask = tableMask
88+
this.stepShift = i32(Math.log2(f64(WAVETABLE_SIZE))) - i32(Math.log2(f64(this.tableLength)))
89+
90+
this.makeTables(this.saw, Real.saw)
91+
this.makeTables(this.ramp, Real.ramp)
92+
this.makeTables(this.sqr, Real.sqr)
93+
this.makeTables(this.tri, Real.tri)
94+
}
95+
96+
getTableIndex(hz: f32): u32 {
97+
let tableIndex: u32 = 0
98+
while (
99+
hz >= this.freqs[tableIndex]
100+
&& tableIndex < this.numOfTables - 1
101+
) {
102+
tableIndex = tableIndex + 1
103+
}
104+
return tableIndex
105+
}
106+
107+
makeTables(target: StaticArray<StaticArray<f32>>, fn: (real: StaticArray<f32>, i: u32, j: u32) => void): void {
108+
let topFreq: f64 = this.topFreq
109+
let i: u32 = 0
110+
for (let harms: u32 = this.maxHarms; harms >= 1; harms >>= 1) {
111+
this.defineWaveform(harms, fn)
112+
this.makeWavetable(target[i])
113+
this.freqs[i] = f32(topFreq)
114+
topFreq = topFreq * 2
115+
i = i + 1
116+
}
117+
}
118+
119+
defineWaveform(harms: u32, fn: (real: StaticArray<f32>, i: u32, j: u32) => void): void {
120+
if (harms > (this.tableLength >> 1)) {
121+
harms = (this.tableLength >> 1)
122+
}
123+
124+
this.imag.fill(0)
125+
this.real.fill(0)
126+
127+
Real.sign = 1.0
128+
for (let i: u32 = 1, j: u32 = this.tableLength - 1; i <= harms; i++, j--) {
129+
fn(this.real, i, j)
130+
}
131+
}
132+
133+
writeSaw(i: u32, j: u32): void {
134+
const temp: f32 = -1.0 / f32(i)
135+
this.real[i] = temp
136+
this.real[j] = -temp
137+
}
138+
139+
makeWavetable(wave: StaticArray<f32>): void {
140+
fft(this.tableLength, this.real, this.imag)
141+
142+
// calc normal
143+
let scale: f32
144+
let max: f32 = 0.0
145+
for (let i: u32 = 0; i < this.tableLength; i++) {
146+
let temp: f32 = Mathf.abs(this.imag[i])
147+
if (max < temp) max = temp
148+
}
149+
scale = 1.0 / max * 0.999
150+
151+
for (let idx: u32 = 0; idx < this.tableLength; idx++) {
152+
wave[idx] = this.imag[idx] * scale
153+
}
154+
}
155+
}

0 commit comments

Comments
 (0)