using System; using System.Numerics; using AcDream.Core.Physics; using DatReaderWriter.Types; namespace AcDream.App.Audio; /// /// Hook sink for UI-OWNED presentations (the portal tunnel is retail's /// gmSmartBoxUI): sound-bearing hooks go to the interface bus — from /// centre, distance 0, immune to the world-audio suspension that covers /// reveal holds — while every other hook kind forwards to the shared router /// unchanged, so particles/lighting/translucency behave exactly as before. /// /// /// Without this split the tunnel's authored in-flight SoundTweakedHook /// went down the world 3-D path at the synthetic owner's origin: usually /// beyond the −50 dB no-allocate radius AND inside the suspended-transit /// window, so the tunnel interior was silent while the enter/exit cues (on /// the interface bus already) played fine. /// /// public sealed class UiPresentationHookSink : IAnimationHookSink { private readonly IAnimationHookSink _router; private readonly AudioHookSink? _audio; public UiPresentationHookSink(IAnimationHookSink router, AudioHookSink? audio) { _router = router ?? throw new ArgumentNullException(nameof(router)); _audio = audio; } public void OnHook(uint entityId, Vector3 entityWorldPosition, AnimationHook hook) { if (hook is SoundHook or SoundTableHook or SoundTweakedHook) { // With no audio graph (headless/driver-less) the sound hook is // simply dropped — forwarding it to the router would put it back // on the world 3-D path this sink exists to bypass. _audio?.OnUiHook(entityId, hook); return; } _router.OnHook(entityId, entityWorldPosition, hook); } }