Merge "AudioService: SpatializerHelper initializes sensors" into sc-v2-dev

This commit is contained in:
Jean-Michel Trivi
2021-09-22 17:33:37 +00:00
committed by Android (Google) Code Review
3 changed files with 139 additions and 34 deletions

View File

@@ -129,6 +129,14 @@ public class Spatializer {
*/ */
public static final int SPATIALIZER_IMMERSIVE_LEVEL_MULTICHANNEL = 1; public static final int SPATIALIZER_IMMERSIVE_LEVEL_MULTICHANNEL = 1;
/**
* @hide
* Constant indicating the {@code Spatializer} on this device supports the spatialization of
* multichannel bed plus objects.
* @see #getImmersiveAudioLevel()
*/
public static final int SPATIALIZER_IMMERSIVE_LEVEL_MCHAN_BED_PLUS_OBJECTS = 2;
/** @hide */ /** @hide */
@IntDef(flag = false, value = { @IntDef(flag = false, value = {
HEAD_TRACKING_MODE_UNSUPPORTED, HEAD_TRACKING_MODE_UNSUPPORTED,

View File

@@ -243,7 +243,7 @@ public class AudioService extends IAudioService.Stub
*/ */
private static final int FLAG_ADJUST_VOLUME = 1; private static final int FLAG_ADJUST_VOLUME = 1;
private final Context mContext; final Context mContext;
private final ContentResolver mContentResolver; private final ContentResolver mContentResolver;
private final AppOpsManager mAppOps; private final AppOpsManager mAppOps;
@@ -318,6 +318,7 @@ public class AudioService extends IAudioService.Stub
private static final int MSG_A2DP_DEV_CONFIG_CHANGE = 39; private static final int MSG_A2DP_DEV_CONFIG_CHANGE = 39;
private static final int MSG_DISPATCH_AUDIO_MODE = 40; private static final int MSG_DISPATCH_AUDIO_MODE = 40;
private static final int MSG_ROUTING_UPDATED = 41; private static final int MSG_ROUTING_UPDATED = 41;
private static final int MSG_INIT_HEADTRACKING_SENSORS = 42;
// start of messages handled under wakelock // start of messages handled under wakelock
// these messages can only be queued, i.e. sent with queueMsgUnderWakeLock(), // these messages can only be queued, i.e. sent with queueMsgUnderWakeLock(),
@@ -7575,6 +7576,10 @@ public class AudioService extends IAudioService.Stub
mAudioEventWakeLock.release(); mAudioEventWakeLock.release();
break; break;
case MSG_INIT_HEADTRACKING_SENSORS:
mSpatializerHelper.onInitSensors(/*init*/ msg.arg1 == 1);
break;
case MSG_CHECK_MUSIC_ACTIVE: case MSG_CHECK_MUSIC_ACTIVE:
onCheckMusicActive((String) msg.obj); onCheckMusicActive((String) msg.obj);
break; break;
@@ -8447,6 +8452,18 @@ public class AudioService extends IAudioService.Stub
mSpatializerHelper.getEffectParameter(key, value); mSpatializerHelper.getEffectParameter(key, value);
} }
/**
* post a message to schedule init/release of head tracking sensors
* @param init initialization if true, release if false
*/
void postInitSpatializerHeadTrackingSensors(boolean init) {
sendMsg(mAudioHandler,
MSG_INIT_HEADTRACKING_SENSORS,
SENDMSG_REPLACE,
/*arg1*/ init ? 1 : 0,
0, TAG, /*delay*/ 0);
}
//========================================================================================== //==========================================================================================
private boolean readCameraSoundForced() { private boolean readCameraSoundForced() {
return SystemProperties.getBoolean("audio.camerasound.force", false) || return SystemProperties.getBoolean("audio.camerasound.force", false) ||

View File

@@ -18,6 +18,9 @@ package com.android.server.audio;
import android.annotation.NonNull; import android.annotation.NonNull;
import android.annotation.Nullable; import android.annotation.Nullable;
import android.content.Context;
import android.hardware.Sensor;
import android.hardware.SensorManager;
import android.media.AudioAttributes; import android.media.AudioAttributes;
import android.media.AudioDeviceAttributes; import android.media.AudioDeviceAttributes;
import android.media.AudioFormat; import android.media.AudioFormat;
@@ -28,6 +31,7 @@ import android.media.ISpatializerCallback;
import android.media.ISpatializerHeadToSoundStagePoseCallback; import android.media.ISpatializerHeadToSoundStagePoseCallback;
import android.media.ISpatializerHeadTrackingCallback; import android.media.ISpatializerHeadTrackingCallback;
import android.media.ISpatializerHeadTrackingModeCallback; import android.media.ISpatializerHeadTrackingModeCallback;
import android.media.SpatializationLevel;
import android.media.Spatializer; import android.media.Spatializer;
import android.media.SpatializerHeadTrackingMode; import android.media.SpatializerHeadTrackingMode;
import android.os.RemoteCallbackList; import android.os.RemoteCallbackList;
@@ -45,6 +49,7 @@ public class SpatializerHelper {
private static final String TAG = "AS.SpatializerHelper"; private static final String TAG = "AS.SpatializerHelper";
private static final boolean DEBUG = true; private static final boolean DEBUG = true;
private static final boolean DEBUG_MORE = false;
private static void logd(String s) { private static void logd(String s) {
if (DEBUG) { if (DEBUG) {
@@ -54,6 +59,7 @@ public class SpatializerHelper {
private final @NonNull AudioSystemAdapter mASA; private final @NonNull AudioSystemAdapter mASA;
private final @NonNull AudioService mAudioService; private final @NonNull AudioService mAudioService;
private @Nullable SensorManager mSensorManager;
//------------------------------------------------------------ //------------------------------------------------------------
// Spatializer state machine // Spatializer state machine
@@ -127,7 +133,7 @@ public class SpatializerHelper {
for (byte level : levels) { for (byte level : levels) {
logd("found support for level: " + level); logd("found support for level: " + level);
if (level == Spatializer.SPATIALIZER_IMMERSIVE_LEVEL_MULTICHANNEL) { if (level == Spatializer.SPATIALIZER_IMMERSIVE_LEVEL_MULTICHANNEL) {
logd("Setting Spatializer to LEVEL_MULTICHANNEL"); logd("Setting capable level to LEVEL_MULTICHANNEL");
mCapableSpatLevel = level; mCapableSpatLevel = level;
break; break;
} }
@@ -191,9 +197,16 @@ public class SpatializerHelper {
public void onLevelChanged(byte level) { public void onLevelChanged(byte level) {
logd("SpatializerCallback.onLevelChanged level:" + level); logd("SpatializerCallback.onLevelChanged level:" + level);
synchronized (SpatializerHelper.this) { synchronized (SpatializerHelper.this) {
mSpatLevel = level; mSpatLevel = spatializationLevelToSpatializerInt(level);
} }
// TODO use reported spat level to change state // TODO use reported spat level to change state
// init sensors
if (level == SpatializationLevel.NONE) {
initSensors(/*init*/false);
} else {
postInitSensors(true);
}
} }
}; };
@@ -224,7 +237,7 @@ public class SpatializerHelper {
+ " invalid transform length" + headToStage.length); + " invalid transform length" + headToStage.length);
return; return;
} }
if (DEBUG) { if (DEBUG_MORE) {
// 6 values * (4 digits + 1 dot + 2 brackets) = 42 characters // 6 values * (4 digits + 1 dot + 2 brackets) = 42 characters
StringBuilder t = new StringBuilder(42); StringBuilder t = new StringBuilder(42);
for (float val : headToStage) { for (float val : headToStage) {
@@ -641,36 +654,6 @@ public class SpatializerHelper {
} }
} }
private int headTrackingModeTypeToSpatializerInt(byte mode) {
switch (mode) {
case SpatializerHeadTrackingMode.OTHER:
return Spatializer.HEAD_TRACKING_MODE_OTHER;
case SpatializerHeadTrackingMode.DISABLED:
return Spatializer.HEAD_TRACKING_MODE_DISABLED;
case SpatializerHeadTrackingMode.RELATIVE_WORLD:
return Spatializer.HEAD_TRACKING_MODE_RELATIVE_WORLD;
case SpatializerHeadTrackingMode.RELATIVE_SCREEN:
return Spatializer.HEAD_TRACKING_MODE_RELATIVE_DEVICE;
default:
throw(new IllegalArgumentException("Unexpected head tracking mode:" + mode));
}
}
private byte spatializerIntToHeadTrackingModeType(int sdkMode) {
switch (sdkMode) {
case Spatializer.HEAD_TRACKING_MODE_OTHER:
return SpatializerHeadTrackingMode.OTHER;
case Spatializer.HEAD_TRACKING_MODE_DISABLED:
return SpatializerHeadTrackingMode.DISABLED;
case Spatializer.HEAD_TRACKING_MODE_RELATIVE_WORLD:
return SpatializerHeadTrackingMode.RELATIVE_WORLD;
case Spatializer.HEAD_TRACKING_MODE_RELATIVE_DEVICE:
return SpatializerHeadTrackingMode.RELATIVE_SCREEN;
default:
throw(new IllegalArgumentException("Unexpected head tracking mode:" + sdkMode));
}
}
private boolean checkSpatForHeadTracking(String funcName) { private boolean checkSpatForHeadTracking(String funcName) {
switch (mState) { switch (mState) {
case STATE_UNINITIALIZED: case STATE_UNINITIALIZED:
@@ -792,4 +775,101 @@ public class SpatializerHelper {
Log.e(TAG, "Error in getParameter for key:" + key, e); Log.e(TAG, "Error in getParameter for key:" + key, e);
} }
} }
//------------------------------------------------------
// sensors
private void initSensors(boolean init) {
if (mSensorManager == null) {
mSensorManager = (SensorManager)
mAudioService.mContext.getSystemService(Context.SENSOR_SERVICE);
}
final int headHandle;
final int screenHandle;
if (init) {
if (mSensorManager == null) {
Log.e(TAG, "Null SensorManager, can't init sensors");
return;
}
// TODO replace with dynamic association of sensor for headtracker
Sensor headSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_GAME_ROTATION_VECTOR);
headHandle = headSensor.getHandle();
//Sensor screenSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ROTATION_VECTOR);
//screenHandle = deviceSensor.getHandle();
screenHandle = -1;
} else {
// -1 is disable value
screenHandle = -1;
headHandle = -1;
}
try {
Log.i(TAG, "setScreenSensor:" + screenHandle);
mSpat.setScreenSensor(screenHandle);
} catch (Exception e) {
Log.e(TAG, "Error calling setScreenSensor:" + screenHandle, e);
}
try {
Log.i(TAG, "setHeadSensor:" + headHandle);
mSpat.setHeadSensor(headHandle);
} catch (Exception e) {
Log.e(TAG, "Error calling setHeadSensor:" + headHandle, e);
}
}
private void postInitSensors(boolean init) {
mAudioService.postInitSpatializerHeadTrackingSensors(init);
}
synchronized void onInitSensors(boolean init) {
final int[] modes = getSupportedHeadTrackingModes();
if (modes.length == 0) {
Log.i(TAG, "not initializing sensors, no headtracking supported");
return;
}
initSensors(init);
}
//------------------------------------------------------
// SDK <-> AIDL converters
private static int headTrackingModeTypeToSpatializerInt(byte mode) {
switch (mode) {
case SpatializerHeadTrackingMode.OTHER:
return Spatializer.HEAD_TRACKING_MODE_OTHER;
case SpatializerHeadTrackingMode.DISABLED:
return Spatializer.HEAD_TRACKING_MODE_DISABLED;
case SpatializerHeadTrackingMode.RELATIVE_WORLD:
return Spatializer.HEAD_TRACKING_MODE_RELATIVE_WORLD;
case SpatializerHeadTrackingMode.RELATIVE_SCREEN:
return Spatializer.HEAD_TRACKING_MODE_RELATIVE_DEVICE;
default:
throw(new IllegalArgumentException("Unexpected head tracking mode:" + mode));
}
}
private static byte spatializerIntToHeadTrackingModeType(int sdkMode) {
switch (sdkMode) {
case Spatializer.HEAD_TRACKING_MODE_OTHER:
return SpatializerHeadTrackingMode.OTHER;
case Spatializer.HEAD_TRACKING_MODE_DISABLED:
return SpatializerHeadTrackingMode.DISABLED;
case Spatializer.HEAD_TRACKING_MODE_RELATIVE_WORLD:
return SpatializerHeadTrackingMode.RELATIVE_WORLD;
case Spatializer.HEAD_TRACKING_MODE_RELATIVE_DEVICE:
return SpatializerHeadTrackingMode.RELATIVE_SCREEN;
default:
throw(new IllegalArgumentException("Unexpected head tracking mode:" + sdkMode));
}
}
private static int spatializationLevelToSpatializerInt(byte level) {
switch (level) {
case SpatializationLevel.NONE:
return Spatializer.SPATIALIZER_IMMERSIVE_LEVEL_NONE;
case SpatializationLevel.SPATIALIZER_MULTICHANNEL:
return Spatializer.SPATIALIZER_IMMERSIVE_LEVEL_MULTICHANNEL;
case SpatializationLevel.SPATIALIZER_MCHAN_BED_PLUS_OBJECTS:
return Spatializer.SPATIALIZER_IMMERSIVE_LEVEL_MCHAN_BED_PLUS_OBJECTS;
default:
throw(new IllegalArgumentException("Unexpected spatializer level:" + level));
}
}
} }