Autore Topic: Riprodurre effetti sonori con SoundPool  (Letto 5306 volte)

Offline teskio

  • Moderatore globale
  • Utente normale
  • *****
  • Post: 387
  • Respect: +118
    • Github
    • Google+
    • Mostra profilo
    • Skullab
  • Dispositivo Android:
    Cubot GT99 / SurfTab Ventos 10.1
  • Play Store ID:
    Skullab Software
  • Sistema operativo:
    windows 7 / ubuntu 12.04
Riprodurre effetti sonori con SoundPool
« il: 13 Febbraio 2011, 14:33:30 CET »
+4
Snippet o non Snippet ? Troppo corto per un tutorial e un po’ prolisso sulle spiegazioni per uno snippet, ma alla fine la scelta è stata quest’ultima. Ho creato questo oggettino per la riproduzione di effetti sonori, come ad esempio il “click” dei bottoni presenti nelle activity, utilizzando la classe SoundPool presente in Android. Questo perché la soluzione che sviluppai usando il MediaPlayer creava latenze alquanto fastidiose. Con “Effect” invece vi basterà creare l’effetto nell’onCreate dell’activity, passando al costruttore il Context e l’id della risorsa audio (R.raw.nome_effetto) e poi usare il metodo “play” ogni volta che volete riprodurre il suono. Una volta che l’effetto non è più necessario il metodo “release” rilascerà le risorse occupate dalla classe SoundPool. Enjoy ! :-P

PS: Il tipo di stream che ho utilizzato nella creazione del SoundPool è AudioManager.STREAM_MUSIC, ma nulla vieta di utilizzarne uno differente.
Interessante anche l’implementazione del listener SoundPool.OnLoadCompleteListener, che però è supportato solo a partire dalle API LEVEL 8, e che quindi non ho implementato per motivi di retro-compatibilità.
Codice (Java): [Seleziona]
/**
         * Effect object to play sound effects. Create the effects in onCreate state
         * of the Activity,to allow SoundPool to load audio resources. Release
         * effects when no longer needed, for example in onDestroy state of the
         * Activity
         *
         * @author ivan.maruca@gmail.com
         */

        public class Effect {
                /**
                 * CONSTANTS :
                 * PRIORITY : the priority of the sound. Currently has no
                 * effect. Use a value of 1 for future compatibility. (Google doc.)
                 * MAX_STREAMS : the maximum number of simultaneous streams for this
                 * SoundPool object (Google doc.)
                 * STREAM_TYPE : the audio stream type as described in AudioManager.
                 * For example, game applications will normally use STREAM_MUSIC. (Google doc.)
                 *  
                 */

                private static final int PRIORITY = 1;
                private static final int MAX_STREAMS = 4;
                private static final int STREAM_TYPE = AudioManager.STREAM_MUSIC;

                private SoundPool sound;
                private AudioManager am;
                private float volume;
                private int soundID;

                /**
                 * Constructs a Effect object with the following characteristics:
                 *
                 * @param context
                 *            The context of the application
                 * @param resId
                 *            The resource id of sound effect, like
                 *            R.raw.music_effect_example
                 */

                public Effect(Context context, int resId) {
                        am = (AudioManager) context.getSystemService(Context.AUDIO_SERVICE);
                        volume = am.getStreamVolume(STREAM_TYPE);
                        sound = new SoundPool(MAX_STREAMS, STREAM_TYPE, 0);
                        soundID = sound.load(context, resId, PRIORITY);
                }

                /**
                 * Play the sound
                 */

                public void play() {
                        sound.play(soundID, volume, volume, PRIORITY, 0, 1f);
                }
                /**
                 * Release the SoundPool resources. Release all memory and native resources used by the SoundPool object.
                 * The SoundPool can no longer be used and the reference should be set to null. (Google doc.)
                 */

                public void release() {
                        sound.release();
                }
        }

Offline Grifith

  • Utente junior
  • **
  • Post: 56
  • Respect: +1
    • Mostra profilo
    • La mia prima applicazione...
Re:Riprodurre effetti sonori con SoundPool
« Risposta #1 il: 28 Marzo 2011, 17:17:42 CEST »
0
Buonasera,

sto cercando di utilizzare il tuo codice all'interno di un progetto che sto svolgendo...

Ti chiedo supporto per un piccolo problema.

