diff --git a/README.md b/README.md index 98b9b6b..9b5eefe 100644 --- a/README.md +++ b/README.md @@ -35,8 +35,9 @@ Aquarium currently expects the sibling `CultMath` and `CultLib` repos at `E:\Projects\CultMath` and `E:\Projects\CultLib`, or the equivalent `..\..\..\CultMath` / `..\..\..\CultLib` paths from the engine project. -Aquarium consumes `AquaSynth.Dsl` from the repo-local `packages` NuGet feed, -not as a live project reference to `AquaSynth`. This keeps Aquarium +Aquarium consumes `AquaSynth.Faust` from the repo-local `packages` NuGet feed, +not as a live project reference to `AquaSynth`. That package pulls +`AquaSynth.Core` transitively for the built-in patch editor. This keeps Aquarium builds stable while synth work is in flight. To intentionally update that boundary, pack a new synth version and bump the `Aquarium.Engine` package reference: diff --git a/packages/AquaSynth.Dsl.0.1.0-aquasynth.1.nupkg b/packages/AquaSynth.Core.0.1.0-aquasynth.1.nupkg similarity index 79% rename from packages/AquaSynth.Dsl.0.1.0-aquasynth.1.nupkg rename to packages/AquaSynth.Core.0.1.0-aquasynth.1.nupkg index 8c46317..55157c5 100644 Binary files a/packages/AquaSynth.Dsl.0.1.0-aquasynth.1.nupkg and b/packages/AquaSynth.Core.0.1.0-aquasynth.1.nupkg differ diff --git a/packages/AquaSynth.Faust.0.1.0-aquasynth.1.nupkg b/packages/AquaSynth.Faust.0.1.0-aquasynth.1.nupkg new file mode 100644 index 0000000..53f6b22 Binary files /dev/null and b/packages/AquaSynth.Faust.0.1.0-aquasynth.1.nupkg differ diff --git a/scripts/publish-win-x64.ps1 b/scripts/publish-win-x64.ps1 index b101c76..7136692 100644 --- a/scripts/publish-win-x64.ps1 +++ b/scripts/publish-win-x64.ps1 @@ -60,7 +60,8 @@ $requiredFiles = @( "Aquarium.Engine.exe", "Aquarium.Epiphany.dll", "Aquarium.Engine.Contracts.dll", - "AquaSynth.Dsl.dll", + "AquaSynth.Core.dll", + "AquaSynth.Faust.dll", "Tools\Faust\lib\faust.dll", "Tools\Faust\share\faust\stdfaust.lib", "Assets\Aquarium-Engine-Icon.ico", diff --git a/scripts/update-synth-package.ps1 b/scripts/update-synth-package.ps1 index 587f907..295320a 100644 --- a/scripts/update-synth-package.ps1 +++ b/scripts/update-synth-package.ps1 @@ -7,14 +7,20 @@ $ErrorActionPreference = "Stop" $root = Resolve-Path (Join-Path $PSScriptRoot "..") $feed = Join-Path $root "packages" -$project = Join-Path $SynthRepo "src\AquaSynth.Dsl\AquaSynth.Dsl.csproj" +$coreProject = Join-Path $SynthRepo "src\AquaSynth.Core\AquaSynth.Core.csproj" +$faustProject = Join-Path $SynthRepo "src\AquaSynth.Faust\AquaSynth.Faust.csproj" -if (-not (Test-Path $project)) { - throw "AquaSynth.Dsl project not found at $project" +if (-not (Test-Path $coreProject)) { + throw "AquaSynth.Core project not found at $coreProject" +} + +if (-not (Test-Path $faustProject)) { + throw "AquaSynth.Faust project not found at $faustProject" } New-Item -ItemType Directory -Force -Path $feed | Out-Null -dotnet pack $project -c $Configuration -o $feed +dotnet pack $coreProject -c $Configuration -o $feed +dotnet pack $faustProject -c $Configuration -o $feed -Write-Host "Packed AquaSynth.Dsl into $feed" +Write-Host "Packed AquaSynth.Core and AquaSynth.Faust into $feed" Write-Host "If the package version changed, update src\Aquarium.Engine\Aquarium.Engine.csproj to match." diff --git a/src/Aquarium.Engine/Aquarium.Engine.csproj b/src/Aquarium.Engine/Aquarium.Engine.csproj index 1122613..451894a 100644 --- a/src/Aquarium.Engine/Aquarium.Engine.csproj +++ b/src/Aquarium.Engine/Aquarium.Engine.csproj @@ -11,7 +11,7 @@ - + diff --git a/src/Aquarium.Engine/Audio/AquariumSynthHost.cs b/src/Aquarium.Engine/Audio/AquariumSynthHost.cs index 0d92223..5320f8b 100644 --- a/src/Aquarium.Engine/Audio/AquariumSynthHost.cs +++ b/src/Aquarium.Engine/Audio/AquariumSynthHost.cs @@ -1,4 +1,4 @@ -using AquaSynth.Dsl; +using AquaSynth.Faust; namespace Aquarium.Engine.Audio; diff --git a/state/evidence.jsonl b/state/evidence.jsonl index 37ad2da..7d9a71c 100644 --- a/state/evidence.jsonl +++ b/state/evidence.jsonl @@ -68,7 +68,8 @@ {"timestamp":"2026-05-12T21:28:22+01:00","topic":"single-solution-authority","lesson":"Keep one solution inventory for Aquarium. Maintaining both Aquarium.Engine.sln and Aquarium.Engine.slnx created duplicate project authority, Rider confusion, and verification races when both were built against shared obj/bin outputs. Aquarium.Engine.sln is the canonical solution for IDE and CLI work.","files":["Aquarium.Engine.sln","AGENTS.md","README.md","scripts/dev-watch.ps1","state/map.yaml","state/evidence.jsonl"],"source":"user solution authority cleanup"} {"timestamp":"2026-05-12T23:08:00+01:00","topic":"synth-test-ownership","lesson":"Aquarium must not own synth reference truth. Engine tests may smoke-test the runtime synth host boundary, but synth correctness belongs in AquariumSynthCSharp so Aquarium can keep iterating while the synth library is under construction.","files":["tests/Aquarium.Engine.Tests/SynthPlaybackTests.cs","tests/Aquarium.Engine.Tests/Aquarium.Engine.Tests.csproj","state/evidence.jsonl"],"source":"user questioned synth testing ownership"} {"timestamp":"2026-05-13T00:26:00+01:00","topic":"synth-package-boundary","lesson":"Aquarium must not build against the live AquariumSynthCSharp project while a synth agent is mutating it. Consume AquariumSynth.Dsl as a pinned repo-local NuGet package and update that package only by deliberate version bump.","files":["NuGet.config","packages/AquariumSynth.Dsl.0.1.0-aquarium.1.nupkg","src/Aquarium.Engine/Aquarium.Engine.csproj","scripts/update-synth-package.ps1","state/map.yaml","state/memory.json","state/scratch.md","state/evidence.jsonl"],"source":"user asked whether synth-agent work can break Aquarium builds"} -{"timestamp":"2026-05-17T15:15:00+01:00","topic":"aquasynth-native-audio-ownership","lesson":"Aquarium should host completed synth products, not own AquaSynth parsing, Faust emission, native libfaust factory creation, render duration estimation, compile keys, DSP source artifacts, or sample-buffer rendering. Those responsibilities now live in AquaSynth.Dsl through AquaSynthNativeCompiler; AquariumSynthHost keeps scheduling, debounce/status, cache playback, and WASAPI output.","files":["src/Aquarium.Engine/Audio/AquariumSynthHost.cs","src/Aquarium.Engine/Aquarium.Engine.csproj","scripts/update-synth-package.ps1","scripts/publish-win-x64.ps1","state/map.yaml","state/memory.json"],"source":"user asked to finish taking over Aquarium's current audio rendering ownership so the engine does not concern itself with synth internals"} +{"timestamp":"2026-05-17T15:15:00+01:00","topic":"aquasynth-native-audio-ownership","lesson":"Aquarium should host completed synth products, not own AquaSynth parsing, Faust emission, native libfaust factory creation, render duration estimation, compile keys, DSP source artifacts, or sample-buffer rendering. Those responsibilities now live in AquaSynth.Faust through AquaSynthNativeCompiler; AquariumSynthHost keeps scheduling, debounce/status, cache playback, and WASAPI output.","files":["src/Aquarium.Engine/Audio/AquariumSynthHost.cs","src/Aquarium.Engine/Aquarium.Engine.csproj","scripts/update-synth-package.ps1","scripts/publish-win-x64.ps1","state/map.yaml","state/memory.json"],"source":"user asked to finish taking over Aquarium's current audio rendering ownership so the engine does not concern itself with synth internals"} +{"timestamp":"2026-05-17T15:45:00+01:00","topic":"aquasynth-package-split","lesson":"Aquarium consumes AquaSynth.Faust, not a catch-all AquaSynth.Dsl package. AquaSynth.Faust carries the runtime/toolchain surface and pulls AquaSynth.Core transitively for the built-in patch editor's parser/model/built-in script needs.","files":["src/Aquarium.Engine/Aquarium.Engine.csproj","packages/AquaSynth.Core.0.1.0-aquasynth.1.nupkg","packages/AquaSynth.Faust.0.1.0-aquasynth.1.nupkg","scripts/update-synth-package.ps1","scripts/publish-win-x64.ps1","state/map.yaml","state/memory.json","state/scratch.md"],"source":"user pointed out .Dsl no longer described the package and confirmed Aquarium still needs DSL through the Faust dependency"} {"timestamp":"2026-05-13T00:40:00+01:00","topic":"generic-sdf-field-ids","lesson":"Aquarium shared SDF code must not special-case Epiphany object identities. SDF field ids are generic base-plus-object-index metadata; Self, Cursor, and role meaning stay in Epiphany's object table and shaders, while temporal reprojection uses uploaded AquariumSdfObject current/previous centers for every SDF object.","files":["src/Aquarium.Engine/Render/Shaders/D3D12SdfCommon.hlsli","src/Aquarium.Engine/Render/Shaders/D3D12SdfProxy.hlsli","src/Aquarium.Engine/Render/Shaders/D3D12Post.hlsl","src/Aquarium.Epiphany/EpiphanySceneBuilder.cs","docs/epiphany-agent-sdf-visual-language.md","state/memory.json"]} {"timestamp":"2026-05-13T01:05:00+01:00","topic":"sdf-metallic-roughness-pbr","lesson":"SDF surfaces now use the industry-standard metallic-roughness material language: baseColor, metallic, roughness, and emission. The shared shader derives dielectric F0, metal-tinted specular F0, non-metal diffuse color, direct Cook-Torrance GGX specular, Fresnel-gated Lambert diffuse, diffuse irradiance IBL, and roughness-mip PMREM specular from those fields.","files":["src/Aquarium.Engine/Render/Shaders/D3D12SdfCommon.hlsli","src/Aquarium.Engine/Render/Shaders/D3D12SdfProxy.hlsli","src/Aquarium.Epiphany/Shaders","docs/epiphany-agent-sdf-visual-language.md","state/memory.json"],"source":"Khronos glTF 2.0 metallic-roughness material model; Google Filament material model notes"} {"timestamp":"2026-05-13T01:45:00+01:00","topic":"imagination-topology-spec","lesson":"Imagination's visual spec needs topology, not just evocative nouns. The target is a luminous opal seed wrapped by broad translucent curling ribbon-sheets with traced raised rims, visible interior apertures, vertical fountain bias, sparse candidate filaments/sparks, and cool backlog shadow. Trefoil/tube curves may define rim paths, but tubes alone do not satisfy the petal form.","files":["docs/epiphany-agent-sdf-visual-language.md","state/memory.json"],"source":"user supplied imagegen reference and noted current output did not match the imagined impossible flower"} @@ -105,3 +106,4 @@ {"timestamp":"2026-05-14T15:32:00+01:00","topic":"life-balanced-whorl-domain","lesson":"Life needs both sides of the nautilus grammar: a log-spiral whorl solve must physically shape the shell, but it cannot be the only body authority or the form collapses into a hollow C-shell. Union the whorl with a smaller same-domain backing mass, then derive aperture lip, chamber gold, ember reveal, raised ribs, and pearl beads from the shared spiral/aperture fields.","files":["src/Aquarium.Epiphany/Shaders/D3D12LifeAgent.hlsl","state/life-agent-sdf-notes.md","state/evidence.jsonl"],"source":"user rejected the egg lineage and required repeated restart until the spiral shell manifests as geometry"} {"timestamp":"2026-05-14T16:31:00+01:00","topic":"life-curve-first-build","lesson":"When rebuilding Life, do not start by tuning the full organ. First make the log-spiral domain read as a naked curve: ember at the core, roughly two revolutions, and the wide mouth-side lip termination. Only after that curve reads should shell inflation, aperture carving, ember reveal, ribs, and pearl beads be layered back on the same solved domain.","files":["src/Aquarium.Epiphany/Shaders/D3D12LifeAgent.hlsl","state/life-agent-sdf-notes.md","state/evidence.jsonl"],"source":"user corrected the iteration process: build the log spiral one step at a time instead of doing everything at once"} {"lesson":"Shader hot reload edits must update the running process slot Render/Shaders files so D3D12Renderer can rebuild pipelines from its existing shader source root. Client assembly live reload does not change renderer shaderSourceRoot, so treating .hlsl/.hlsli edits as assembly reloads leaves the renderer watching stale slot files.","timestamp":"2026-05-15T17:48:35.6220956+01:00","files":["scripts/dev-watch.ps1","src/Aquarium.Engine/Render/D3D12Renderer.cs"],"topic":"shader-hot-reload-slot-transport"} + diff --git a/state/map.yaml b/state/map.yaml index 6157d3b..51095c7 100644 --- a/state/map.yaml +++ b/state/map.yaml @@ -44,7 +44,8 @@ current_model: dependencies: cult_math: E:\Projects\CultMath cult_lib: E:\Projects\CultLib - aqua_synth_dsl: NuGet package AquaSynth.Dsl 0.1.0-aquasynth.1 from repo-local packages feed + aqua_synth_faust: NuGet package AquaSynth.Faust 0.1.0-aquasynth.1 from repo-local packages feed + aqua_synth_core: transitive NuGet package AquaSynth.Core 0.1.0-aquasynth.1 from repo-local packages feed docs: doctrine: docs/aquarium-engine-doctrine.md engine_client_boundary: docs/engine-client-boundary.md @@ -83,7 +84,7 @@ renderer_state: - SDF light buffer feeds Self emission and direct object lighting; future other Selves should join this light lane, not a generic field-instance table. - Studio2 PMREM and irradiance DDS cubemaps are loaded as D3D12 TextureCubes; PMREM serves roughness-mip specular, irradiance serves Lambertian diffuse IBL for non-metal bodies. - DirectWrite/Direct2D unified debug panel with tabs for Aquarium renderer controls, client-declared debug panels, terminal commands, and engine/client tooling surfaces. - - Aquarium exposes an optional synth/audio hosting boundary through AquariumSynthDocument; Aquarium consumes AquaSynth.Dsl as a pinned repo-local NuGet package so synth-agent construction cannot break Aquarium builds until the package is intentionally updated. + - Aquarium exposes an optional synth/audio hosting boundary through AquariumSynthDocument; Aquarium consumes AquaSynth.Faust as a pinned repo-local NuGet package so synth-agent construction cannot break Aquarium builds until the package is intentionally updated. AquaSynth.Core arrives transitively for patch editor/parser surfaces. - Global GraphicsSettings document feeding render debug, exposure, bloom intensity, and bloom veil. - Temporal resolve uses scene color, metadata, and control history only; dormant event history lanes are cut until a real producer and consumer contract exists. - Isolated Epiphany agent preview renders run through the real D3D12 renderer from src/Aquarium.Epiphany.AgentPreview; preview isolation is owned by a preview-only scene shader, while the engine exposes only final-frame PNG capture. @@ -102,7 +103,7 @@ next_actions: - Keep main as the live development branch. - Keep scripts/verify-boundaries.ps1 green: Aquarium.Engine and Aquarium.Engine.Contracts must not contain Epiphany/client policy nouns such as grid, agent, body, or epiphany. - Verify publish output after every packaging-affecting change. - - Update AquaSynth.Dsl only by packing a new version into packages and changing the pinned PackageReference version deliberately. + - Update AquaSynth.Faust/Core only by packing new versions into packages and changing the pinned PackageReference version deliberately. - Grow renderer debug controls through the Direct2D/DirectWrite overlay path. - Use scripts/render-agent-preview.ps1 for multi-view isolated SDF review before asking the user to judge another agent body iteration. - Follow research/rendering/hdr-pbr-presentation.md before changing HDR exposure, bloom, tonemapping, or display transforms. diff --git a/state/memory.json b/state/memory.json index 7f8198a..f3cc650 100644 --- a/state/memory.json +++ b/state/memory.json @@ -85,7 +85,7 @@ ], "audio": [ "Aquarium exposes an optional audio/synth hosting boundary through contracts; clients declare intent, Aquarium schedules playback and owns device/toolchain integration.", - "Aquarium consumes AquaSynth.Dsl as a pinned repo-local NuGet package. AquaSynth owns synth internals, native Faust compilation, generated DSP manifests, and tests; update the package only by deliberate version bump so visual/renderer work can continue while synth construction changes underneath." + "Aquarium consumes AquaSynth.Faust as a pinned repo-local NuGet package, with AquaSynth.Core arriving transitively for the built-in patch editor/parser surface. AquaSynth owns synth internals, native Faust compilation, generated DSP manifests, and tests; update the package only by deliberate version bump so visual/renderer work can continue while synth construction changes underneath." ], "state_and_reload": [ "CultCache is the client memory organ. Runtime state, camera, renderer knobs, body state, UI state, and future Epiphany connection state should be typed Cult documents.", diff --git a/state/scratch.md b/state/scratch.md index db6fd08..f442d9c 100644 --- a/state/scratch.md +++ b/state/scratch.md @@ -11,8 +11,9 @@ Keep the engine/client boundary strict: debug UI plumbing, and device/toolchain integration. - Aquarium.Epiphany owns client policy, semantic state interpretation, role layout, and render-plan configuration through Aquarium.Engine.Contracts. -- Aquarium consumes AquaSynth.Dsl as a pinned package in the repo-local - `packages` feed. AquaSynth owns synth internals and tests; update +- Aquarium consumes AquaSynth.Faust as a pinned package in the repo-local + `packages` feed; AquaSynth.Core arrives transitively for patch editor/parser + surfaces. AquaSynth owns synth internals and tests; update the package only through an intentional version bump. The renderer work that matters next: