fixed audio context

This commit is contained in:
Corey Johnson 2025-07-02 10:54:14 -07:00
parent 8843349413
commit 1e705db7c3
6 changed files with 12 additions and 56 deletions

View File

@ -1,7 +1,7 @@
import KV from "@workshop/shared/kv"
import { submitAction, useAction, type Head, type LoaderProps } from "@workshop/nano-remix"
import { TodoEditor } from "@workshop/todo"
import { useCallback } from "hono/jsx/dom"
import { TodoEditor } from "@workshop/todo"
export const head: Head = {
title: "Todos",

View File

@ -99,53 +99,6 @@ const getStorePath = <T extends keyof Keys>(key: T): string => {
return join(kvDir, `${key}.v${version}.json`)
}
// Migration function to convert from old kv.json to new individual files
const migrateFromOldFormat = async (): Promise<void> => {
timeBomb("2025-07-01", "This migration isn't needed anymore. Delete it.")
try {
const rootDir = process.env.DATA_DIR ?? join(import.meta.dir, "..")
const oldKvPath = join(rootDir, "data/kv.json")
const oldFile = Bun.file(oldKvPath)
if (!(await oldFile.exists())) {
return // No old file to migrate
}
console.log("Migrating from old kv.json format to new individual files...")
const oldData = await oldFile.json()
const migrations: Promise<void>[] = []
// Migrate each key from the old format
for (const [oldKey, value] of Object.entries(oldData)) {
const keyParts = oldKey.split(".")
const keyName = keyParts[0] as keyof Keys
// Only migrate if it's a valid key we recognize and value exists
if (keyName in keyVersions && value !== undefined && value !== null) {
console.log(`Migrating key: ${keyName}`)
migrations.push(writeStore(keyName, value as Keys[typeof keyName]))
}
}
await Promise.all(migrations)
const backupPath = join(rootDir, "data/kv.json.backup")
await Bun.write(backupPath, await oldFile.text())
await oldFile.delete()
console.log("Migration completed successfully. Old file backed up as kv.json.backup")
} catch (error) {
console.error("Error during migration:", error)
}
}
if (typeof process !== "undefined") {
// If this is running via bun, run the migration
await migrateFromOldFormat()
}
export default { set, get, remove, update }
export type Conversation = { message: string; role: "user" | "assistant" }

View File

@ -29,7 +29,8 @@ export const timeBomb = (date: string, message: string) => {
const targetDate = DateTime.fromISO(date)
if (now > targetDate) {
console.warn(`💣 Time bomb triggered: ${message}`)
const stack = new Error().stack
console.warn(`💣 Time bomb triggered: ${message}\n${stack}`)
}
}

View File

@ -1,13 +1,14 @@
import { RangeSetBuilder } from "@codemirror/state"
import { Decoration, EditorView } from "@codemirror/view"
import { zzfx } from "zzfx"
export function triggerTodoCompletionEffect(view: EditorView, pos: number) {
export const triggerTodoCompletionEffect = async (view: EditorView, pos: number) => {
const builder = new RangeSetBuilder<Decoration>()
const line = view.state.doc.lineAt(pos)
builder.add(pos, pos, Decoration.line({ class: "animate-completion" }))
builder.finish()
// Only play sound in browser environment (not during SSR)
const { zzfx } = await import("zzfx")
zzfx(...[0.8, , 617, 0.02, 0.03, 0.18, , 3, -0.1, , 358, 0.06, -0.01, , , , 0.02, 1.09, 0.05, 0.02, -1213]) // Pickup 58 - Mutation 5
}

View File

@ -14,7 +14,7 @@ export const buildKeyBindings = (
): Command[] => [
{
label: "Insert empty",
key: "alt-h",
key: "alt-l",
preventDefault: true,
run: (view: EditorView) => {
// if the line is empty, insert a new todo item
@ -58,7 +58,7 @@ export const buildKeyBindings = (
},
{
label: "Toggle the todo timer",
key: "alt-Enter",
key: "alt-k",
preventDefault: true,
run: (view: EditorView) => {
const timerPlugin = view.plugin(todoTimer)
@ -71,7 +71,7 @@ export const buildKeyBindings = (
},
{
label: "Move all done todos to # Done",
key: "alt-k",
key: "alt-,",
preventDefault: true,
run: (view: EditorView) => {
moveToDone(view)

View File

@ -1,7 +1,6 @@
import { EditorView, ViewPlugin, ViewUpdate, WidgetType, Decoration } from "@codemirror/view"
import { RangeSetBuilder } from "@codemirror/state"
import { Todo } from "@/todo"
import { zzfx } from "zzfx"
class CountdownWidget extends WidgetType {
duration: number
@ -52,7 +51,7 @@ class CountdownWidget extends WidgetType {
this.toggleTimer()
})
const updateTimer = () => {
const updateTimer = async () => {
if (this.startedAt) {
span.classList.add("running")
} else {
@ -72,6 +71,8 @@ class CountdownWidget extends WidgetType {
span.classList.remove("running")
span.classList.add("finished")
this.stopTimer()
// Only play sound in browser environment (not during SSR)
const { zzfx } = await import("zzfx")
zzfx(...[1.2, , 117, 0.03, 0.01, 0.12, , 2.1, , , , , , 1.3, , 0.3, 0.08, 0.6, 0.1, , 1946]) // Hit 107
this.showNotification()
return