Ovvero, ho la mia activity che ha integrato un Handler per la restituzione di alcuni dati da un thread.
All'interno della classe MyHandler volevo aggiungere un effetto sonoro al momento in cui vengono visualizzate le informazioni.
Ho, quindi, creato la tua classe Effect e l'ho richiamata all'interno della classe MyHandler in questo modo:
Codice (Java): [Seleziona]
Effect eff = new Effect(MyActivity.this, R.raw.alert);
eff.play();

ma purtroppo non mi parte alcun suono.

Ho creato la cartella raw e inserito un file alert.mp3 ...

Hai qualche idea sul perchè non vada?

Grazie

P.S. Ho pensato che potesse dipendere dall'emulatore, ma ho testato la visualizzazione di un file da youtube e il suono si sente...

Offline teskio

  • Moderatore globale
  • Utente normale
  • *****
  • Post: 387
  • Respect: +118
    • Github
    • Google+
    • Mostra profilo
    • Skullab
  • Dispositivo Android:
    Cubot GT99 / SurfTab Ventos 10.1
  • Play Store ID:
    Skullab Software
  • Sistema operativo:
    windows 7 / ubuntu 12.04
Re:Riprodurre effetti sonori con SoundPool
« Risposta #2 il: 28 Marzo 2011, 19:00:52 CEST »
0
Credo che il problema possa dipendere dal tempo di caricamento del file audio e la sua riproduzione. Se infatti creai un nuovo effetto sonoro e subito dopo provi a riprodurlo, quasi sicuramente non sentirai nulla, perchè il SoundPool non sarà ancora pronto ! Per ovviare a ciò ti consiglio di istanziare tutti gli effetti che vuoi nell'onCreate dell'Activity :
Codice (Java): [Seleziona]
@Override
private Effect effect1,effect2,effect3 ;
public void onCreate(Bundle savedInstanceState) {
    effect1 = new Effect(this,R.raw.effect_sound_1);
    effect2 = new Effect(this,R.raw.effect_sound_2);
    effect3 = new Effect(this,R.raw.effect_sound_3);
...
}

Dopodichè potrai usare gli effetti e riprodurli in altre parti del codice usando il metodo play(). Se la tua classe MyHandler è una sottoclasse dell'Activity, nessun problema, usa i riferimenti che hai dichiarato all'inizio :

Codice (Java): [Seleziona]
// All'interno della sottoclasse MyHandler, nel punto desirato :
effect1.play();

Se invece hai scritto le classi separate dovrai usare un riferimento statico o passare comunque il riferimento dell'oggeto Effect che vuoi riprodurre. ;-)

Offline Grifith

  • Utente junior
  • **
  • Post: 56
  • Respect: +1
    • Mostra profilo
    • La mia prima applicazione...
Re:Riprodurre effetti sonori con SoundPool
« Risposta #3 il: 29 Marzo 2011, 00:37:53 CEST »
0
Ok.
Domani mattina lo testo e ti faccio sapere.
Anche se con il MediaPlayer pare che il suono si senta... Ma una domanda. Cosa intendi per problemi di latenza, usando il MediaPlayer ?



Aggiornamento - 29/03/2011:
Ho testato quanto detto da te, ed effettivamente funziona. Si vede che ha bisogno di qualche secondo per caricare il tutto.
Conosci, per caso, come poter mettere un loop al file sonoro appena creato? O meglio, fare in modo che vada in loop ma, tra un avvio e l'altro, ci sia del margine di tempo?
P.S. Io intanto continuo a cercare.



Grazie ancora!
« Ultima modifica: 29 Marzo 2011, 11:49:06 CEST da Grifith »

Offline crow610

  • Nuovo arrivato
  • *
  • Post: 4
  • Respect: 0
    • Mostra profilo
Re:Riprodurre effetti sonori con SoundPool
« Risposta #4 il: 15 Maggio 2012, 18:34:31 CEST »
0
Salve, ho implementato questo metodo in una piccola applicazione che alla pressione di un tasto riproduce un suono.
Ho caricato una ventina di suoni diversi associati ad ogni tasto, inizialmente funziona tutto egregiamente ma dopo un pò non vengono riprodotti più i suoni. La cosa strana è che sembra che smetta di funzionare qualsiasi altro suono del telefono fino a quando non viene riavviato.
Dove sto sbagliando?

Offline teskio

  • Moderatore globale
  • Utente normale
  • *****
  • Post: 387
  • Respect: +118
    • Github
    • Google+
    • Mostra profilo
    • Skullab
  • Dispositivo Android:
    Cubot GT99 / SurfTab Ventos 10.1
  • Play Store ID:
    Skullab Software
  • Sistema operativo:
    windows 7 / ubuntu 12.04
