moon-wav

    MoonBit 原生 WAV 音频解码库 | A native MoonBit WAV audio decoding library

    wav
    audio
    pcm
    decode
    encode
    RIFF
    float
    Download zip
    Author
    Version
    0.3.0
    License
    Apache-2.0
    Last updated
    2 months ago
    Downloads
    33

    No dependencies

    #🎵 moon-wav

    MoonBit 原生 WAV 音频库

    A native MoonBit WAV audio library.

    一个纯 MoonBit 实现的 WAV 音频库,支持解码、编码、格式转换、音频操作、波形生成和音频分析。

    License mooncakes.io

    #✨ Features / 功能特性

    • WAV 解码 - 支持 8/16/24/32 位 PCM 和 IEEE 754 浮点格式
    • WAV 编码 - 将音频数据编码为标准 WAV 文件
    • 格式验证 - 详细的 WAV 文件格式检查和警告
    • 格式转换 - 位深转换、声道转换、采样率重采样
    • 音频操作 - 裁剪、拼接、音量调整、混音、淡入淡出、反转
    • 音频效果 - 回声、延迟、归一化、软限幅、低通/高通滤波
    • 波形生成 - 正弦波、方波、锯齿波、三角波、噪声、啁啾
    • 音频分析 - 峰值、RMS、直流偏移、过零率、削波检测、静音检测
    • 工具函数 - 声道分离/合并、重复、填充、交叉相关

    #📦 Installation

    moon add bw448/moon-wav

    #🚀 Quick Start

    fn main {
    // Generate a 440Hz sine wave
    let audio = generate_sine_wav(440.0, 16000.0, 44100, 1.0, 16)

    // Encode to WAV format
    let wav_bytes = encode(audio)
    println("Generated " + wav_bytes.length().to_string() + " bytes")

    // Decode and analyze
    match decode(wav_bytes) {
    Ok(decoded) => {
    let analysis = analyze(decoded, 100)
    println("Peak: " + analysis.peak.to_string())
    println("RMS: " + analysis.rms.to_string())
    }
    Err(_) => println("Decode failed")
    }
    }

    #📚 API Reference

    #Core Types

    #WavInfo

    pub struct WavInfo {
    audio_format : Int // 1 = PCM, 3 = IEEE float
    num_channels : Int // 1 = mono, 2 = stereo
    sample_rate : Int // Sample rate in Hz (e.g., 44100)
    byte_rate : Int // Byte rate
    block_align : Int // Block align
    bits_per_sample : Int // 8, 16, 24, or 32
    data_size : Int // Data size in bytes
    }

    #AudioData

    pub struct AudioData {
    samples : Array[Int] // Decoded samples (32-bit signed integers)
    info : WavInfo // Format information
    }

    #WavError

    pub enum WavError {
    InvalidHeader
    UnsupportedFormat
    CorruptedData
    InvalidChunk
    }

    #ValidationResult

    pub struct ValidationResult {
    is_valid : Bool
    warnings : Array[String]
    error : String?
    }

    #AudioAnalysis

    pub struct AudioAnalysis {
    duration_sec : Double
    samples_per_channel : Int
    peak : Int
    rms : Double
    dc_offset : Double
    zero_crossings : Int
    has_clipping : Bool
    clipped_samples : Int
    is_silent : Bool
    silence_ratio : Double
    }

    #Decoding Functions

    FunctionDescription
    decode(data : Bytes) -> Result[AudioData, WavError]Decode a WAV file (PCM & IEEE float)
    get_info(data : Bytes) -> Result[WavInfo, WavError]Get WAV info without decoding

    #Encoding Functions

    FunctionDescription
    encode(audio : AudioData) -> BytesEncode audio data to WAV format
    encode_with_format(samples, num_channels, sample_rate, bits_per_sample) -> BytesEncode with specified format

    #Validation Functions

    FunctionDescription
    validate(data : Bytes) -> ValidationResultValidate WAV file structure

    #Conversion Functions

    FunctionDescription
    convert_bit_depth(samples, from_bits, to_bits) -> Result[Array[Int], WavError]Convert bit depth
    convert_channels(samples, from_channels, to_channels) -> Result[Array[Int], WavError]Convert channels
    resample(samples, from_rate, to_rate, num_channels) -> Array[Int]Resample audio

    #Audio Operations

    FunctionDescription
    trim(samples, start, end) -> Array[Int]Trim audio
    concat(a, b) -> Array[Int]Concatenate audio
    adjust_volume(samples, factor) -> Array[Int]Adjust volume
    mix(a, b) -> Array[Int]Mix two streams
    fade_in(samples, fade_samples) -> Array[Int]Fade in
    fade_out(samples, fade_samples) -> Array[Int]Fade out
    reverse(samples) -> Array[Int]Reverse audio
    get_peak_amplitude(samples) -> IntGet peak amplitude
    get_rms_level(samples) -> DoubleGet RMS level

    #Audio Effects

    FunctionDescription
    echo(samples, delay_samples, decay) -> Array[Int]Echo effect
    delay(samples, delay_samples, mix) -> Array[Int]Delay effect
    normalize(samples, target_peak) -> Array[Int]Normalize to target peak
    soft_clip(samples, threshold) -> Array[Int]Soft clipping
    remove_dc_offset(samples) -> Array[Int]Remove DC offset
    low_pass_filter(samples, window_size) -> Array[Int]Low-pass filter
    high_pass_filter(samples, window_size) -> Array[Int]High-pass filter
    reverse_reverb(samples, fade_samples) -> Array[Int]Reverse reverb

    #Waveform Generators

    FunctionDescription
    generate_sine(freq, amp, rate, duration) -> Array[Int]Sine wave
    generate_square(freq, amp, rate, duration) -> Array[Int]Square wave
    generate_sawtooth(freq, amp, rate, duration) -> Array[Int]Sawtooth wave
    generate_triangle(freq, amp, rate, duration) -> Array[Int]Triangle wave
    generate_noise(amp, rate, duration, seed) -> Array[Int]White noise
    generate_chirp(start_freq, end_freq, amp, rate, duration) -> Array[Int]Frequency sweep
    generate_silence(rate, duration) -> Array[Int]Silence
    generate_sine_wav(freq, amp, rate, duration, bits) -> AudioDataSine as AudioData

    #Audio Analysis

    FunctionDescription
    analyze(audio, silence_threshold) -> AudioAnalysisFull analysis
    calculate_dc_offset(samples) -> DoubleDC offset
    count_zero_crossings(samples) -> IntZero crossings
    count_clipped_samples(samples, min, max) -> IntClipped samples
    count_silent_samples(samples, threshold) -> IntSilent samples
    format_analysis(analysis) -> StringFormat analysis as string

    #Utility Functions

    FunctionDescription
    format_wav_info(info) -> StringFormat WAV info as string
    split_stereo(samples) -> (Array[Int], Array[Int])Split stereo to L/R
    combine_stereo(left, right) -> Array[Int]Combine L/R to stereo
    get_duration(audio) -> DoubleGet duration in seconds
    get_frame_count(audio) -> IntGet frame count
    extract_channel(samples, num_channels, channel) -> Array[Int]Extract one channel
    mix_multiple(streams) -> Array[Int]Mix multiple streams
    repeat(samples, times) -> Array[Int]Repeat audio
    pad_to_length(samples, target_length) -> Array[Int]Pad with silence
    cross_correlation_zero_lag(a, b) -> DoubleCross-correlation

    #⚠️ Limitations / 功能边界

    #Supported Formats / 支持的格式

    FormatDecodeEncode
    PCM 8-bit unsigned✅✅
    PCM 16-bit signed LE✅✅
    PCM 24-bit signed LE✅✅
    PCM 32-bit signed LE✅✅
    IEEE 754 32-bit float✅❌
    ADPCM, A-law, μ-law❌❌
    Compressed formats❌❌

    #Channel Support / 声道支持

    ChannelsSupport
    Mono (1ch)✅ Full
    Stereo (2ch)✅ Full
    Multi-channel (3+)⚠️ Partial (decode only)

    #Sample Rate / 采样率

    • Any sample rate from 1 Hz to 192,000 Hz
    • Resampling uses linear interpolation (not band-limited)

    #Known Limitations / 已知限制

    1. Only standard WAV files - RIFF/WAVE format only, no RF64 or BWF
    2. No compressed formats - ADPCM, A-law, μ-law not supported
    3. IEEE float encode not supported - Can decode but not encode float WAV
    4. Linear interpolation resampling - May introduce aliasing at extreme ratios
    5. No metadata chunks - LIST, INFO chunks are ignored
    6. 32-bit integer samples - All samples stored as 32-bit signed integers internally

    #📝 Examples

    #Generate and Encode WAV

    let audio = generate_sine_wav(440.0, 16000.0, 44100, 1.0, 16)
    let wav_bytes = encode(audio)
    println("WAV file: " + wav_bytes.length().to_string() + " bytes")

    #Validate WAV File

    let result = validate(wav_data)
    if result.is_valid {
    println("Valid WAV file")
    } else {
    println("Invalid: " + result.error.to_string())
    }

    #Audio Analysis

    match decode(wav_data) {
    Ok(audio) => {
    let analysis = analyze(audio, 100)
    println("Duration: " + analysis.duration_sec.to_string() + "s")
    println("Peak: " + analysis.peak.to_string())
    println("Clipping: " + analysis.has_clipping.to_string())
    }
    Err(_) => ()
    }

    #Processing Pipeline

    let audio = generate_sine_wav(440.0, 16000.0, 44100, 1.0, 16)
    let processed = fade_in(audio.samples, 4410) // 100ms fade in
    let processed = fade_out(processed, 4410) // 100ms fade out
    let processed = normalize(processed, 32000) // Normalize
    let encoded = encode({ samples: processed, info: audio.info })

    #🔨 Building

    # Build the library moon build # Run tests moon test # Run the example moon run cmd/main

    #📄 License

    Apache-2.0

    #🤝 Contributing

    Contributions are welcome! Please feel free to submit a Pull Request.

    AudioAnalysis

    pub struct AudioAnalysis {
    duration_sec : Double
    samples_per_channel : Int
    peak : Int
    rms : Double
    dc_offset : Double
    zero_crossings : Int
    has_clipping : Bool
    clipped_samples : Int
    is_silent : Bool
    silence_ratio : Double
    } derive(
    Debug
    )

    Result of audio analysis.

    AudioData

    pub struct AudioData {
    samples : Array[Int]
    info : WavInfo
    } derive(
    Debug
    )

    Represents decoded audio data with format information.

    ValidationResult

    pub struct ValidationResult {
    is_valid : Bool
    warnings : Array[String]
    error : String?
    } derive(
    Debug
    )

    Validation result with detailed error information.

    WavError

    pub enum WavError {
    InvalidHeader
    UnsupportedFormat
    CorruptedData
    InvalidChunk
    } derive(Eq,
    Debug
    )

    Errors that can occur during WAV decoding.

    WavInfo

    pub struct WavInfo {
    audio_format : Int
    num_channels : Int
    sample_rate : Int
    byte_rate : Int
    block_align : Int
    bits_per_sample : Int
    data_size : Int
    } derive(
    Debug
    )

    Represents the format information of a WAV file.

    adjust_volume

    fn adjust_volume(samples : Array[Int], factor : Double) -> Array[Int]

    Adjust the volume of audio samples.

    Arguments

    • samples - Input audio samples
    • factor - Volume multiplier (1.0 = no change, 0.5 = half volume, 2.0 = double)

    Returns

    • Array[Int] - Volume-adjusted samples

    analyze

    fn analyze(audio : AudioData, silence_threshold : Int) -> AudioAnalysis

    Analyze audio samples and return comprehensive statistics.

    Arguments

    • audio - The audio data to analyze
    • silence_threshold - Amplitude threshold below which is considered silent (default: 100)

    Returns

    • AudioAnalysis - Comprehensive analysis result

    calculate_dc_offset

    fn calculate_dc_offset(samples : Array[Int]) -> Double

    Calculate the DC offset (mean value) of audio samples.

    combine_stereo

    fn combine_stereo(left : Array[Int], right : Array[Int]) -> Array[Int]

    Combine left and right channels into interleaved stereo samples.

    Arguments

    • left - Left channel samples
    • right - Right channel samples

    Returns

    • Array[Int] - Interleaved stereo samples [L0, R0, L1, R1, ...]

    concat

    fn concat(a : Array[Int], b : Array[Int]) -> Array[Int]

    Concatenate two audio sample arrays.

    Arguments

    • a - First audio samples
    • b - Second audio samples

    Returns

    • Array[Int] - Concatenated samples

    convert_bit_depth

    fn convert_bit_depth(samples : Array[Int], from_bits : Int, to_bits : Int) -> Result[Array[Int], WavError]

    Convert audio samples from one bit depth to another.

    Arguments

    • samples - Input audio samples
    • from_bits - Source bit depth (8, 16, or 24)
    • to_bits - Target bit depth (8, 16, or 24)

    Returns

    • Ok(Array[Int]) - Converted samples
    • Err(WavError) - Error during conversion

    convert_channels

    fn convert_channels(samples : Array[Int], from_channels : Int, to_channels : Int) -> Result[Array[Int], WavError]

    Convert audio samples between mono and stereo.

    Arguments

    • samples - Input audio samples
    • from_channels - Source channel count (1 or 2)
    • to_channels - Target channel count (1 or 2)

    Returns

    • Ok(Array[Int]) - Converted samples
    • Err(WavError) - Error during conversion

    count_clipped_samples

    fn count_clipped_samples(samples : Array[Int], min_val : Int, max_val : Int) -> Int

    Count the number of clipped samples (at min or max value).

    count_silent_samples

    fn count_silent_samples(samples : Array[Int], threshold : Int) -> Int

    Count the number of silent samples (absolute value below threshold).

    count_zero_crossings

    fn count_zero_crossings(samples : Array[Int]) -> Int

    Count the number of zero crossings in the audio signal. A zero crossing occurs when consecutive samples have different signs.

    cross_correlation_zero_lag

    fn cross_correlation_zero_lag(a : Array[Int], b : Array[Int]) -> Double

    Calculate the cross-correlation between two signals at zero lag. Useful for comparing similarity of two audio signals.

    decode

    fn decode(data : Bytes) -> Result[AudioData, WavError]

    Parse a WAV file from bytes and return the decoded audio data.

    Arguments

    • data - The raw bytes of the WAV file

    Returns

    • Ok(AudioData) - Successfully decoded audio data
    • Err(WavError) - Error during decoding

    delay

    fn delay(samples : Array[Int], delay_samples : Int, mix : Double) -> Array[Int]

    Apply delay effect to audio samples.

    Arguments

    • samples - Input audio samples
    • delay_samples - Delay in samples
    • mix - Mix ratio (0.0 = dry only, 1.0 = wet only, 0.5 = equal mix)

    Returns

    • Array[Int] - Samples with delay applied

    echo

    fn echo(samples : Array[Int], delay_samples : Int, decay : Double) -> Array[Int]

    Apply echo effect to audio samples.

    Arguments

    • samples - Input audio samples
    • delay_samples - Delay in samples (e.g., 4410 for 100ms at 44100Hz)
    • decay - Decay factor for echo (0.0 to 1.0, e.g., 0.5)

    Returns

    • Array[Int] - Samples with echo applied

    encode

    fn encode(audio : AudioData) -> Bytes

    Encode audio samples and format info into a WAV file.

    Arguments

    • audio - The audio data to encode

    Returns

    • Bytes - The encoded WAV file bytes

    encode_with_format

    fn encode_with_format(samples : Array[Int], num_channels : Int, sample_rate : Int, bits_per_sample : Int) -> Bytes

    Encode audio samples into a WAV file with specified format.

    Arguments

    • samples - The audio samples
    • num_channels - Number of channels (1 or 2)
    • sample_rate - Sample rate in Hz
    • bits_per_sample - Bit depth (8, 16, 24, or 32)

    Returns

    • Bytes - The encoded WAV file bytes

    extract_channel

    fn extract_channel(samples : Array[Int], num_channels : Int, channel : Int) -> Array[Int]

    Extract a single channel from multi-channel audio.

    Arguments

    • samples - Interleaved multi-channel samples
    • num_channels - Total number of channels
    • channel - Channel index to extract (0-based)

    Returns

    • Array[Int] - Extracted channel samples

    fade_in

    fn fade_in(samples : Array[Int], fade_samples : Int) -> Array[Int]

    Fade in audio samples.

    Arguments

    • samples - Input audio samples
    • fade_samples - Number of samples to fade in

    Returns

    • Array[Int] - Samples with fade in applied

    fade_out

    fn fade_out(samples : Array[Int], fade_samples : Int) -> Array[Int]

    Fade out audio samples.

    Arguments

    • samples - Input audio samples
    • fade_samples - Number of samples to fade out

    Returns

    • Array[Int] - Samples with fade out applied

    format_analysis

    fn format_analysis(analysis : AudioAnalysis) -> String

    Format audio analysis as a human-readable string.

    format_wav_info

    fn format_wav_info(info : WavInfo) -> String

    Format WAV info as a human-readable string.

    generate_chirp

    fn generate_chirp(start_freq : Double, end_freq : Double, amplitude : Double, sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate a chirp (frequency sweep) from start_freq to end_freq.

    Arguments

    • start_freq - Starting frequency in Hz
    • end_freq - Ending frequency in Hz
    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples

    generate_noise

    fn generate_noise(amplitude : Double, sample_rate : Int, duration_sec : Double, seed : Int) -> Array[Int]

    Generate white noise.

    Arguments

    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds
    • seed - Random seed for reproducibility

    Returns

    • Array[Int] - Generated samples

    generate_sawtooth

    fn generate_sawtooth(frequency : Double, amplitude : Double, sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate a sawtooth wave.

    Arguments

    • frequency - Frequency in Hz
    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples

    generate_silence

    fn generate_silence(sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate silence (all zeros).

    Arguments

    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples (all zeros)

    generate_sine

    fn generate_sine(frequency : Double, amplitude : Double, sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate a sine wave.

    Arguments

    • frequency - Frequency in Hz
    • amplitude - Peak amplitude (e.g., 16000 for 16-bit)
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples

    generate_sine_wav

    fn generate_sine_wav(frequency : Double, amplitude : Double, sample_rate : Int, duration_sec : Double, bits_per_sample : Int) -> AudioData

    Generate a sine wave and return as AudioData ready for encoding.

    Arguments

    • frequency - Frequency in Hz
    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds
    • bits_per_sample - Bit depth (8, 16, 24, 32)

    Returns

    • AudioData - Audio data ready for encoding

    generate_square

    fn generate_square(frequency : Double, amplitude : Double, sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate a square wave.

    Arguments

    • frequency - Frequency in Hz
    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples

    generate_triangle

    fn generate_triangle(frequency : Double, amplitude : Double, sample_rate : Int, duration_sec : Double) -> Array[Int]

    Generate a triangle wave.

    Arguments

    • frequency - Frequency in Hz
    • amplitude - Peak amplitude
    • sample_rate - Sample rate in Hz
    • duration_sec - Duration in seconds

    Returns

    • Array[Int] - Generated samples

    get_duration

    fn get_duration(audio : AudioData) -> Double

    Get the duration of audio in seconds.

    get_frame_count

    fn get_frame_count(audio : AudioData) -> Int

    Get the number of frames (samples per channel).

    get_info

    fn get_info(data : Bytes) -> Result[WavInfo, WavError]

    Get WAV file information without decoding the audio data.

    Arguments

    • data - The raw bytes of the WAV file

    Returns

    • Ok(WavInfo) - WAV file format information
    • Err(WavError) - Error during parsing

    get_peak_amplitude

    fn get_peak_amplitude(samples : Array[Int]) -> Int

    Get the peak amplitude of audio samples.

    Arguments

    • samples - Input audio samples

    Returns

    • Int - Peak amplitude (absolute value)

    get_rms_level

    fn get_rms_level(samples : Array[Int]) -> Double

    Get the RMS (Root Mean Square) level of audio samples.

    Arguments

    • samples - Input audio samples

    Returns

    • Double - RMS level

    high_pass_filter

    fn high_pass_filter(samples : Array[Int], window_size : Int) -> Array[Int]

    Apply a simple high-pass filter (difference from moving average).

    Arguments

    • samples - Input audio samples
    • window_size - Size of the moving average window

    Returns

    • Array[Int] - Filtered samples

    low_pass_filter

    fn low_pass_filter(samples : Array[Int], window_size : Int) -> Array[Int]

    Apply a simple low-pass filter (moving average).

    Arguments

    • samples - Input audio samples
    • window_size - Size of the moving average window (must be odd)

    Returns

    • Array[Int] - Filtered samples

    make_audio_data

    fn make_audio_data(samples : Array[Int], info : WavInfo) -> AudioData

    Create a new AudioData with the given samples and info.

    make_wav_info

    fn make_wav_info(audio_format : Int, num_channels : Int, sample_rate : Int, byte_rate : Int, block_align : Int, bits_per_sample : Int, data_size : Int) -> WavInfo

    Create a new WavInfo with the given parameters.

    mix

    fn mix(a : Array[Int], b : Array[Int]) -> Array[Int]

    Mix two audio streams together by averaging.

    Arguments

    • a - First audio samples
    • b - Second audio samples

    Returns

    • Array[Int] - Mixed samples (length = max(a.length, b.length))

    mix_multiple

    fn mix_multiple(streams : Array[Array[Int]]) -> Array[Int]

    Mix multiple audio streams with equal weight.

    Arguments

    • streams - Array of audio sample arrays

    Returns

    • Array[Int] - Mixed samples

    normalize

    fn normalize(samples : Array[Int], target_peak : Int) -> Array[Int]

    Normalize audio to a target peak amplitude.

    Arguments

    • samples - Input audio samples
    • target_peak - Target peak amplitude (e.g., 32000 for 16-bit)

    Returns

    • Array[Int] - Normalized samples

    pad_to_length

    fn pad_to_length(samples : Array[Int], target_length : Int) -> Array[Int]

    Pad audio with silence to reach a target length.

    Arguments

    • samples - Input audio samples
    • target_length - Target number of samples

    Returns

    • Array[Int] - Padded samples

    remove_dc_offset

    fn remove_dc_offset(samples : Array[Int]) -> Array[Int]

    Remove DC offset from audio samples.

    Arguments

    • samples - Input audio samples

    Returns

    • Array[Int] - Samples with DC offset removed

    repeat

    fn repeat(samples : Array[Int], times : Int) -> Array[Int]

    Repeat audio samples a specified number of times.

    Arguments

    • samples - Input audio samples
    • times - Number of times to repeat

    Returns

    • Array[Int] - Repeated samples

    resample

    fn resample(samples : Array[Int], from_rate : Int, to_rate : Int, num_channels : Int) -> Array[Int]

    Resample audio data to a different sample rate using linear interpolation.

    Arguments

    • samples - Input audio samples
    • from_rate - Source sample rate in Hz
    • to_rate - Target sample rate in Hz
    • num_channels - Number of channels

    Returns

    • Array[Int] - Resampled samples

    reverse

    fn reverse(samples : Array[Int]) -> Array[Int]

    Reverse audio samples.

    Arguments

    • samples - Input audio samples

    Returns

    • Array[Int] - Reversed samples

    reverse_reverb

    fn reverse_reverb(samples : Array[Int], fade_samples : Int) -> Array[Int]

    Reverse audio and apply fade (creates a "reverse reverb" effect).

    Arguments

    • samples - Input audio samples
    • fade_samples - Number of samples for fade

    Returns

    • Array[Int] - Processed samples

    soft_clip

    fn soft_clip(samples : Array[Int], threshold : Int) -> Array[Int]

    Apply soft clipping to prevent harsh distortion. Uses a tanh-like curve to smoothly limit amplitude.

    Arguments

    • samples - Input audio samples
    • threshold - Clipping threshold (e.g., 30000 for 16-bit)

    Returns

    • Array[Int] - Samples with soft clipping applied

    split_stereo

    fn split_stereo(samples : Array[Int]) -> (Array[Int], Array[Int])

    Split stereo samples into left and right channels.

    Arguments

    • samples - Interleaved stereo samples [L0, R0, L1, R1, ...]

    Returns

    • (Array[Int], Array[Int]) - (left_channel, right_channel)

    trim

    fn trim(samples : Array[Int], start_sample : Int, end_sample : Int) -> Array[Int]

    Trim audio samples to a specified range.

    Arguments

    • samples - Input audio samples
    • start_sample - Start index (inclusive)
    • end_sample - End index (exclusive)

    Returns

    • Array[Int] - Trimmed samples

    validate

    fn validate(data : Bytes) -> ValidationResult

    Validate a WAV file and return detailed results.

    Checks:
    • RIFF header correctness
    • WAVE marker presence
    • fmt chunk structure and values
    • data chunk presence
    • Chunk alignment
    • Data size consistency

    Arguments

    • data - The raw bytes of the WAV file

    Returns

    • ValidationResult - Detailed validation result