# SoftBank Robotics documentation What's new in NAOqi 2.8?

# Reacting to an audio event: loud noise

<< return to C++ examples

## Principle

If you want to have a sound-based reaction, you need to retrieve the sound received by NAO’s microphones. To do so, you have to implement a particular kind of module: it must inherit from ALSoundExtractor.

ALSoundExtractor implements some key methods to help you process sound:

- process. This method has to be redefined by the user. It is automatically called each time a sound buffer is sent, and its arguments correspond to the buffer information. You do not have to worry about any optimization, since it will automatically be called in local mode if possible.
- startDetection. Once this method has been called, sound buffers will be sent regularly with the desired preferences to the process method.
- stopDetection. This method stops the sound buffer sending.

The preferences for the kind of buffer to be sent are set through a proxy to ALAudioDevice.

Warning

Make sure that your sound processing function has an execution time either much smaller than the time between two sound buffers, or is thread-safe.

## Example: ALSoundBasedReaction module

This section implements an example module. It will make NAO say “Hello there” each time a sufficiently loud noise is detected.

The whole example is available here: `soundbasedreaction.zip`

### Header:

`alsoundbasedreaction.h`

    /**
    * @author Gwennael Gate
    * Copyright (c) Aldebaran Robotics 2010
    */

    #ifndef SOUNDBASEDREACTION_H
    #define SOUNDBASEDREACTION_H

    #ifdef SOUNDBASEDREACTION_IS_REMOTE
    #include <qi/application.hpp>
    #include <boost/function.hpp>
    #include <boost/bind.hpp>
    #endif

    #include <boost/shared_ptr.hpp>
    #include <alcommon/almodule.h>
    #include <string>
    #include <alproxies/altexttospeechproxy.h>
    #include "alaudio/alsoundextractor.h"

    using namespace AL;

    class ALSoundBasedReaction : public ALSoundExtractor
    {
    public:

      ALSoundBasedReaction(boost::shared_ptr<ALBroker> broker,
                           const std::string & name);
      virtual ~ALSoundBasedReaction();

      void init();

      void process(const int & nbOfChannels,
                   const int & nbrOfSamplesByChannel,
                   const AL_SOUND_FORMAT * buffer,
                   const ALValue & timeStamp);

    private:
      ALTextToSpeechProxy fProxyToTextToSpeech;
    };

    #endif  // SOUNDBASEDREACTION_H

### Source file:

`alsoundbasedreaction.cpp`

    /**
    * @author Gwennael Gate
    * Copyright (c) Aldebaran Robotics 2010
    */

    #include "alsoundbasedreaction.h"

    #include <alvalue/alvalue.h>
    #include <alcommon/alproxy.h>
    #include <alcommon/albroker.h>
    #include <iostream>
    #include <fstream>

    ALSoundBasedReaction::ALSoundBasedReaction(boost::shared_ptr<ALBroker> broker,
                                               const std::string& name) :
      ALSoundExtractor(broker, name)
    {
      /// This line will display a description of this module on the web page of the robot
      setModuleDescription("This module launch a texttospeech command when a "
                           "sudden and significative noise is heard.");
    }

    void ALSoundBasedReaction::init()
    {
      /// Setting up the appropriate language
      fProxyToTextToSpeech.setLanguage("English");

      audioDevice->callVoid("setClientPreferences",
                            getName(),                //Name of this module
                            16000,                    //16000 Hz requested
                            (int)FRONTCHANNEL,        //Front Channels requested
                            0                         //Deinterleaving is not needed here
                            );
    #ifdef SOUNDBASEDREACTION_IS_REMOTE
      qi::Application::atStop(boost::bind(&ALSoundBasedReaction::stopDetection, this));
    #endif
      startDetection();
    }

    ALSoundBasedReaction::~ALSoundBasedReaction()
    {
      stopDetection();
    }

    /// This function will be automatically called by the module ALAudioDevice
    /// every 170ms with the appropriate audio buffer (front channel at 16000Hz)
    void ALSoundBasedReaction::process(const int & nbOfChannels,
                                       const int & nbrOfSamplesByChannel,
                                       const AL_SOUND_FORMAT * buffer,
                                       const ALValue & timeStamp)
    {
      /// Compute the maximum value of the front microphone signal.
      int maxValueFront = 0;
      for(int i = 0 ; i < nbrOfSamplesByChannel ; i++)
      {
        if(buffer[i] > maxValueFront)
        {
          maxValueFront = buffer[i];
        }
      }

      /// Print it in the console
      /// (Naoqi needs to be launched in console mode to see the log)
      std::cout << "maxvalue : " << maxValueFront << std::endl;

      /// Launch a texttospeech command when it is appropriate
      if(maxValueFront > 10000)
      {
        fProxyToTextToSpeech.say("Hello there!");
      }
    }

### Main:

`soundbasedreactionmain.cpp`

    /**
    * @author Gwennael Gate
    * Copyright (c) Aldebaran Robotics 2010
    */

    #include <signal.h>
    #include <boost/shared_ptr.hpp>
    #include <alcommon/albroker.h>
    #include <alcommon/almodule.h>
    #include <alcommon/albrokermanager.h>
    #include <alcommon/altoolsmain.h>

    #include "alsoundbasedreaction.h"

    #ifdef SOUNDBASEDREACTION_IS_REMOTE
    # define ALCALL
    #else
    # ifdef _WIN32
    #  define ALCALL __declspec(dllexport)
    # else
    #  define ALCALL
    # endif
    #endif

    extern "C"
    {
      ALCALL int _createModule(boost::shared_ptr<AL::ALBroker> pBroker)
      {
        // init broker with the main broker instance
        // from the parent executable
        AL::ALBrokerManager::setInstance(pBroker->fBrokerManager.lock());
        AL::ALBrokerManager::getInstance()->addBroker(pBroker);

        AL::ALModule::createModule<ALSoundBasedReaction>(pBroker, "ALSoundBasedReaction");

        return 0;
      }

      ALCALL int _closeModule()
      {
        return 0;
      }
    }

    #ifdef SOUNDBASEDREACTION_IS_REMOTE
    int main(int argc, char *argv[])
    {
      // pointer to createModule
      TMainType sig;
      sig = &_createModule;

      // call main
      ALTools::mainFunction("alsoundbasedreaction",argc, argv,sig);
    }
    #endif

### CMakeLists.txt:

`CMakeLists.txt`

    # Copyright (C) 2010 Aldebaran Robotics

    cmake_minimum_required(VERSION 2.6.4 FATAL_ERROR)
    project(soundbasedreaction)
    find_package(qibuild)

    option(SOUNDBASEDREACTION_IS_REMOTE
      "module is compiled as a remote module (ON or OFF)"
      ON)

    set(_srcs
        main.cpp
        alsoundbasedreaction.h
        alsoundbasedreaction.cpp
    )

    if(SOUNDBASEDREACTION_IS_REMOTE)
      add_definitions(" -DSOUNDBASEDREACTION_IS_REMOTE ")
      qi_create_bin(soundbasedreaction ${_srcs})
    else()
      qi_create_lib(soundbasedreaction SHARED ${_srcs} SUBFOLDER naoqi)
    endif()

    qi_use_lib(soundbasedreaction ALCOMMON ALPROXIES ALAUDIO)

Glossary Site map Index Support Contact Legal Notices