Re:Riprodurre effetti sonori con SoundPool
« Risposta #5 il: 19 Maggio 2012, 08:02:03 CEST »
0
Cosa dice il logcat ? :-)

Offline crow610

  • Nuovo arrivato
  • *
  • Post: 4
  • Respect: 0
    • Mostra profilo
Re:Riprodurre effetti sonori con SoundPool
« Risposta #6 il: 22 Maggio 2012, 14:43:54 CEST »
0
05-22 12:36:38.755: D/dalvikvm(411): GC_EXTERNAL_ALLOC freed 55K, 53% free 2559K/5379K, external 2002K/2137K, paused 50ms
05-22 12:36:40.775: D/dalvikvm(411): GREF has increased to 201
05-22 12:37:59.255: W/KeyCharacterMap(411): No keyboard for id 0
05-22 12:37:59.255: W/KeyCharacterMap(411): Using default keymap: /system/usr/keychars/qwerty.kcm.bin
05-22 12:40:14.514: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:40:14.524: E/SoundPool(411): Error creating AudioTrack
05-22 12:40:16.845: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:40:16.845: E/SoundPool(411): Error creating AudioTrack
05-22 12:40:26.315: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:40:26.315: E/SoundPool(411): Error creating AudioTrack
05-22 12:40:30.725: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:40:30.725: E/SoundPool(411): Error creating AudioTrack
05-22 12:41:05.997: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:41:06.005: E/SoundPool(411): Error creating AudioTrack
05-22 12:41:09.564: E/AudioTrack(411): AudioFlinger could not create track, status: -12
05-22 12:41:09.564: E/SoundPool(411): Error creating AudioTrack

Offline teskio

  • Moderatore globale
  • Utente normale
  • *****
  • Post: 387
  • Respect: +118
    • Github
    • Google+
    • Mostra profilo
    • Skullab
  • Dispositivo Android:
    Cubot GT99 / SurfTab Ventos 10.1
  • Play Store ID:
    Skullab Software
  • Sistema operativo:
    windows 7 / ubuntu 12.04
Re:Riprodurre effetti sonori con SoundPool
« Risposta #7 il: 22 Maggio 2012, 22:47:42 CEST »
0
Si pianta il server audio, AudioFlinger, che non riesce a caricare le tracce, impedendo anche la riproduzione di altri suoni del telefono, avendo le risorse impegnate. Hai per caso creato un loop dove tenti di eseguire un suono che non è stato ancora caricato ? Tutti i suoni devono essere prima caricati prima di poter essere riprodotti...a partire dalle API Level 8 è stato introdotto un listener per determinare quando un suono è stato caricato correttamente, potresti implementarlo  ;-)

Offline crow610

  • Nuovo arrivato
  • *
  • Post: 4
  • Respect: 0
    • Mostra profilo
Re:Riprodurre effetti sonori con SoundPool
« Risposta #8 il: 24 Maggio 2012, 19:11:06 CEST »
0
Probabilmente era semplicemente un problema con le risorse di sistema. Ho implementato una funzione che dopo un pò di tempo effettua un release del soundpool e poi lo ricarica. adesso sembra funzionare correttamente.

Offline walter90

  • Nuovo arrivato
  • *
  • Post: 6
  • Respect: 0
    • Mostra profilo
Re:Riprodurre effetti sonori con SoundPool
« Risposta #9 il: 13 Novembre 2012, 14:56:22 CET »
0
Salve so ke il post  un pò vecchiotto ma spero riusciate ad aiutarmi. Io ho scritto una classe EffectSound identica a quella scritta sopra. Ho aggiunto la cartella raw ed il file audio da riprodurre. Ho creato un nuovo oggetto EffectSound nel metodo onCreate() e nello stesso metodo ho richiamato sull'oggeto il metodo statico play() ma all'avvio dell'app nn succede nulla.Non si sente nessun suono. Dove sbaglio?

Offline teskio

  • Moderatore globale
  • Utente normale
  • *****
  • Post: 387
  • Respect: +118
    • Github
    • Google+
    • Mostra profilo
    • Skullab
  • Dispositivo Android:
    Cubot GT99 / SurfTab Ventos 10.1
  • Play Store ID:
    Skullab Software
  • Sistema operativo:
    windows 7 / ubuntu 12.04
Re:Riprodurre effetti sonori con SoundPool
« Risposta #10 il: 17 Novembre 2012, 10:30:36 CET »
+1
Apri un topic in supporto tecnico postando codice e logcat  ;-)