10f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent/* 20f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * Copyright (C) 2011 The Android Open Source Project 30f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * 40f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * Licensed under the Apache License, Version 2.0 (the "License"); 50f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * you may not use this file except in compliance with the License. 60f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * You may obtain a copy of the License at 70f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * 80f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * http://www.apache.org/licenses/LICENSE-2.0 90f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * 100f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * Unless required by applicable law or agreed to in writing, software 110f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * distributed under the License is distributed on an "AS IS" BASIS, 120f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 130f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * See the License for the specific language governing permissions and 140f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * limitations under the License. 150f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent */ 160f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent 170f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurentpackage android.media.audiofx; 180f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent 19855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurentimport android.util.Log; 20855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent 210f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent/** 220f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * Automatic Gain Control (AGC). 230f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <p>Automatic Gain Control (AGC) is an audio pre-processing which automatically normalizes the 240f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * output of the captured signal by boosting or lowering input from the microphone to match a preset 25855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * level so that the output signal level is virtually constant. 260f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * AGC can be used by applications where the input signal dynamic range is not important but where 270f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * a constant strong capture level is desired. 280f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <p>An application creates a AutomaticGainControl object to instantiate and control an AGC 290f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * engine in the audio framework. 300f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <p>To attach the AutomaticGainControl to a particular {@link android.media.AudioRecord}, 31855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * specify the audio session ID of this AudioRecord when creating the AutomaticGainControl. 320f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * The audio session is retrieved by calling 330f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * {@link android.media.AudioRecord#getAudioSessionId()} on the AudioRecord instance. 340f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <p>On some devices, an AGC can be inserted by default in the capture path by the platform 35855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * according to the {@link android.media.MediaRecorder.AudioSource} used. The application should 36855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * call AutomaticGainControl.getEnable() after creating the AGC to check the default AGC activation 37855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * state on a particular AudioRecord session. 380f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <p>See {@link android.media.audiofx.AudioEffect} class for more details on 390f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * controlling audio effects. 400f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent */ 410f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent 420f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurentpublic class AutomaticGainControl extends AudioEffect { 430f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent 440f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent private final static String TAG = "AutomaticGainControl"; 450f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent 460f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent /** 47855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * Checks if the device implements automatic gain control. 48855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * @return true if the device implements automatic gain control, false otherwise. 49855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent */ 50855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent public static boolean isAvailable() { 51855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent return AudioEffect.isEffectTypeAvailable(AudioEffect.EFFECT_TYPE_AGC); 52855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } 53855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent 54855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent /** 55855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * Creates an AutomaticGainControl and attaches it to the AudioRecord on the audio 56855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * session specified. 57855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * @param audioSession system wide unique audio session identifier. The AutomaticGainControl 58855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * will be applied to the AudioRecord with the same audio session. 59855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * @return AutomaticGainControl created or null if the device does not implement AGC. 60855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent */ 61855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent public static AutomaticGainControl create(int audioSession) { 62855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent AutomaticGainControl agc = null; 63855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent try { 64855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent agc = new AutomaticGainControl(audioSession); 65855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } catch (IllegalArgumentException e) { 66855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent Log.w(TAG, "not implemented on this device "+agc); 67855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } catch (UnsupportedOperationException e) { 68855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent Log.w(TAG, "not enough resources"); 69855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } catch (RuntimeException e) { 70855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent Log.w(TAG, "not enough memory"); 71855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } 72b304ba5bc8fbc6034cf232cbbeeb3a34a5ce5b9fEric Laurent return agc; 73855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent } 74855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent 75855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent /** 760f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * Class constructor. 77855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * <p> The constructor is not guarantied to succeed and throws the following exceptions: 780f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <ul> 790f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <li>IllegalArgumentException is thrown if the device does not implement an AGC</li> 800f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * <li>UnsupportedOperationException is thrown is the resources allocated to audio 810f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * pre-procesing are currently exceeded.</li> 82855255d89fe0a14abe796355bebb64031ec6ff47Eric Laurent * <li>RuntimeException is thrown if a memory allocation error occurs.</li> 830f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * </ul> 840f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * 850f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * @param audioSession system wide unique audio session identifier. The AutomaticGainControl 860f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * will be applied to the AudioRecord with the same audio session. 870f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * 880f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * @throws java.lang.IllegalArgumentException 890f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * @throws java.lang.UnsupportedOperationException 900f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent * @throws java.lang.RuntimeException 910f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent */ 928dfc10571a83389593fc11b92fbf9fc1f22c9f21Eric Laurent private AutomaticGainControl(int audioSession) 930f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent throws IllegalArgumentException, UnsupportedOperationException, RuntimeException { 940f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent super(EFFECT_TYPE_AGC, EFFECT_TYPE_NULL, 0, audioSession); 950f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent } 960f7f4ece1b6b73caf608d533d833a8cdc11c8131Eric Laurent} 97