1df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent/* 2df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Copyright (C) 2010 The Android Open Source Project 3df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * 4df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Licensed under the Apache License, Version 2.0 (the "License"); 5df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * you may not use this file except in compliance with the License. 6df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * You may obtain a copy of the License at 7df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * 8df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * http://www.apache.org/licenses/LICENSE-2.0 9df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * 10df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Unless required by applicable law or agreed to in writing, software 11df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * distributed under the License is distributed on an "AS IS" BASIS, 12df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * See the License for the specific language governing permissions and 14df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * limitations under the License. 15df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 16df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 171a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurentpackage android.media.audiofx; 18df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 19df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport android.util.Log; 20df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport java.lang.ref.WeakReference; 21df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport java.io.IOException; 22df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport android.os.Handler; 23df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport android.os.Looper; 24df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentimport android.os.Message; 25df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 26df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent/** 27df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * The Visualizer class enables application to retrieve part of the currently playing audio for 28df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * visualization purpose. It is not an audio recording interface and only returns partial and low 29df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * quality audio content. However, to protect privacy of certain audio data (e.g voice mail) the use 30df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * of the visualizer requires the permission android.permission.RECORD_AUDIO. 31df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>The audio session ID passed to the constructor indicates which audio content should be 32df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * visualized:<br> 33df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <ul> 34df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <li>If the session is 0, the audio output mix is visualized</li> 351a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurent * <li>If the session is not 0, the audio from a particular {@link android.media.MediaPlayer} or 361a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurent * {@link android.media.AudioTrack} 37df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * using this audio session is visualized </li> 38df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * </ul> 39df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>Two types of representation of audio content can be captured: <br> 40df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <ul> 41df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <li>Waveform data: consecutive 8-bit (unsigned) mono samples by using the 42df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #getWaveForm(byte[])} method</li> 43df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <li>Frequency data: 8-bit magnitude FFT by using the {@link #getFft(byte[])} method</li> 44df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * </ul> 45df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>The length of the capture can be retrieved or specified by calling respectively 4603a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * {@link #getCaptureSize()} and {@link #setCaptureSize(int)} methods. The capture size must be a 4703a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * power of 2 in the range returned by {@link #getCaptureSizeRange()}. 48df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>In addition to the polling capture mode described above with {@link #getWaveForm(byte[])} and 49df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #getFft(byte[])} methods, a callback mode is also available by installing a listener by 50df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * use of the {@link #setDataCaptureListener(OnDataCaptureListener, int, boolean, boolean)} method. 51df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * The rate at which the listener capture method is called as well as the type of data returned is 52df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * specified. 53df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>Before capturing data, the Visualizer must be enabled by calling the 54df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #setEnabled(boolean)} method. 55df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * When data capture is not needed any more, the Visualizer should be disabled. 56df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>It is good practice to call the {@link #release()} method when the Visualizer is not used 57df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * anymore to free up native resources associated to the Visualizer instance. 581a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurent * <p>Creating a Visualizer on the output mix (audio session 0) requires permission 591a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurent * {@link android.Manifest.permission#MODIFY_AUDIO_SETTINGS} 60df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 61df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 62df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurentpublic class Visualizer { 63df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 64df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent static { 65df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent System.loadLibrary("audioeffect_jni"); 66df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent native_init(); 67df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 68df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 69df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private final static String TAG = "Visualizer-JAVA"; 70df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 71df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 72df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * State of a Visualizer object that was not successfully initialized upon creation 73df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 74df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int STATE_UNINITIALIZED = 0; 75df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 76df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * State of a Visualizer object that is ready to be used. 77df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 78df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int STATE_INITIALIZED = 1; 79df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 80df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * State of a Visualizer object that is active. 81df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 82df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int STATE_ENABLED = 2; 83df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 84e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi // to keep in sync with system/media/audio_effects/include/audio_effects/effect_visualizer.h 85e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi /** 86e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * Defines a capture mode where amplification is applied based on the content of the captured 87e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * data. This is the default Visualizer mode, and is suitable for music visualization. 88e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi */ 89e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi public static final int SCALING_MODE_NORMALIZED = 0; 90e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi /** 91e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * Defines a capture mode where the playback volume will affect (scale) the range of the 92e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * captured data. A low playback volume will lead to low sample and fft values, and vice-versa. 93e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi */ 94e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi public static final int SCALING_MODE_AS_PLAYED = 1; 95e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi 96df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // to keep in sync with frameworks/base/media/jni/audioeffect/android_media_Visualizer.cpp 9717cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private static final int NATIVE_EVENT_PCM_CAPTURE = 0; 9817cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private static final int NATIVE_EVENT_FFT_CAPTURE = 1; 993540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman private static final int NATIVE_EVENT_SERVER_DIED = 2; 100df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 101df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Error codes: 102df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 103df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Successful operation. 104df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 105df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int SUCCESS = 0; 106df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 107df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Unspecified error. 108df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 109df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR = -1; 110df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 111ed6eae420fd60dcb7d90f54c3116959b75bd6276Glenn Kasten * Internal operation status. Not returned by any method. 112df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 113df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ALREADY_EXISTS = -2; 114df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 115df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Operation failed due to bad object initialization. 116df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 117df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR_NO_INIT = -3; 118df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 119df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Operation failed due to bad parameter value. 120df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 121df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR_BAD_VALUE = -4; 122df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 123df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Operation failed because it was requested in wrong state. 124df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 125df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR_INVALID_OPERATION = -5; 126df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 127df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Operation failed due to lack of memory. 128df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 129df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR_NO_MEMORY = -6; 130df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 131df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Operation failed due to dead remote object. 132df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 133df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static final int ERROR_DEAD_OBJECT = -7; 134df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 135df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------------------------------------------------------------- 136df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Member variables 137df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------- 138df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 139df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Indicates the state of the Visualizer instance 140df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 14117cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private int mState = STATE_UNINITIALIZED; 142df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 143df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Lock to synchronize access to mState 144df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 14517cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private final Object mStateLock = new Object(); 146df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 147df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * System wide unique Identifier of the visualizer engine used by this Visualizer instance 148df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 14917cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private int mId; 150df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 151df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 152df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Lock to protect listeners updates against event notifications 153df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 15417cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private final Object mListenerLock = new Object(); 155df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 156df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Handler for events coming from the native code 157df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 15817cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private NativeEventHandler mNativeEventHandler = null; 159df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 160df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * PCM and FFT capture listener registered by client 161df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 16217cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent private OnDataCaptureListener mCaptureListener = null; 1633540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman /** 1643540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * Server Died listener registered by client 1653540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman */ 1663540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman private OnServerDiedListener mServerDiedListener = null; 167df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 168df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // accessed by native methods 169df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private int mNativeVisualizer; 170df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private int mJniData; 171df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 172df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------------------------------------------------------------- 173df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Constructor, Finalize 174df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------- 175df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 176df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Class constructor. 17717cb280e7f1ac3556eac90ab08263712e0348cb9Eric Laurent * @param audioSession system wide unique audio session identifier. If audioSession 178df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * is not 0, the visualizer will be attached to the MediaPlayer or AudioTrack in the 179df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * same audio session. Otherwise, the Visualizer will apply to the output mix. 180df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * 181df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws java.lang.UnsupportedOperationException 182df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws java.lang.RuntimeException 183df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 184df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 185df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public Visualizer(int audioSession) 186df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws UnsupportedOperationException, RuntimeException { 187df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int[] id = new int[1]; 188df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 189df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 190df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mState = STATE_UNINITIALIZED; 191df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // native initialization 192df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int result = native_setup(new WeakReference<Visualizer>(this), audioSession, id); 193df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (result != SUCCESS && result != ALREADY_EXISTS) { 194df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent Log.e(TAG, "Error code "+result+" when initializing Visualizer."); 195df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent switch (result) { 196df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent case ERROR_INVALID_OPERATION: 197df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw (new UnsupportedOperationException("Effect library not loaded")); 198df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent default: 199df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw (new RuntimeException("Cannot initialize Visualizer engine, error: " 200df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent +result)); 201df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 202df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 203df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mId = id[0]; 204df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (native_getEnabled()) { 205df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mState = STATE_ENABLED; 206df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } else { 207df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mState = STATE_INITIALIZED; 208df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 209df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 210df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 211df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 212df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 213df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Releases the native Visualizer resources. It is a good practice to release the 214df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * visualization engine when not in use. 215df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 216df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public void release() { 217df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 218df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent native_release(); 219df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mState = STATE_UNINITIALIZED; 220df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 221df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 222df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 223df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent @Override 224df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent protected void finalize() { 225df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent native_finalize(); 226df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 227df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 228df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 229df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Enable or disable the visualization engine. 230df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param enabled requested enable state 231df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return {@link #SUCCESS} in case of success, 232df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #ERROR_INVALID_OPERATION} or {@link #ERROR_DEAD_OBJECT} in case of failure. 233df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws IllegalStateException 234df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 235df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int setEnabled(boolean enabled) 236df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 237df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 238672c0dc3a04cb149691603342c319994e21235cbEric Laurent if (mState == STATE_UNINITIALIZED) { 239df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("setEnabled() called in wrong state: "+mState)); 240df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 241672c0dc3a04cb149691603342c319994e21235cbEric Laurent int status = SUCCESS; 242672c0dc3a04cb149691603342c319994e21235cbEric Laurent if ((enabled && (mState == STATE_INITIALIZED)) || 243672c0dc3a04cb149691603342c319994e21235cbEric Laurent (!enabled && (mState == STATE_ENABLED))) { 244672c0dc3a04cb149691603342c319994e21235cbEric Laurent status = native_setEnabled(enabled); 245672c0dc3a04cb149691603342c319994e21235cbEric Laurent if (status == SUCCESS) { 246672c0dc3a04cb149691603342c319994e21235cbEric Laurent mState = enabled ? STATE_ENABLED : STATE_INITIALIZED; 247672c0dc3a04cb149691603342c319994e21235cbEric Laurent } 248df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 249df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return status; 250df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 251df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 252df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 253df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 254df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Get current activation state of the visualizer. 255df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return true if the visualizer is active, false otherwise 256df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 257df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public boolean getEnabled() 258df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent { 259df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 260df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState == STATE_UNINITIALIZED) { 261df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("getEnabled() called in wrong state: "+mState)); 262df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 263df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_getEnabled(); 264df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 265df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 266df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 267df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 268df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Returns the capture size range. 269df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return the mininum capture size is returned in first array element and the maximum in second 270df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * array element. 271df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 272df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static native int[] getCaptureSizeRange(); 273df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 274df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 275df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Returns the maximum capture rate for the callback capture method. This is the maximum value 276df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * for the rate parameter of the 277df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #setDataCaptureListener(OnDataCaptureListener, int, boolean, boolean)} method. 278df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return the maximum capture rate expressed in milliHertz 279df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 280df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public static native int getMaxCaptureRate(); 281df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 282df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 283df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Sets the capture size, i.e. the number of bytes returned by {@link #getWaveForm(byte[])} and 284df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #getFft(byte[])} methods. The capture size must be a power of 2 in the range returned 285df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * by {@link #getCaptureSizeRange()}. 286df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * This method must not be called when the Visualizer is enabled. 287df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param size requested capture size 288df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return {@link #SUCCESS} in case of success, 289df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #ERROR_BAD_VALUE} in case of failure. 290df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws IllegalStateException 291df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 292df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int setCaptureSize(int size) 293df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 294df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 295df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState != STATE_INITIALIZED) { 296df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("setCaptureSize() called in wrong state: "+mState)); 297df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 298df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_setCaptureSize(size); 299df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 300df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 301df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 302df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 303df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Returns current capture size. 304df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return the capture size in bytes. 305df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 306df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int getCaptureSize() 307df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 308df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 309df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState == STATE_UNINITIALIZED) { 310df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("getCaptureSize() called in wrong state: "+mState)); 311df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 312df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_getCaptureSize(); 313df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 314df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 315df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 316df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 317e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * Set the type of scaling applied on the captured visualization data. 318e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * @param mode see {@link #SCALING_MODE_NORMALIZED} 319e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * and {@link #SCALING_MODE_AS_PLAYED} 320e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * @return {@link #SUCCESS} in case of success, 321e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * {@link #ERROR_BAD_VALUE} in case of failure. 322e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * @throws IllegalStateException 323e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi */ 324e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi public int setScalingMode(int mode) 325e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi throws IllegalStateException { 326e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi synchronized (mStateLock) { 327e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi if (mState == STATE_UNINITIALIZED) { 328e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi throw(new IllegalStateException("setScalingMode() called in wrong state: " 329e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi + mState)); 330e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 331e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi return native_setScalingMode(mode); 332e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 333e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 334e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi 335e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi /** 336e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * Returns the current scaling mode on the captured visualization data. 337e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * @return the scaling mode, see {@link #SCALING_MODE_NORMALIZED} 338e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * and {@link #SCALING_MODE_AS_PLAYED}. 339e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi * @throws IllegalStateException 340e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi */ 341e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi public int getScalingMode() 342e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi throws IllegalStateException { 343e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi synchronized (mStateLock) { 344e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi if (mState == STATE_UNINITIALIZED) { 345e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi throw(new IllegalStateException("getScalingMode() called in wrong state: " 346e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi + mState)); 347e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 348e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi return native_getScalingMode(); 349e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 350e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi } 351e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi 352e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi /** 353df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Returns the sampling rate of the captured audio. 354df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return the sampling rate in milliHertz. 355df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 356df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int getSamplingRate() 357df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 358df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 359df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState == STATE_UNINITIALIZED) { 360df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("getSamplingRate() called in wrong state: "+mState)); 361df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 362df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_getSamplingRate(); 363df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 364df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 365df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 366df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 367df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Returns a waveform capture of currently playing audio content. The capture consists in 368df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * a number of consecutive 8-bit (unsigned) mono PCM samples equal to the capture size returned 369df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * by {@link #getCaptureSize()}. 370df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>This method must be called when the Visualizer is enabled. 371df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param waveform array of bytes where the waveform should be returned 372df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return {@link #SUCCESS} in case of success, 373df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #ERROR_NO_MEMORY}, {@link #ERROR_INVALID_OPERATION} or {@link #ERROR_DEAD_OBJECT} 374df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * in case of failure. 375df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws IllegalStateException 376df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 377df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int getWaveForm(byte[] waveform) 378df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 379df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 380df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState != STATE_ENABLED) { 381df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("getWaveForm() called in wrong state: "+mState)); 382df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 383df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_getWaveForm(waveform); 384df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 385df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 386df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 38703a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * Returns a frequency capture of currently playing audio content. 388df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>This method must be called when the Visualizer is enabled. 38903a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <p>The capture is an 8-bit magnitude FFT, the frequency range covered being 0 (DC) to half of 39003a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * the sampling rate returned by {@link #getSamplingRate()}. The capture returns the real and 39103a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * imaginary parts of a number of frequency points equal to half of the capture size plus one. 39203a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <p>Note: only the real part is returned for the first point (DC) and the last point 39303a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * (sampling frequency / 2). 39403a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <p>The layout in the returned byte array is as follows: 39503a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <ul> 39603a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <li> n is the capture size returned by getCaptureSize()</li> 39703a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <li> Rfk, Ifk are respectively the real and imaginary parts of the kth frequency 39803a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * component</li> 39903a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <li> If Fs is the sampling frequency retuned by getSamplingRate() the kth frequency is: 40003a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * (k*Fs)/(n/2) </li> 40103a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * </ul> 40203a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <table border="0" cellspacing="0" cellpadding="0"> 40303a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <tr><td>Index </p></td> 40403a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>0 </p></td> 40503a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>1 </p></td> 40603a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>2 </p></td> 40703a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>3 </p></td> 40803a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>4 </p></td> 40903a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>5 </p></td> 41003a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>... </p></td> 41103a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>n - 2 </p></td> 41203a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>n - 1 </p></td></tr> 41303a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <tr><td>Data </p></td> 41403a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>Rf0 </p></td> 41503a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>Rf(n/2) </p></td> 41603a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>Rf1 </p></td> 41703a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>If1 </p></td> 41803a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>Rf2 </p></td> 41903a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>If2 </p></td> 42003a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>... </p></td> 42103a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>Rf(n-1)/2 </p></td> 42203a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * <td>If(n-1)/2 </p></td></tr> 42303a4090b4d5965ff01cbb03dcf6d96b30d634fa3Eric Laurent * </table> 424df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param fft array of bytes where the FFT should be returned 425df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return {@link #SUCCESS} in case of success, 426df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #ERROR_NO_MEMORY}, {@link #ERROR_INVALID_OPERATION} or {@link #ERROR_DEAD_OBJECT} 427df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * in case of failure. 428df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @throws IllegalStateException 429df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 430df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int getFft(byte[] fft) 431df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throws IllegalStateException { 432df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mStateLock) { 433df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (mState != STATE_ENABLED) { 434df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent throw(new IllegalStateException("getFft() called in wrong state: "+mState)); 435df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 436df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return native_getFft(fft); 437df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 438df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 439df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 440df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //--------------------------------------------------------- 441df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Interface definitions 442df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------- 443df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 444df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * The OnDataCaptureListener interface defines methods called by the Visualizer to periodically 445df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * update the audio visualization capture. 446df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * The client application can implement this interface and register the listener with the 447df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #setDataCaptureListener(OnDataCaptureListener, int, boolean, boolean)} method. 448df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 449df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public interface OnDataCaptureListener { 450df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 451df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Method called when a new waveform capture is available. 452449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * <p>Data in the waveform buffer is valid only within the scope of the callback. 453449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * Applications which needs access to the waveform data after returning from the callback 454449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * should make a copy of the data instead of holding a reference. 455df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param visualizer Visualizer object on which the listener is registered. 456df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param waveform array of bytes containing the waveform representation. 457df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param samplingRate sampling rate of the audio visualized. 458df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 459df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent void onWaveFormDataCapture(Visualizer visualizer, byte[] waveform, int samplingRate); 460df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 461df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 462df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Method called when a new frequency capture is available. 463449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * <p>Data in the fft buffer is valid only within the scope of the callback. 464449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * Applications which needs access to the fft data after returning from the callback 465449725f9aa67136a38c7554ba76ac4e27e5e3bd3John Grossman * should make a copy of the data instead of holding a reference. 466df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param visualizer Visualizer object on which the listener is registered. 467df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param fft array of bytes containing the frequency representation. 468df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param samplingRate sampling rate of the audio visualized. 469df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 470df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent void onFftDataCapture(Visualizer visualizer, byte[] fft, int samplingRate); 471df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 472df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 473df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 474df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Registers an OnDataCaptureListener interface and specifies the rate at which the capture 475df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * should be updated as well as the type of capture requested. 476df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * <p>Call this method with a null listener to stop receiving the capture updates. 477df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param listener OnDataCaptureListener registered 478df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param rate rate in milliHertz at which the capture should be updated 479df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param waveform true if a waveform capture is requested: the onWaveFormDataCapture() 480df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * method will be called on the OnDataCaptureListener interface. 481df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @param fft true if a frequency capture is requested: the onFftDataCapture() method will be 482df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * called on the OnDataCaptureListener interface. 483df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * @return {@link #SUCCESS} in case of success, 484df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * {@link #ERROR_NO_INIT} or {@link #ERROR_BAD_VALUE} in case of failure. 485df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 486df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public int setDataCaptureListener(OnDataCaptureListener listener, 487df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int rate, boolean waveform, boolean fft) { 488df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mListenerLock) { 489df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mCaptureListener = listener; 490df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 491df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (listener == null) { 492df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // make sure capture callback is stopped in native code 493df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent waveform = false; 494df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent fft = false; 495df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 496df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int status = native_setPeriodicCapture(rate, waveform, fft); 497df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (status == SUCCESS) { 498df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if ((listener != null) && (mNativeEventHandler == null)) { 499df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent Looper looper; 500df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if ((looper = Looper.myLooper()) != null) { 501df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mNativeEventHandler = new NativeEventHandler(this, looper); 502df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } else if ((looper = Looper.getMainLooper()) != null) { 503df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mNativeEventHandler = new NativeEventHandler(this, looper); 504df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } else { 505df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mNativeEventHandler = null; 506df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent status = ERROR_NO_INIT; 507df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 508df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 509df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 510df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return status; 511df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 512df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 513df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent /** 5143540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * @hide 5153540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * 5163540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * The OnServerDiedListener interface defines a method called by the Visualizer to indicate that 5173540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * the connection to the native media server has been broken and that the Visualizer object will 5183540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * need to be released and re-created. 5193540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * The client application can implement this interface and register the listener with the 5203540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * {@link #setServerDiedListener(OnServerDiedListener)} method. 5213540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman */ 5223540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman public interface OnServerDiedListener { 5233540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman /** 5243540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * @hide 5253540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * 5263540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * Method called when the native media server has died. 5273540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * <p>If the native media server encounters a fatal error and needs to restart, the binder 5283540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * connection from the {@link #Visualizer} to the media server will be broken. Data capture 5293540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * callbacks will stop happening, and client initiated calls to the {@link #Visualizer} 5303540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * instance will fail with the error code {@link #DEAD_OBJECT}. To restore functionality, 5313540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * clients should {@link #release()} their old visualizer and create a new instance. 5323540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman */ 5333540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman void onServerDied(); 5343540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 5353540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 5363540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman /** 5373540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * @hide 5383540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * 5393540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * Registers an OnServerDiedListener interface. 5403540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * <p>Call this method with a null listener to stop receiving server death notifications. 5413540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman * @return {@link #SUCCESS} in case of success, 5423540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman */ 5433540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman public int setServerDiedListener(OnServerDiedListener listener) { 5443540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman synchronized (mListenerLock) { 5453540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman mServerDiedListener = listener; 5463540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 5473540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman return SUCCESS; 5483540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 5493540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 5503540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman /** 551df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent * Helper class to handle the forwarding of native events to the appropriate listeners 552df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent */ 553df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private class NativeEventHandler extends Handler 554df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent { 555df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private Visualizer mVisualizer; 556df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 557df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent public NativeEventHandler(Visualizer v, Looper looper) { 558df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent super(looper); 559df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent mVisualizer = v; 560df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 561df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 5623540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman private void handleCaptureMessage(Message msg) { 563df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent OnDataCaptureListener l = null; 564df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent synchronized (mListenerLock) { 565df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent l = mVisualizer.mCaptureListener; 566df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 567df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 568df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (l != null) { 569df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent byte[] data = (byte[])msg.obj; 570df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int samplingRate = msg.arg1; 5713540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 572df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent switch(msg.what) { 573df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent case NATIVE_EVENT_PCM_CAPTURE: 574df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent l.onWaveFormDataCapture(mVisualizer, data, samplingRate); 575df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent break; 576df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent case NATIVE_EVENT_FFT_CAPTURE: 577df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent l.onFftDataCapture(mVisualizer, data, samplingRate); 578df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent break; 579df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent default: 5803540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman Log.e(TAG,"Unknown native event in handleCaptureMessge: "+msg.what); 581df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent break; 582df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 583df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 584df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 5853540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 5863540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman private void handleServerDiedMessage(Message msg) { 5873540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman OnServerDiedListener l = null; 5883540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman synchronized (mListenerLock) { 5893540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman l = mVisualizer.mServerDiedListener; 5903540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 5913540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 5923540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman if (l != null) 5933540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman l.onServerDied(); 5943540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 5953540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 5963540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman @Override 5973540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman public void handleMessage(Message msg) { 5983540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman if (mVisualizer == null) { 5993540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman return; 6003540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 6013540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman 6023540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman switch(msg.what) { 6033540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman case NATIVE_EVENT_PCM_CAPTURE: 6043540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman case NATIVE_EVENT_FFT_CAPTURE: 6053540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman handleCaptureMessage(msg); 6063540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman break; 6073540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman case NATIVE_EVENT_SERVER_DIED: 6083540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman handleServerDiedMessage(msg); 6093540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman break; 6103540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman default: 6113540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman Log.e(TAG,"Unknown native event: "+msg.what); 6123540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman break; 6133540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 6143540a0197f56c4bcd7d7419f4502bfca34257de2John Grossman } 615df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 616df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 617df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //--------------------------------------------------------- 618df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Interface definitions 619df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------- 620df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 621df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private static native final void native_init(); 622df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 623df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_setup(Object audioeffect_this, 624df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int audioSession, 625df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int[] id); 626df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 627df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final void native_finalize(); 628df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 629df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final void native_release(); 630df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 631df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_setEnabled(boolean enabled); 632df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 633df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final boolean native_getEnabled(); 634df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 635df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_setCaptureSize(int size); 636df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 637df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_getCaptureSize(); 638df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 639e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi private native final int native_setScalingMode(int mode); 640e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi 641e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi private native final int native_getScalingMode(); 642e1123e7f36723a8b888501c9a22a589297849ca2Jean-Michel Trivi 643df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_getSamplingRate(); 644df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 645df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_getWaveForm(byte[] waveform); 646df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 647df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_getFft(byte[] fft); 648df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 649df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private native final int native_setPeriodicCapture(int rate, boolean waveForm, boolean fft); 650df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 651df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //--------------------------------------------------------- 652df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent // Java methods called from the native side 653df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent //-------------------- 654df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent @SuppressWarnings("unused") 655df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent private static void postEventFromNative(Object effect_ref, 656df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent int what, int arg1, int arg2, Object obj) { 657df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent Visualizer visu = (Visualizer)((WeakReference)effect_ref).get(); 658df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (visu == null) { 659df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent return; 660df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 661df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 662df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent if (visu.mNativeEventHandler != null) { 663df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent Message m = visu.mNativeEventHandler.obtainMessage(what, arg1, arg2, obj); 664df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent visu.mNativeEventHandler.sendMessage(m); 665df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 666df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 667df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent } 668df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 669df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent} 670df9b81ced437b11f8a3fcf4ba3ea6af703d121e2Eric Laurent 671