1391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent/* 2391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * Copyright (C) 2010 The Android Open Source Project 3391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * 4391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * Licensed under the Apache License, Version 2.0 (the "License"); 5391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * you may not use this file except in compliance with the License. 6391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * You may obtain a copy of the License at 7391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * 8391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * http://www.apache.org/licenses/LICENSE-2.0 9391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * 10391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * Unless required by applicable law or agreed to in writing, software 11391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * distributed under the License is distributed on an "AS IS" BASIS, 12391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * See the License for the specific language governing permissions and 14391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * limitations under the License. 15391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent */ 16391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 17391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurentpackage com.android.mediaframeworktest.functional; 18391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 191a5149e5d7f2dddc8b324f7695e69fd89af73c52Eric Laurentimport android.media.audiofx.Visualizer; 20391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurentimport android.util.Log; 21391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 22391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent/** 23391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * The EnergyProbe class provides audio signal energy measurements based on the FFT returned 24391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * by the Visualizer class. The measure is qualitative and not quantitative in that the returned 25391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * value has no unit and is just proportional to the amount of energy present around the 26391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent * specified frequency. 27391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent */ 28391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 29391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurentpublic class EnergyProbe { 30391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private String TAG = "EnergyProbe"; 31391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 32391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private static int CAPTURE_SIZE = 1024; 33391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private static int MEASURE_COUNT = 5; 34391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private static int AVERAGE_COUNT = 3; 35391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 36391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private Visualizer mVisualizer = null; 37391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private int mMaxFrequency = 0; 38391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private int mCapturePeriodMs; 39391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent private byte[] mFft = new byte[CAPTURE_SIZE]; 40391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 41391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent public EnergyProbe(int session) { 42391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent try { 43391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer = new Visualizer(session); 44391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (mVisualizer != null) { 45391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer.setCaptureSize(CAPTURE_SIZE); 46391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mMaxFrequency = mVisualizer.getSamplingRate() / 2000; 47391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mCapturePeriodMs = 1000000 / mVisualizer.getMaxCaptureRate(); 48391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 49391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } catch (UnsupportedOperationException e) { 50391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent Log.e(TAG, "Error creating visualizer"); 51391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } catch (IllegalStateException e) { 52391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent Log.e(TAG, "Error configuring visualizer"); 53391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 54391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 55391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 56391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent public int capture(int freq) throws InterruptedException { 57391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent int energy = 0; 58391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent int count = 0; 59391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 60391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (freq > mMaxFrequency) { 61391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent return 0; 62391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 63391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 64391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (mVisualizer != null) { 65391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent try { 66391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer.setEnabled(true); 67391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent for (int i = 0; i < MEASURE_COUNT; i++) { 68391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (mVisualizer.getFft(mFft) == Visualizer.SUCCESS) { 69391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (freq == mMaxFrequency) { 70391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent energy += (int)mFft[0] * (int)mFft[0]; 71391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } else { 72391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent int bin = 2 * (freq * CAPTURE_SIZE / mMaxFrequency / 2); 73391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (bin < 2) bin = 2; 74391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent int tmp = 0; 75391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent int j; 76391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent for (j = 0; 77391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent (j < AVERAGE_COUNT) && ((bin + 2 * j) < CAPTURE_SIZE); 78391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent j++) { 79391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent tmp += (int)mFft[bin + 2 * j] * (int)mFft[bin + 2 * j] + 80391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent (int)mFft[bin + 2 * j + 1] * (int)mFft[bin + 2 * j + 1]; 81391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 82391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent // j is always != 0 83391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent energy += tmp/j; 84391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 85391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent count++; 86391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 87391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent Thread.sleep(mCapturePeriodMs); 88391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 89391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer.setEnabled(false); 90391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } catch (IllegalStateException e) { 91391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent Log.e(TAG, "Error capturing audio"); 92391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 93391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 94391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (count == 0) { 95391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent return 0; 96391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 97391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent return energy/count; 98391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 99391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent 100391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent public void release() { 101391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent if (mVisualizer != null) { 102391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer.release(); 103391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent mVisualizer = null; 104391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 105391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent } 106391e2d0d88c1acd87b1503be276cfa4e7ce66c88Eric Laurent} 107