Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 1 | /* |
| 2 | * Copyright (C) 2014 The Android Open Source Project |
| 3 | * |
| 4 | * Licensed under the Apache License, Version 2.0 (the "License"); |
| 5 | * you may not use this file except in compliance with the License. |
| 6 | * You may obtain a copy of the License at |
| 7 | * |
| 8 | * http://www.apache.org/licenses/LICENSE-2.0 |
| 9 | * |
| 10 | * Unless required by applicable law or agreed to in writing, software |
| 11 | * distributed under the License is distributed on an "AS IS" BASIS, |
| 12 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| 13 | * See the License for the specific language governing permissions and |
| 14 | * limitations under the License. |
| 15 | */ |
| 16 | |
| 17 | package com.android.camera; |
| 18 | |
| 19 | import android.content.Context; |
Sascha Haeberling | 0d1764d | 2014-12-09 10:33:01 -0800 | [diff] [blame] | 20 | import android.media.AudioManager; |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 21 | import android.media.SoundPool; |
| 22 | import android.util.SparseIntArray; |
| 23 | |
Sascha Haeberling | 0d1764d | 2014-12-09 10:33:01 -0800 | [diff] [blame] | 24 | import com.android.camera.util.ApiHelper; |
| 25 | |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 26 | /** |
| 27 | * Loads a plays custom sounds. For playing system-standard sounds for various |
| 28 | * camera actions, please refer to {@link SoundClips}. |
| 29 | */ |
| 30 | public class SoundPlayer { |
| 31 | private final Context mAppContext; |
| 32 | private final SoundPool mSoundPool; |
| 33 | /** Keeps a mapping from sound resource ID to sound ID */ |
| 34 | private final SparseIntArray mResourceToSoundId = new SparseIntArray(); |
Paul Rohde | 987ee64 | 2014-12-05 12:17:15 -0800 | [diff] [blame] | 35 | private boolean mIsReleased = false; |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 36 | |
| 37 | /** |
| 38 | * Construct a new sound player. |
| 39 | */ |
| 40 | public SoundPlayer(Context appContext) { |
| 41 | mAppContext = appContext; |
Sascha Haeberling | 0d1764d | 2014-12-09 10:33:01 -0800 | [diff] [blame] | 42 | final int audioType = getAudioTypeForSoundPool(); |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 43 | mSoundPool = new SoundPool(1 /* max streams */, audioType, 0 /* quality */); |
| 44 | } |
| 45 | |
| 46 | /** |
| 47 | * Load the sound from a resource. |
| 48 | */ |
| 49 | public void loadSound(int resourceId) { |
| 50 | int soundId = mSoundPool.load(mAppContext, resourceId, 1/* priority */); |
| 51 | mResourceToSoundId.put(resourceId, soundId); |
| 52 | } |
| 53 | |
| 54 | /** |
| 55 | * Play the sound with the given resource. The resource has to be loaded |
| 56 | * before it can be played, otherwise an exception will be thrown. |
| 57 | */ |
| 58 | public void play(int resourceId, float volume) { |
| 59 | Integer soundId = mResourceToSoundId.get(resourceId); |
| 60 | if (soundId == null) { |
| 61 | throw new IllegalStateException("Sound not loaded. Must call #loadSound first."); |
| 62 | } |
| 63 | mSoundPool.play(soundId, volume, volume, 0 /* priority */, 0 /* loop */, 1 /* rate */); |
| 64 | } |
| 65 | |
| 66 | /** |
| 67 | * Unload the given sound if it's not needed anymore to release memory. |
| 68 | */ |
| 69 | public void unloadSound(int resourceId) { |
| 70 | Integer soundId = mResourceToSoundId.get(resourceId); |
| 71 | if (soundId == null) { |
| 72 | throw new IllegalStateException("Sound not loaded. Must call #loadSound first."); |
| 73 | } |
| 74 | mSoundPool.unload(soundId); |
| 75 | } |
| 76 | |
| 77 | /** |
| 78 | * Call this if you don't need the SoundPlayer anymore. All memory will be |
| 79 | * released and the object cannot be re-used. |
| 80 | */ |
| 81 | public void release() { |
Paul Rohde | 987ee64 | 2014-12-05 12:17:15 -0800 | [diff] [blame] | 82 | mIsReleased = true; |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 83 | mSoundPool.release(); |
| 84 | } |
Sascha Haeberling | 0d1764d | 2014-12-09 10:33:01 -0800 | [diff] [blame] | 85 | |
Paul Rohde | 987ee64 | 2014-12-05 12:17:15 -0800 | [diff] [blame] | 86 | public boolean isReleased() { |
| 87 | return mIsReleased; |
| 88 | } |
| 89 | |
Sascha Haeberling | 0d1764d | 2014-12-09 10:33:01 -0800 | [diff] [blame] | 90 | private static int getAudioTypeForSoundPool() { |
| 91 | // STREAM_SYSTEM_ENFORCED is hidden API. |
| 92 | return ApiHelper.getIntFieldIfExists(AudioManager.class, |
| 93 | "STREAM_SYSTEM_ENFORCED", null, AudioManager.STREAM_RING); |
| 94 | } |
Sascha Haeberling | 2d4be25 | 2014-08-27 17:56:08 -0700 | [diff] [blame] | 95 | } |