VolumeUI.java revision c86f573fb8ef20097f92357c7763358f3a56ea20
1package com.android.systemui.volume; 2 3import android.app.ActivityManagerNative; 4import android.content.Context; 5import android.content.Intent; 6import android.database.ContentObserver; 7import android.media.AudioManager; 8import android.media.IRemoteVolumeController; 9import android.media.IVolumeController; 10import android.media.session.ISessionController; 11import android.media.session.MediaController; 12import android.media.session.MediaSessionManager; 13import android.net.Uri; 14import android.os.AsyncTask; 15import android.os.Handler; 16import android.os.RemoteException; 17import android.os.UserHandle; 18import android.provider.Settings; 19import android.util.Log; 20 21import com.android.systemui.R; 22import com.android.systemui.SystemUI; 23import com.android.systemui.keyguard.KeyguardViewMediator; 24import com.android.systemui.statusbar.policy.ZenModeController; 25import com.android.systemui.statusbar.policy.ZenModeControllerImpl; 26 27/* 28 * Copyright (C) 2014 The Android Open Source Project 29 * 30 * Licensed under the Apache License, Version 2.0 (the "License"); 31 * you may not use this file except in compliance with the License. 32 * You may obtain a copy of the License at 33 * 34 * http://www.apache.org/licenses/LICENSE-2.0 35 * 36 * Unless required by applicable law or agreed to in writing, software 37 * distributed under the License is distributed on an "AS IS" BASIS, 38 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 39 * See the License for the specific language governing permissions and 40 * limitations under the License. 41 */ 42 43public class VolumeUI extends SystemUI { 44 private static final String TAG = "VolumeUI"; 45 private static final String SETTING = "systemui_volume_controller"; // for testing 46 private static final Uri SETTING_URI = Settings.Global.getUriFor(SETTING); 47 private static final int DEFAULT = 1; // enabled by default 48 49 private final Handler mHandler = new Handler(); 50 51 private AudioManager mAudioManager; 52 private MediaSessionManager mMediaSessionManager; 53 private VolumeController mVolumeController; 54 private RemoteVolumeController mRemoteVolumeController; 55 56 private VolumePanel mDialogPanel; 57 private VolumePanel mPanel; 58 private int mDismissDelay; 59 60 @Override 61 public void start() { 62 mAudioManager = (AudioManager) mContext.getSystemService(Context.AUDIO_SERVICE); 63 mMediaSessionManager = (MediaSessionManager) mContext 64 .getSystemService(Context.MEDIA_SESSION_SERVICE); 65 initPanel(); 66 mVolumeController = new VolumeController(); 67 mRemoteVolumeController = new RemoteVolumeController(); 68 putComponent(VolumeComponent.class, mVolumeController); 69 updateController(); 70 mContext.getContentResolver().registerContentObserver(SETTING_URI, false, mObserver); 71 } 72 73 private void updateController() { 74 if (Settings.Global.getInt(mContext.getContentResolver(), SETTING, DEFAULT) != 0) { 75 Log.d(TAG, "Registering volume controller"); 76 mAudioManager.setVolumeController(mVolumeController); 77 mMediaSessionManager.setRemoteVolumeController(mRemoteVolumeController); 78 } else { 79 Log.d(TAG, "Unregistering volume controller"); 80 mAudioManager.setVolumeController(null); 81 mMediaSessionManager.setRemoteVolumeController(null); 82 } 83 } 84 85 private void initPanel() { 86 mDismissDelay = mContext.getResources().getInteger(R.integer.volume_panel_dismiss_delay); 87 mPanel = new VolumePanel(mContext, null, new ZenModeControllerImpl(mContext, mHandler)); 88 mPanel.setCallback(new VolumePanel.Callback() { 89 @Override 90 public void onZenSettings() { 91 mHandler.removeCallbacks(mStartZenSettings); 92 mHandler.post(mStartZenSettings); 93 } 94 95 @Override 96 public void onInteraction() { 97 final KeyguardViewMediator kvm = getComponent(KeyguardViewMediator.class); 98 if (kvm != null) { 99 kvm.userActivity(); 100 } 101 } 102 103 @Override 104 public void onVisible(boolean visible) { 105 if (mAudioManager != null && mVolumeController != null) { 106 mAudioManager.notifyVolumeControllerVisible(mVolumeController, visible); 107 } 108 } 109 }); 110 mDialogPanel = mPanel; 111 } 112 113 private final ContentObserver mObserver = new ContentObserver(mHandler) { 114 public void onChange(boolean selfChange, Uri uri) { 115 if (SETTING_URI.equals(uri)) { 116 updateController(); 117 } 118 } 119 }; 120 121 private final Runnable mStartZenSettings = new Runnable() { 122 @Override 123 public void run() { 124 AsyncTask.execute(new Runnable() { 125 @Override 126 public void run() { 127 try { 128 // Dismiss the lock screen when Settings starts. 129 ActivityManagerNative.getDefault().dismissKeyguardOnNextActivity(); 130 } catch (RemoteException e) { 131 } 132 final Intent intent = ZenModePanel.ZEN_SETTINGS; 133 intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP); 134 mContext.startActivityAsUser(intent, new UserHandle(UserHandle.USER_CURRENT)); 135 136 // dismiss shade if showing 137 mContext.sendBroadcast(new Intent(Intent.ACTION_CLOSE_SYSTEM_DIALOGS)); 138 } 139 }); 140 mDialogPanel.postDismiss(mDismissDelay); 141 } 142 }; 143 144 /** For now, simply host an unmodified base volume panel in this process. */ 145 private final class VolumeController extends IVolumeController.Stub implements VolumeComponent { 146 147 @Override 148 public void displaySafeVolumeWarning(int flags) throws RemoteException { 149 mPanel.postDisplaySafeVolumeWarning(flags); 150 } 151 152 @Override 153 public void volumeChanged(int streamType, int flags) 154 throws RemoteException { 155 mPanel.postVolumeChanged(streamType, flags); 156 } 157 158 @Override 159 public void masterVolumeChanged(int flags) throws RemoteException { 160 mPanel.postMasterVolumeChanged(flags); 161 } 162 163 @Override 164 public void masterMuteChanged(int flags) throws RemoteException { 165 mPanel.postMasterMuteChanged(flags); 166 } 167 168 @Override 169 public void setLayoutDirection(int layoutDirection) 170 throws RemoteException { 171 mPanel.postLayoutDirection(layoutDirection); 172 } 173 174 @Override 175 public void dismiss() throws RemoteException { 176 mPanel.postDismiss(0); 177 } 178 179 @Override 180 public ZenModeController getZenController() { 181 return mDialogPanel.getZenController(); 182 } 183 184 @Override 185 public void setVolumePanel(VolumePanel panel) { 186 mPanel = panel == null ? mDialogPanel : panel; 187 } 188 } 189 190 private final class RemoteVolumeController extends IRemoteVolumeController.Stub { 191 192 @Override 193 public void remoteVolumeChanged(ISessionController binder, int flags) 194 throws RemoteException { 195 MediaController controller = new MediaController(binder); 196 mPanel.postRemoteVolumeChanged(controller, flags); 197 } 198 199 @Override 200 public void updateRemoteController(ISessionController session) throws RemoteException { 201 mPanel.postRemoteSliderVisibility(session != null); 202 // TODO stash default session in case the slider can be opened other 203 // than by remoteVolumeChanged. 204 } 205 } 206} 207