Please help me with my understanding AiffAudioFormat I keep getting this error

Hi, Im new to juce and I am working on a practice project where I’m trying to learn the AiffAudioFromat object. I keep getting this error and can figure out why.

here is the error below:

Here is what I got so far. I’m using the playing sound file tutorial to help me understand the AiffAudioFormat object.

here is my code below:

the header file:

#pragma once

#include <JuceHeader.h>

//==============================================================================
/*
    This component lives inside our window, and this is where you should put all
    your controls and content.
*/
class MainComponent  : public juce::AudioAppComponent,
                       public juce::ChangeListener
                       
                        
{
public:
    //==============================================================================
    MainComponent();
    ~MainComponent() override;

    //==============================================================================
    void prepareToPlay (int samplesPerBlockExpected, double sampleRate) override;
    void getNextAudioBlock (const juce::AudioSourceChannelInfo& bufferToFill) override;
    void releaseResources() override;

    //==============================================================================
    void paint (juce::Graphics& g) override;
    void resized() override;
    
    //===============================================================================
    
private:
    
    void openButtonClicked()
    {
        juce::FileChooser chooser ("Select a Aiff file to play...", {}, "*.aiff");
        
        if (chooser.browseForFileToOpen())
        {
            auto file = chooser.getResult();

            DBG("file opened"); //debug
            
            
            if (file.existsAsFile())
            {
                DBG("file exists");
                
                
                
                juce::FileInputStream fis(file);
                
               
                
                auto* reader = readAiff.createReaderFor (&fis,true);
                
                
                if (reader != nullptr)
                {
                    DBG("file OpenedOK");
                    DBG("can handlefile " << (int)readAiff.canHandleFile(file));
                    
                    std::unique_ptr<juce::AudioFormatReaderSource> newSource(new juce::AudioFormatReaderSource (reader, true));
                    transportSource.setSource (newSource.get(), 0, nullptr, reader->sampleRate);
                    playButton.setEnabled (true);
                    readerSource.reset (newSource.release());
                  
                }
            }
        }
    }
    
     void changeListenerCallback (juce::ChangeBroadcaster* source) override
    {
       if (source == &transportSource)
       {
           if (transportSource.isPlaying())
               changeState (Playing);
           else
               changeState (Stopped);
       }
    }
    
    void playButtonClicked()
    {
        
        changeState(Starting);
        DBG("play works");
    }
    enum TransportState
    {
        Stopped,
        Starting,
        Playing,
        Stopping
    };
    
    
    void changeState (TransportState newState)
    {
        if (state != newState)
        {
            state = newState;

            switch (state)
            {
                case Stopped:
                    
                    playButton.setEnabled (true);
                    transportSource.setPosition (0.0);
                    break;

                case Starting:
                    playButton.setEnabled (false);
                    transportSource.start();
                    break;

                case Playing:
                   
                    break;

                case Stopping:
                    transportSource.stop();
                    break;
            }
        }
    }

    //==============================================================================
    // Your private member variables go here...
    juce::TextButton openButton;
    juce::TextButton playButton;
    
    
    juce::AiffAudioFormat readAiff;
    
    std::unique_ptr<juce::AudioFormatReaderSource> readerSource;
    
    juce::AudioTransportSource transportSource;
    
  
    TransportState state;
    
    
    JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (MainComponent)
};

here is the .cpp file:

#include "MainComponent.h"

//==============================================================================
MainComponent::MainComponent() : state (Stopped)
{
    // Make sure you set the size of the component after
    // you add any child components.
    setSize (800, 600);

    setAudioChannels(0, 2);
    
    openButton.setButtonText("Open...");
    openButton.onClick = [this] { openButtonClicked(); };
    addAndMakeVisible(&openButton);
    
    playButton.setButtonText("Play");
    playButton.onClick = [this] { playButtonClicked(); };
    addAndMakeVisible(&playButton);
    playButton.setEnabled(false);
    
    transportSource.addChangeListener(this);
}

MainComponent::~MainComponent()
{
    // This shuts down the audio device and clears the audio source.
    shutdownAudio();
}

//==============================================================================
void MainComponent::prepareToPlay (int samplesPerBlockExpected, double sampleRate)
{
    // This function will be called when the audio device is started, or when
    // its settings (i.e. sample rate, block size, etc) are changed.

    // You can use this function to initialise any resources you might need,
    // but be careful - it will be called on the audio thread, not the GUI thread.

    // For more details, see the help for AudioProcessor::prepareToPlay()
    transportSource.prepareToPlay(samplesPerBlockExpected, sampleRate);
    //transportSource.setPosition(0.0);
}

void MainComponent::getNextAudioBlock (const juce::AudioSourceChannelInfo& bufferToFill)
{
    if (readerSource.get() == nullptr)
    {
        bufferToFill.clearActiveBufferRegion();
        return;
    }
    
    
    transportSource.getNextAudioBlock(bufferToFill);
    
}

void MainComponent::releaseResources()
{
    // This will be called when the audio device stops, or when it is being
    // restarted due to a setting change.
    transportSource.releaseResources();
    // For more details, see the help for AudioProcessor::releaseResources()
}

//==============================================================================
void MainComponent::paint (juce::Graphics& g)
{
    // (Our component is opaque, so we must completely fill the background with a solid colour)
    g.fillAll (getLookAndFeel().findColour (juce::ResizableWindow::backgroundColourId));

    // You can add your drawing code here!
}

void MainComponent::resized()
{
    // This is called when the MainContentComponent is resized.
    // If you add any child components, this is where you should
    // update their positions.
    openButton          .setBounds (10, 10,  getWidth() - 20, 20);
    playButton          .setBounds (10, 40,  getWidth() - 20, 20);
}

Thank you in advance

This will try to delete an object on the stack. fis needs to be created with new on the heap, because createReaderFor takes ownership.

Might not be the full solution, but it needs to be fixed first.

Second issue: The newSource will be deleted once the unique_ptr goes out of scope.

1 Like

Thank you for the nudge. I’m going to do some research and noodle around.

OMG I GOT TO WORK! :smile: sorry, I’ve been banging my head against the wall trying to get it to work and your nudge helped me. OMG lol. thank you! I’ll post my finished code snippet tomorrow. I’m going to get some rest now or at least take a break. I probably won’t be able to sleep for a while because of the rush. I need a cigarette.