183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi/* 283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * Copyright (C) 2013 The Android Open Source Project 383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * 483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * Licensed under the Apache License, Version 2.0 (the "License"); 583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * you may not use this file except in compliance with the License. 683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * You may obtain a copy of the License at 783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * 883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * http://www.apache.org/licenses/LICENSE-2.0 983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * 1083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * Unless required by applicable law or agreed to in writing, software 1183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * distributed under the License is distributed on an "AS IS" BASIS, 1283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * See the License for the specific language governing permissions and 1483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * limitations under the License. 1583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 1683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 176156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockpackage com.android.server.audio; 1883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 190212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Triviimport android.annotation.NonNull; 2099489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Triviimport android.annotation.Nullable; 216156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockimport android.media.AudioAttributes; 226156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockimport android.media.AudioFocusInfo; 236156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockimport android.media.AudioManager; 246156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockimport android.media.IAudioFocusDispatcher; 2583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Triviimport android.os.IBinder; 2683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Triviimport android.util.Log; 2783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 28d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Triviimport com.android.internal.annotations.GuardedBy; 296156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockimport com.android.server.audio.MediaFocusControl.AudioFocusDeathHandler; 306156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlock 3183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Triviimport java.io.PrintWriter; 3283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 3383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi/** 3483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * @hide 3583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * Class to handle all the information about a user of audio focus. The lifecycle of each 3683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * instance is managed by android.media.MediaFocusControl, from its addition to the audio focus 37126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi * stack, or the map of focus owners for an external focus policy, to its release. 3883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 396156017c2217d0fbbbb03434986250ec6bbd69d8John Spurlockpublic class FocusRequester { 4083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 4183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi // on purpose not using this classe's name, as it will only be used from MediaFocusControl 4283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private static final String TAG = "MediaFocusControl"; 43cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi private static final boolean DEBUG = false; 4483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 45e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi private AudioFocusDeathHandler mDeathHandler; // may be null 46e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi private IAudioFocusDispatcher mFocusDispatcher; // may be null 47e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi private final IBinder mSourceRef; // may be null 4883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private final String mClientId; 4983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private final String mPackageName; 5083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private final int mCallingUid; 510212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi private final MediaFocusControl mFocusController; // never null 52461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi private final int mSdkTarget; 5399489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi 5483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi /** 5583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * the audio focus gain request that caused the addition of this object in the focus stack. 5683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 5783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private final int mFocusGainRequest; 5883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi /** 59fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi * the flags associated with the gain request that qualify the type of grant (e.g. accepting 60fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi * delay vs grant must be immediate) 61fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi */ 62fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi private final int mGrantFlags; 63fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi /** 642380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi * the audio focus loss received my mFocusDispatcher, is AudioManager.AUDIOFOCUS_NONE if 6583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * it never lost focus. 6683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 6783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private int mFocusLossReceived; 6883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi /** 6999489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi * whether this focus owner listener was notified when it lost focus 7099489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi */ 7199489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi private boolean mFocusLossWasNotified; 7299489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi /** 73fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi * the audio attributes associated with the focus request 7483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 75fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi private final AudioAttributes mAttributes; 7683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 770212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi /** 780212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * Class constructor 790212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param aa 800212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param focusRequest 810212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param grantFlags 820212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param afl 830212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param source 840212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param id 850212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param hdlr 860212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param pn 870212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param uid 880212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi * @param ctlr cannot be null 890212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi */ 90fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi FocusRequester(AudioAttributes aa, int focusRequest, int grantFlags, 9183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi IAudioFocusDispatcher afl, IBinder source, String id, AudioFocusDeathHandler hdlr, 92461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi String pn, int uid, @NonNull MediaFocusControl ctlr, int sdk) { 93fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi mAttributes = aa; 9483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mFocusDispatcher = afl; 9583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mSourceRef = source; 9683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mClientId = id; 9783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mDeathHandler = hdlr; 9883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mPackageName = pn; 9983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mCallingUid = uid; 10083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi mFocusGainRequest = focusRequest; 101fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi mGrantFlags = grantFlags; 1022380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi mFocusLossReceived = AudioManager.AUDIOFOCUS_NONE; 103087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi mFocusLossWasNotified = true; 1040212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusController = ctlr; 105461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi mSdkTarget = sdk; 10683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 10783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 108126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi FocusRequester(AudioFocusInfo afi, IAudioFocusDispatcher afl, 109126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi IBinder source, AudioFocusDeathHandler hdlr, @NonNull MediaFocusControl ctlr) { 110126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mAttributes = afi.getAttributes(); 111126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mClientId = afi.getClientId(); 112126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mPackageName = afi.getPackageName(); 113126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mCallingUid = afi.getClientUid(); 114126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusGainRequest = afi.getGainRequest(); 115126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusLossReceived = AudioManager.AUDIOFOCUS_NONE; 116087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi mFocusLossWasNotified = true; 117126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mGrantFlags = afi.getFlags(); 118461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi mSdkTarget = afi.getSdkTarget(); 119126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi 120126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusDispatcher = afl; 121126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mSourceRef = source; 122126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mDeathHandler = hdlr; 123126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusController = ctlr; 124126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 12583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 12683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi boolean hasSameClient(String otherClient) { 12783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi try { 12883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return mClientId.compareTo(otherClient) == 0; 12983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } catch (NullPointerException e) { 13083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return false; 13183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 13283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 13383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 134958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi boolean isLockedFocusOwner() { 135958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi return ((mGrantFlags & AudioManager.AUDIOFOCUS_FLAG_LOCK) != 0); 136958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi } 137958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi 13883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi boolean hasSameBinder(IBinder ib) { 13983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return (mSourceRef != null) && mSourceRef.equals(ib); 14083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 14183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 142126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi boolean hasSameDispatcher(IAudioFocusDispatcher fd) { 143126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi return (mFocusDispatcher != null) && mFocusDispatcher.equals(fd); 144126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 145126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi 14683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi boolean hasSamePackage(String pack) { 14783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi try { 14883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return mPackageName.compareTo(pack) == 0; 14983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } catch (NullPointerException e) { 15083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return false; 15183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 15283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 15383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 15483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi boolean hasSameUid(int uid) { 15583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return mCallingUid == uid; 15683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 15783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 15899489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi int getClientUid() { 15999489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi return mCallingUid; 16099489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } 16199489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi 162958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi String getClientId() { 163958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi return mClientId; 164958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi } 16583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 16683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi int getGainRequest() { 16783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return mFocusGainRequest; 16883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 16983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 170fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi int getGrantFlags() { 171fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi return mGrantFlags; 172fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi } 173fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi 174fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi AudioAttributes getAudioAttributes() { 175fd6ad747e6c268753d0edf7a5a59b6815b190854Jean-Michel Trivi return mAttributes; 17683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 17783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 178461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi int getSdkTarget() { 179461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi return mSdkTarget; 180461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi } 18183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 18283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private static String focusChangeToString(int focus) { 18383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi switch(focus) { 1842380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_NONE: 18583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "none"; 18683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN: 18783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "GAIN"; 18883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT: 18983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "GAIN_TRANSIENT"; 19083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK: 19183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "GAIN_TRANSIENT_MAY_DUCK"; 1922380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE: 1932380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi return "GAIN_TRANSIENT_EXCLUSIVE"; 19483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS: 19583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "LOSS"; 19683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT: 19783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "LOSS_TRANSIENT"; 19883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK: 19983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "LOSS_TRANSIENT_CAN_DUCK"; 20083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi default: 20183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return "[invalid focus change" + focus + "]"; 20283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 20383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 20483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 20583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private String focusGainToString() { 20683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return focusChangeToString(mFocusGainRequest); 20783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 20883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 20983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private String focusLossToString() { 21083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi return focusChangeToString(mFocusLossReceived); 21183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 21283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 213958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi private static String flagsToString(int flags) { 214958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi String msg = new String(); 2150212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if ((flags & AudioManager.AUDIOFOCUS_FLAG_DELAY_OK) != 0) { 2160212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi msg += "DELAY_OK"; 2170212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 2180212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if ((flags & AudioManager.AUDIOFOCUS_FLAG_LOCK) != 0) { 2190212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if (!msg.isEmpty()) { msg += "|"; } 2200212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi msg += "LOCK"; 2210212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 2220212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if ((flags & AudioManager.AUDIOFOCUS_FLAG_PAUSES_ON_DUCKABLE_LOSS) != 0) { 2230212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if (!msg.isEmpty()) { msg += "|"; } 2240212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi msg += "PAUSES_ON_DUCKABLE_LOSS"; 2250212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 226958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi return msg; 227958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi } 228958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi 22983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi void dump(PrintWriter pw) { 23083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi pw.println(" source:" + mSourceRef 23183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi + " -- pack: " + mPackageName 23283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi + " -- client: " + mClientId 23383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi + " -- gain: " + focusGainToString() 234958876fe55ea0fdeb73c72240a2f2bab32833443Jean-Michel Trivi + " -- flags: " + flagsToString(mGrantFlags) 23583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi + " -- loss: " + focusLossToString() 23699489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi + " -- notified: " + mFocusLossWasNotified 23783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi + " -- uid: " + mCallingUid 238461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi + " -- attr: " + mAttributes 239461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi + " -- sdk:" + mSdkTarget); 24083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 24183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 24283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 24383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi void release() { 244e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi final IBinder srcRef = mSourceRef; 245e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi final AudioFocusDeathHandler deathHdlr = mDeathHandler; 24683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi try { 247e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi if (srcRef != null && deathHdlr != null) { 248e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi srcRef.unlinkToDeath(deathHdlr, 0); 24983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 250e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } catch (java.util.NoSuchElementException e) { } 251e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi mDeathHandler = null; 252e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi mFocusDispatcher = null; 25383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 25483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 25583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi @Override 25683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi protected void finalize() throws Throwable { 25783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi release(); 25883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi super.finalize(); 25983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 26083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 26183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi /** 26283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * For a given audio focus gain request, return the audio focus loss type that will result 26353e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi * from it, taking into account any previous focus loss. 26483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * @param gainRequest 26583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi * @return the audio focus loss type that matches the gain request 26683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi */ 26783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi private int focusLossForGainRequest(int gainRequest) { 26853e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi switch(gainRequest) { 26953e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN: 27053e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi switch(mFocusLossReceived) { 27153e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK: 27253e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT: 27353e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS: 2742380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_NONE: 27553e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS; 27653e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi } 2772380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE: 27853e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT: 27953e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi switch(mFocusLossReceived) { 28053e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK: 28153e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT: 2822380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_NONE: 28353e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS_TRANSIENT; 28453e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS: 28553e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS; 28653e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi } 28753e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK: 28853e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi switch(mFocusLossReceived) { 2892380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi case AudioManager.AUDIOFOCUS_NONE: 29053e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK: 291cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK; 29253e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS_TRANSIENT: 29353e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS_TRANSIENT; 29453e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi case AudioManager.AUDIOFOCUS_LOSS: 29553e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi return AudioManager.AUDIOFOCUS_LOSS; 29653e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi } 29753e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi default: 29853e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi Log.e(TAG, "focusLossForGainRequest() for invalid focus request "+ gainRequest); 2992380566debfc57eb1cc07db1306ccee23b84ddd4Jean-Michel Trivi return AudioManager.AUDIOFOCUS_NONE; 30053e6e287ffe924b6d26237e167a1a8996054e17eJean-Michel Trivi } 30183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 30283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 3030212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi /** 304d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi * Handle the loss of focus resulting from a given focus gain. 305d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi * @param focusGain the focus gain from which the loss of focus is resulting 306d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi * @param frWinner the new focus owner 307d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi * @return true if the focus loss is definitive, false otherwise. 3080212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi */ 309d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi @GuardedBy("MediaFocusControl.mAudioFocusLock") 3109228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi boolean handleFocusLossFromGain(int focusGain, final FocusRequester frWinner, boolean forceDuck) 3119228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi { 312d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi final int focusLoss = focusLossForGainRequest(focusGain); 3139228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi handleFocusLoss(focusLoss, frWinner, forceDuck); 314d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi return (focusLoss == AudioManager.AUDIOFOCUS_LOSS); 31583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 31683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 317d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi @GuardedBy("MediaFocusControl.mAudioFocusLock") 31883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi void handleFocusGain(int focusGain) { 31983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi try { 3200212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusLossReceived = AudioManager.AUDIOFOCUS_NONE; 3210212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusController.notifyExtPolicyFocusGrant_syncAf(toAudioFocusInfo(), 3220212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi AudioManager.AUDIOFOCUS_REQUEST_GRANTED); 323e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi final IAudioFocusDispatcher fd = mFocusDispatcher; 324e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi if (fd != null) { 325cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi if (DEBUG) { 326cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi Log.v(TAG, "dispatching " + focusChangeToString(focusGain) + " to " 327cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi + mClientId); 328cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi } 32999489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi if (mFocusLossWasNotified) { 33099489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi fd.dispatchAudioFocusChange(focusGain, mClientId); 33199489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } 332cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi } 333270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi mFocusController.unduckPlayers(this); 33483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } catch (android.os.RemoteException e) { 33583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi Log.e(TAG, "Failure to signal gain of audio focus due to: ", e); 33683283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 33783283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 33883283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 339d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi @GuardedBy("MediaFocusControl.mAudioFocusLock") 340270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi void handleFocusGainFromRequest(int focusRequestResult) { 341270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi if (focusRequestResult == AudioManager.AUDIOFOCUS_REQUEST_GRANTED) { 342270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi mFocusController.unduckPlayers(this); 343270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi } 344270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi } 345270f1c9d8ff38be25b8972f7d158ca178da82eb7Jean-Michel Trivi 346d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi @GuardedBy("MediaFocusControl.mAudioFocusLock") 3479228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi void handleFocusLoss(int focusLoss, @Nullable final FocusRequester frWinner, boolean forceDuck) 3489228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi { 34983283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi try { 350cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi if (focusLoss != mFocusLossReceived) { 3510212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusLossReceived = focusLoss; 35299489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi mFocusLossWasNotified = false; 3530212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi // before dispatching a focus loss, check if the following conditions are met: 3540212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi // 1/ the framework is not supposed to notify the focus loser on a DUCK loss 3557b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi // (i.e. it has a focus controller that implements a ducking policy) 3560212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi // 2/ it is a DUCK loss 3570212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi // 3/ the focus loser isn't flagged as pausing in a DUCK loss 3580212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi // if they are, do not notify the focus loser 3590212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if (!mFocusController.mustNotifyFocusOwnerOnDuck() 3600212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi && mFocusLossReceived == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK 3610212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi && (mGrantFlags 3620212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi & AudioManager.AUDIOFOCUS_FLAG_PAUSES_ON_DUCKABLE_LOSS) == 0) { 3630212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi if (DEBUG) { 3640212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi Log.v(TAG, "NOT dispatching " + focusChangeToString(mFocusLossReceived) 3650212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi + " to " + mClientId + ", to be handled externally"); 3660212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 3670212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusController.notifyExtPolicyFocusLoss_syncAf( 3680212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi toAudioFocusInfo(), false /* wasDispatched */); 3690212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi return; 3700212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 37199489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi 37299489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi // check enforcement by the framework 37399489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi boolean handled = false; 37499489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi if (focusLoss == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK 37599489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi && MediaFocusControl.ENFORCE_DUCKING 376d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi && frWinner != null) { 37799489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi // candidate for enforcement by the framework 378d9fef5cf4c62e10ed41ace93a44362b5f0142340Jean-Michel Trivi if (frWinner.mCallingUid != this.mCallingUid) { 3799228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi if (!forceDuck && ((mGrantFlags 3809228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi & AudioManager.AUDIOFOCUS_FLAG_PAUSES_ON_DUCKABLE_LOSS) != 0)) { 3817b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi // the focus loser declared it would pause instead of duck, let it 3827b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi // handle it (the framework doesn't pause for apps) 3837b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi handled = false; 384087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi Log.v(TAG, "not ducking uid " + this.mCallingUid + " - flags"); 3859228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi } else if (!forceDuck && (MediaFocusControl.ENFORCE_DUCKING_FOR_NEW && 3869228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi this.getSdkTarget() <= MediaFocusControl.DUCKING_IN_APP_SDK_LEVEL)) 3879228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi { 388087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi // legacy behavior, apps used to be notified when they should be ducking 389087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi handled = false; 390087b672797b23d6c7451f975ca7f825d64fb1bd9Jean-Michel Trivi Log.v(TAG, "not ducking uid " + this.mCallingUid + " - old SDK"); 3917b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi } else { 3929228af6bc20c27b9949df36684f9c06ca9cdb27dJean-Michel Trivi handled = mFocusController.duckPlayers(frWinner, this, forceDuck); 3937b8da92d49caf965e8616ceeba828275574f09c0Jean-Michel Trivi } 39499489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } // else: the focus change is within the same app, so let the dispatching 39599489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi // happen as if the framework was not involved. 39699489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } 39799489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi 39899489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi if (handled) { 39999489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi if (DEBUG) { 40099489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi Log.v(TAG, "NOT dispatching " + focusChangeToString(mFocusLossReceived) 40199489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi + " to " + mClientId + ", ducking implemented by framework"); 40299489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } 403081249282005640682da315d6f0e0e3697fe4b37Jean-Michel Trivi mFocusController.notifyExtPolicyFocusLoss_syncAf( 404081249282005640682da315d6f0e0e3697fe4b37Jean-Michel Trivi toAudioFocusInfo(), false /* wasDispatched */); 40599489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi return; // with mFocusLossWasNotified = false 40699489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi } 40799489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi 408e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi final IAudioFocusDispatcher fd = mFocusDispatcher; 409e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi if (fd != null) { 410cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi if (DEBUG) { 4110212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi Log.v(TAG, "dispatching " + focusChangeToString(mFocusLossReceived) + " to " 412cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi + mClientId); 413cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi } 4140212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi mFocusController.notifyExtPolicyFocusLoss_syncAf( 4150212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi toAudioFocusInfo(), true /* wasDispatched */); 41699489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi mFocusLossWasNotified = true; 417e89877245fc6dd359e435b5202901f9042819c51Jean-Michel Trivi fd.dispatchAudioFocusChange(mFocusLossReceived, mClientId); 418cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi } 419cbb212ff6f06b004ae19dfb6958ee3852716bbdcJean-Michel Trivi } 42083283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } catch (android.os.RemoteException e) { 42183283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi Log.e(TAG, "Failure to signal loss of audio focus due to:", e); 42283283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 42383283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi } 42483283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi 425126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi int dispatchFocusChange(int focusChange) { 426126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi if (mFocusDispatcher == null) { 427e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi if (MediaFocusControl.DEBUG) { Log.e(TAG, "dispatchFocusChange: no focus dispatcher"); } 428126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi return AudioManager.AUDIOFOCUS_REQUEST_FAILED; 429126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 430126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi if (focusChange == AudioManager.AUDIOFOCUS_NONE) { 431126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi if (MediaFocusControl.DEBUG) { Log.v(TAG, "dispatchFocusChange: AUDIOFOCUS_NONE"); } 432126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi return AudioManager.AUDIOFOCUS_REQUEST_FAILED; 433126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } else if ((focusChange == AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_MAY_DUCK 434126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi || focusChange == AudioManager.AUDIOFOCUS_GAIN_TRANSIENT_EXCLUSIVE 435126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi || focusChange == AudioManager.AUDIOFOCUS_GAIN_TRANSIENT 436126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi || focusChange == AudioManager.AUDIOFOCUS_GAIN) 437126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi && (mFocusGainRequest != focusChange)){ 438126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi Log.w(TAG, "focus gain was requested with " + mFocusGainRequest 439126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi + ", dispatching " + focusChange); 440126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } else if (focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT_CAN_DUCK 441126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi || focusChange == AudioManager.AUDIOFOCUS_LOSS_TRANSIENT 442126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi || focusChange == AudioManager.AUDIOFOCUS_LOSS) { 443126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusLossReceived = focusChange; 444126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 445126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi try { 446126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi mFocusDispatcher.dispatchAudioFocusChange(focusChange, mClientId); 447126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } catch (android.os.RemoteException e) { 448e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi Log.e(TAG, "dispatchFocusChange: error talking to focus listener " + mClientId, e); 449126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi return AudioManager.AUDIOFOCUS_REQUEST_FAILED; 450126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 451126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi return AudioManager.AUDIOFOCUS_REQUEST_GRANTED; 452126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi } 453126cf03f7c8e825a23e47dd133e77eb1b3b7633dJean-Michel Trivi 454e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi void dispatchFocusResultFromExtPolicy(int requestResult) { 455e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi if (mFocusDispatcher == null) { 456e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi if (MediaFocusControl.DEBUG) { 457e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi Log.e(TAG, "dispatchFocusResultFromExtPolicy: no focus dispatcher"); 458e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } 459e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } 460e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi if (DEBUG) { 461e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi Log.v(TAG, "dispatching result" + requestResult + " to " + mClientId); 462e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } 463e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi try { 464e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi mFocusDispatcher.dispatchFocusResultFromExtPolicy(requestResult, mClientId); 465e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } catch (android.os.RemoteException e) { 466e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi Log.e(TAG, "dispatchFocusResultFromExtPolicy: error talking to focus listener" 467e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi + mClientId, e); 468e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } 469e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi } 470e2d8aae2ccc51340cf4846ce28f635b825711368Jean-Michel Trivi 4710212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi AudioFocusInfo toAudioFocusInfo() { 47299489ccf740d369193a8ffc7eeb4bbde6919bd65Jean-Michel Trivi return new AudioFocusInfo(mAttributes, mCallingUid, mClientId, mPackageName, 473461922fcfc8572415aa39c43c06afce685bd998dJean-Michel Trivi mFocusGainRequest, mFocusLossReceived, mGrantFlags, mSdkTarget); 4740212be5150fb9fb3c340f3c7e51f6126372cc6f9Jean-Michel Trivi } 47583283f23eb1b7c1576e253c644b8aade6f657d0aJean-Michel Trivi} 476