|
40 | 40 | import android.content.Intent; |
41 | 41 | import android.content.IntentFilter; |
42 | 42 | import android.content.pm.PackageManager; |
| 43 | +import android.content.res.Configuration; |
43 | 44 | import android.database.ContentObserver; |
44 | 45 | import android.media.MediaPlayer.OnCompletionListener; |
45 | 46 | import android.media.MediaPlayer.OnErrorListener; |
@@ -371,6 +372,8 @@ public void onError(int error) { |
371 | 372 | // Used to play ringtones outside system_server |
372 | 373 | private volatile IRingtonePlayer mRingtonePlayer; |
373 | 374 |
|
| 375 | + private int mDeviceOrientation = Configuration.ORIENTATION_UNDEFINED; |
| 376 | + |
374 | 377 | /////////////////////////////////////////////////////////////////////////// |
375 | 378 | // Construction |
376 | 379 | /////////////////////////////////////////////////////////////////////////// |
@@ -428,6 +431,16 @@ public AudioService(Context context) { |
428 | 431 | intentFilter.addAction(Intent.ACTION_BOOT_COMPLETED); |
429 | 432 | intentFilter.addAction(Intent.ACTION_SCREEN_ON); |
430 | 433 | intentFilter.addAction(Intent.ACTION_SCREEN_OFF); |
| 434 | + |
| 435 | + // Register a configuration change listener only if requested by system properties |
| 436 | + // to monitor orientation changes (off by default) |
| 437 | + if (SystemProperties.getBoolean("ro.audio.monitorOrientation", false)) { |
| 438 | + Log.v(TAG, "monitoring device orientation"); |
| 439 | + intentFilter.addAction(Intent.ACTION_CONFIGURATION_CHANGED); |
| 440 | + // initialize orientation in AudioSystem |
| 441 | + setOrientationForAudioSystem(); |
| 442 | + } |
| 443 | + |
431 | 444 | context.registerReceiver(mReceiver, intentFilter); |
432 | 445 |
|
433 | 446 | // Register for package removal intent broadcasts for media button receiver persistence |
@@ -2778,6 +2791,11 @@ public void handleMessage(Message msg) { |
2778 | 2791 | // Restore master volume |
2779 | 2792 | restoreMasterVolume(); |
2780 | 2793 |
|
| 2794 | + // Reset device orientation (if monitored for this device) |
| 2795 | + if (SystemProperties.getBoolean("ro.audio.monitorOrientation", false)) { |
| 2796 | + setOrientationForAudioSystem(); |
| 2797 | + } |
| 2798 | + |
2781 | 2799 | // indicate the end of reconfiguration phase to audio HAL |
2782 | 2800 | AudioSystem.setParameters("restarting=false"); |
2783 | 2801 | break; |
@@ -3165,6 +3183,8 @@ public void onReceive(Context context, Intent intent) { |
3165 | 3183 | AudioSystem.setParameters("screen_state=on"); |
3166 | 3184 | } else if (action.equals(Intent.ACTION_SCREEN_OFF)) { |
3167 | 3185 | AudioSystem.setParameters("screen_state=off"); |
| 3186 | + } else if (action.equalsIgnoreCase(Intent.ACTION_CONFIGURATION_CHANGED)) { |
| 3187 | + handleConfigurationChanged(context); |
3168 | 3188 | } |
3169 | 3189 | } |
3170 | 3190 | } |
@@ -4282,6 +4302,52 @@ public void remoteControlDisplayUsesBitmapSize(IRemoteControlDisplay rcd, int w, |
4282 | 4302 | } |
4283 | 4303 | } |
4284 | 4304 |
|
| 4305 | + //========================================================================================== |
| 4306 | + // Device orientation |
| 4307 | + //========================================================================================== |
| 4308 | + /** |
| 4309 | + * Handles device configuration changes that may map to a change in the orientation. |
| 4310 | + * This feature is optional, and is defined by the definition and value of the |
| 4311 | + * "ro.audio.monitorOrientation" system property. |
| 4312 | + */ |
| 4313 | + private void handleConfigurationChanged(Context context) { |
| 4314 | + try { |
| 4315 | + // reading new orientation "safely" (i.e. under try catch) in case anything |
| 4316 | + // goes wrong when obtaining resources and configuration |
| 4317 | + int newOrientation = context.getResources().getConfiguration().orientation; |
| 4318 | + if (newOrientation != mDeviceOrientation) { |
| 4319 | + mDeviceOrientation = newOrientation; |
| 4320 | + setOrientationForAudioSystem(); |
| 4321 | + } |
| 4322 | + } catch (Exception e) { |
| 4323 | + Log.e(TAG, "Error retrieving device orientation: " + e); |
| 4324 | + } |
| 4325 | + } |
| 4326 | + |
| 4327 | + private void setOrientationForAudioSystem() { |
| 4328 | + switch (mDeviceOrientation) { |
| 4329 | + case Configuration.ORIENTATION_LANDSCAPE: |
| 4330 | + //Log.i(TAG, "orientation is landscape"); |
| 4331 | + AudioSystem.setParameters("orientation=landscape"); |
| 4332 | + break; |
| 4333 | + case Configuration.ORIENTATION_PORTRAIT: |
| 4334 | + //Log.i(TAG, "orientation is portrait"); |
| 4335 | + AudioSystem.setParameters("orientation=portrait"); |
| 4336 | + break; |
| 4337 | + case Configuration.ORIENTATION_SQUARE: |
| 4338 | + //Log.i(TAG, "orientation is square"); |
| 4339 | + AudioSystem.setParameters("orientation=square"); |
| 4340 | + break; |
| 4341 | + case Configuration.ORIENTATION_UNDEFINED: |
| 4342 | + //Log.i(TAG, "orientation is undefined"); |
| 4343 | + AudioSystem.setParameters("orientation=undefined"); |
| 4344 | + break; |
| 4345 | + default: |
| 4346 | + Log.e(TAG, "Unknown orientation"); |
| 4347 | + } |
| 4348 | + } |
| 4349 | + |
| 4350 | + |
4285 | 4351 | @Override |
4286 | 4352 | public void setRingtonePlayer(IRingtonePlayer player) { |
4287 | 4353 | mContext.enforceCallingOrSelfPermission(REMOTE_AUDIO_PLAYBACK, null); |
|
0 commit comments