From build-visionos-apps
Add sound to visionOS apps — RealityKit spatial audio on entities and simple non-spatial UI sound effects. Use when playing completion chimes, sound on events, ambient/background audio, or positional 3D sound.
How this skill is triggered — by the user, by Claude, or both
Slash command
/build-visionos-apps:spatial-audio-soundThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Use this skill to add audio: **RealityKit spatial audio** (sound emitted from
Use this skill to add audio: RealityKit spatial audio (sound emitted from entities, positioned in 3D, reverberant in immersive spaces — spatial by default) and simple UI sound effects (a one-shot chime not tied to a 3D location). The driving use case is a completion chime when a long async job finishes, plus a general sound model for spatial apps.
playAudio on an entity with
SpatialAudioComponent.AVAudioPlayer or AudioServicesPlaySystemSound.ChannelAudioComponent (sends channels straight to output, no spatialization).AmbientAudioComponent.Spatial (when you have the model entity in a RealityView):
// Preload once
let chime = try await AudioFileResource(named: "done.wav") // or .load(named:in:)
// On task.status == .completed
modelEntity.spatialAudio = SpatialAudioComponent(gain: -6) // dB attenuation
modelEntity.playAudio(chime) // plays once
Non-spatial (2D generation screen, no entity):
import AVFoundation
var player: AVAudioPlayer?
func playChime() {
guard let url = Bundle.main.url(forResource: "done", withExtension: "wav") else { return }
player = try? AVAudioPlayer(contentsOf: url)
player?.prepareToPlay(); player?.play() // retain `player` or it deinits mid-play
}
// Load
let res = try await AudioFileResource(named: "loop.wav",
configuration: .init(shouldLoop: true))
// or from the content bundle:
let res2 = try await AudioFileResource.load(named: "Chime", from: "Scene.usda",
in: realityKitContentBundle)
// Play (fire-and-forget)
entity.playAudio(res)
// Control playback
let controller = entity.prepareAudio(res) // AudioPlaybackController
controller.play(); controller.pause(); controller.stop()
controller.gain = -10; controller.speed = 1.0
controller.completionHandler = { /* finished */ }
SpatialAudioComponent to shape it
(directivity beam, gain). Use a dedicated empty child entity as the emitter if
you want to aim sound independently of the model.AudioFileGroupResource randomly varies among clips each playAudio (avoids
repetitive SFX).ReverbComponent makes virtual sources sound like the virtual environment in a
.full/.progressive space; only one reverb is active at a time.RealityKitContent) and preloaded, not
loaded on the playback hot path..completed), once, not on every state poll.references/realitykit-spatial-audio.md: AudioFileResource, components, playback controllers, reverb.references/sound-effects-and-playback.md: AVAudioPlayer / AudioToolbox one-shots, AVAudioSession, assets.realitykit-entities (entities/RealityView) for emitter setup.AudioFileResource,
SpatialAudioComponent, Entity/playAudio; WWDC24 "Enhance your spatial
computing app with RealityKit audio".AudioFileResource.AVAudioPlayer go out of scope mid-playback (store it).State spatial vs non-spatial choice, the event that triggers playback, how the asset is preloaded/retained, and the stop/cleanup path.
npx claudepluginhub likw99/agent-plugins --plugin build-visionos-appsGuides creation, editing, and verification of skills for AI coding agents using test-driven development with subagent scenarios. Use when authoring or debugging skills.