Search Docs
Loading...
Skip to content

Insert Audio

Add audio files to your CE.SDK scenes programmatically with the Swift Engine API: create audio blocks, configure timeline position, and control playback properties for background music, voiceovers, and sound effects.

6 mins
estimated time
GitHub

Audio blocks are time-based blocks that play sound alongside the rest of a scene. They have no visual canvas representation — they live on the timeline with their own duration, offset, and volume controls, independent of the video fills attached to graphic blocks.

This guide covers creating audio blocks, configuring their time-based properties, controlling playback, and managing audio blocks in a scene.

Creating an Audio Block#

Create an audio block with create(_:), set its source file with setString(_:property:value:) using the audio/fileURI property, then append it to a page with appendChild(to:child:). Audio blocks must be children of a page to participate in the timeline.

// Create an audio block, point it at an audio file, and append it to a page.
let audioBlock = try engine.block.create(.audio)
try engine.block.setURL(
audioBlock,
property: "audio/fileURI",
value: baseURL.appendingPathComponent("ly.img.audio/audios/far_from_home.m4a"),
)
try engine.block.appendChild(to: page, child: audioBlock)

The source URI can point to any reachable URL or local file. CE.SDK supports M4A, MP3, and WAV formats.

Configuring Time Position#

Audio blocks have time-based properties that control when and how long they play. Use setTimeOffset(_:offset:) for the start position and setDuration(_:duration:) for playback length. Call forceLoadAVResource(_:) first to ensure the audio file is loaded before reading metadata such as total duration.

// Wait for the audio resource to load before reading metadata such as duration.
try await engine.block.forceLoadAVResource(audioBlock)
// Start playback at the beginning of the timeline and clamp the duration to
// the page length or the source file, whichever is shorter.
let totalDuration = try engine.block.getAVResourceTotalDuration(audioBlock)
try engine.block.setTimeOffset(audioBlock, offset: 0)
try engine.block.setDuration(audioBlock, duration: min(totalDuration, 30))

getAVResourceTotalDuration(_:) returns the length of the source audio file in seconds. Use it to clamp the playback duration to the available content or to compute timing relative to the file length.

Adjusting Volume#

Set the audio level with setVolume(_:volume:). Volume is a Float between 0.0 (silent) and 1.0 (full volume) and applies to both preview playback and the exported output.

// Set the audio level. Volume is a Float ranging from 0.0 (silent) to 1.0 (full).
try engine.block.setVolume(audioBlock, volume: 0.8)
let currentVolume = try engine.block.getVolume(audioBlock)
print(String(format: "Audio volume: %.0f%%", currentVolume * 100))

Read the current level back with getVolume(_:). For a deeper look at mixing and force-mute behavior, see Adjust Volume.

Muting Audio#

To silence a block without changing its configured volume, use setMuted(_:muted:). Muting preserves the volume value so you can restore the previous level by setting muted back to false.

// Silence the block without changing the configured volume, then read the state back.
try engine.block.setMuted(audioBlock, muted: true)
let muted = try engine.block.isMuted(audioBlock)
print("Audio muted: \(muted)")

Read the current state with isMuted(_:).

Looping Audio#

Enable continuous playback with setLooping(_:looping:). When looping is enabled, the source repeats until the end of the block’s timeline duration is reached.

// Enable looping so the source repeats until the block's timeline duration ends.
try engine.block.setLooping(audioBlock, looping: true)
let looping = try engine.block.isLooping(audioBlock)
print("Audio looping: \(looping)")

Read the current state with isLooping(_:).

Finding Audio Blocks#

Use find(byType:) with DesignBlockType.audio to retrieve every audio block in the scene. This is useful for building audio management interfaces or for batch operations such as adjusting levels across all tracks at once.

// Iterate every audio block in the scene and read its current configuration.
let audioBlocks = try engine.block.find(byType: .audio)
for block in audioBlocks {
let uri = try engine.block.getString(block, property: "audio/fileURI")
let offset = try engine.block.getTimeOffset(block)
let duration = try engine.block.getDuration(block)
let volume = try engine.block.getVolume(block)
print(String(format: "Audio %u — offset %.1fs, duration %.1fs, volume %.0f%%, uri %@",
block, offset, duration, volume * 100, uri))
}

For each block, read the source URI with getString(_:property:) and the timeline properties with getTimeOffset(_:), getDuration(_:), and getVolume(_:).

Removing Audio#

Call destroy(_:) to remove a block from the scene and free its resources. Destroying a block automatically detaches it from its parent.

// Destroy the block to remove it from the scene and free its resources.
try engine.block.destroy(audioBlock)

API Reference#

MethodCategoryPurpose
block.create(.audio)BlockCreate a new audio block
block.setString(_:property:value:) (audio/fileURI)BlockSet the audio source file
block.getString(_:property:) (audio/fileURI)BlockGet the audio source file
block.appendChild(to:child:)BlockAdd audio to a page
block.forceLoadAVResource(_:)BlockLoad audio metadata
block.getAVResourceTotalDuration(_:)BlockGet total audio file duration in seconds
block.setTimeOffset(_:offset:)BlockSet timeline start position
block.getTimeOffset(_:)BlockGet timeline start position
block.setDuration(_:duration:)BlockSet playback duration
block.getDuration(_:)BlockGet playback duration
block.setVolume(_:volume:)BlockSet volume (0.01.0)
block.getVolume(_:)BlockGet current volume
block.setMuted(_:muted:)BlockMute or unmute audio
block.isMuted(_:)BlockCheck if audio is muted
block.setLooping(_:looping:)BlockEnable or disable looping
block.isLooping(_:)BlockCheck if looping is enabled
block.find(byType:)BlockFind all audio blocks
block.destroy(_:)BlockRemove an audio block

Next Steps#