Loading core/java/android/hardware/hdmi/HdmiControlManager.java +16 −0 Original line number Diff line number Diff line Loading @@ -831,6 +831,22 @@ public final class HdmiControlManager { } } /** * For CEC source devices (OTT/STB/Audio system): toggle the power status of the HDMI-connected * display and follow the display's new power status. * For all other devices: no functionality. * * @hide */ @RequiresPermission(android.Manifest.permission.HDMI_CEC) public void toggleAndFollowTvPower() { try { mService.toggleAndFollowTvPower(); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** * Controls whether volume control commands via HDMI CEC are enabled. * Loading core/java/android/hardware/hdmi/HdmiControlServiceWrapper.java +8 −0 Original line number Diff line number Diff line Loading @@ -66,6 +66,11 @@ public final class HdmiControlServiceWrapper { HdmiControlServiceWrapper.this.oneTouchPlay(callback); } @Override public void toggleAndFollowTvPower() { HdmiControlServiceWrapper.this.toggleAndFollowTvPower(); } @Override public void queryDisplayStatus(IHdmiControlCallback callback) { HdmiControlServiceWrapper.this.queryDisplayStatus(callback); Loading Loading @@ -359,6 +364,9 @@ public final class HdmiControlServiceWrapper { /** @hide */ public void oneTouchPlay(IHdmiControlCallback callback) {} /** @hide */ public void toggleAndFollowTvPower() {} /** @hide */ public void queryDisplayStatus(IHdmiControlCallback callback) {} Loading core/java/android/hardware/hdmi/IHdmiControlService.aidl +1 −0 Original line number Diff line number Diff line Loading @@ -42,6 +42,7 @@ interface IHdmiControlService { int[] getSupportedTypes(); HdmiDeviceInfo getActiveSource(); void oneTouchPlay(IHdmiControlCallback callback); void toggleAndFollowTvPower(); void queryDisplayStatus(IHdmiControlCallback callback); void addHdmiControlStatusChangeListener(IHdmiControlStatusChangeListener listener); void removeHdmiControlStatusChangeListener(IHdmiControlStatusChangeListener listener); Loading core/tests/hdmitests/src/android/hardware/hdmi/HdmiAudioSystemClientTest.java +4 −0 Original line number Diff line number Diff line Loading @@ -190,6 +190,10 @@ public class HdmiAudioSystemClientTest { public void oneTouchPlay(final IHdmiControlCallback callback) { } @Override public void toggleAndFollowTvPower() { } @Override public void queryDisplayStatus(final IHdmiControlCallback callback) { } Loading services/core/java/com/android/server/hdmi/HdmiCecLocalDeviceSource.java +46 −4 Original line number Diff line number Diff line Loading @@ -87,10 +87,14 @@ abstract class HdmiCecLocalDeviceSource extends HdmiCecLocalDevice { @ServiceThreadOnly protected void sendStandby(int deviceId) { assertRunOnServiceThread(); // Send standby to TV only for now int targetAddress = Constants.ADDR_TV; mService.sendCecCommand(HdmiCecMessageBuilder.buildStandby(mAddress, targetAddress)); String sendStandbyOnSleep = mService.getHdmiCecConfig().getStringValue( HdmiControlManager.CEC_SETTING_NAME_SEND_STANDBY_ON_SLEEP); if (sendStandbyOnSleep.equals(HdmiControlManager.SEND_STANDBY_ON_SLEEP_BROADCAST)) { mService.sendCecCommand( HdmiCecMessageBuilder.buildStandby(mAddress, Constants.ADDR_BROADCAST)); return; } mService.sendCecCommand(HdmiCecMessageBuilder.buildStandby(mAddress, Constants.ADDR_TV)); } @ServiceThreadOnly Loading @@ -112,6 +116,44 @@ abstract class HdmiCecLocalDeviceSource extends HdmiCecLocalDevice { addAndStartAction(action); } @ServiceThreadOnly void toggleAndFollowTvPower() { assertRunOnServiceThread(); // Wake up Android framework to take over CEC control from the microprocessor. mService.wakeUp(); mService.queryDisplayStatus(new IHdmiControlCallback.Stub() { @Override public void onComplete(int status) { if (status == HdmiControlManager.POWER_STATUS_UNKNOWN) { Slog.i(TAG, "TV power toggle: TV power status unknown"); sendUserControlPressedAndReleased(Constants.ADDR_TV, HdmiCecKeycode.CEC_KEYCODE_POWER_TOGGLE_FUNCTION); // Source device remains awake. } else if (status == HdmiControlManager.POWER_STATUS_ON || status == HdmiControlManager.POWER_STATUS_TRANSIENT_TO_ON) { Slog.i(TAG, "TV power toggle: turning off TV"); sendStandby(0 /*unused */); // Source device goes to standby, to follow the toggled TV power state. mService.standby(); } else if (status == HdmiControlManager.POWER_STATUS_STANDBY || status == HdmiControlManager.POWER_STATUS_TRANSIENT_TO_STANDBY) { Slog.i(TAG, "TV power toggle: turning on TV"); oneTouchPlay(new IHdmiControlCallback.Stub() { @Override public void onComplete(int result) { if (result != HdmiControlManager.RESULT_SUCCESS) { Slog.w(TAG, "Failed to complete One Touch Play. result=" + result); sendUserControlPressedAndReleased(Constants.ADDR_TV, HdmiCecKeycode.CEC_KEYCODE_POWER_TOGGLE_FUNCTION); } } }); // Source device remains awake, to follow the toggled TV power state. } } }); } @ServiceThreadOnly protected void onActiveSourceLost() { // Nothing to do. Loading Loading
core/java/android/hardware/hdmi/HdmiControlManager.java +16 −0 Original line number Diff line number Diff line Loading @@ -831,6 +831,22 @@ public final class HdmiControlManager { } } /** * For CEC source devices (OTT/STB/Audio system): toggle the power status of the HDMI-connected * display and follow the display's new power status. * For all other devices: no functionality. * * @hide */ @RequiresPermission(android.Manifest.permission.HDMI_CEC) public void toggleAndFollowTvPower() { try { mService.toggleAndFollowTvPower(); } catch (RemoteException e) { throw e.rethrowFromSystemServer(); } } /** * Controls whether volume control commands via HDMI CEC are enabled. * Loading
core/java/android/hardware/hdmi/HdmiControlServiceWrapper.java +8 −0 Original line number Diff line number Diff line Loading @@ -66,6 +66,11 @@ public final class HdmiControlServiceWrapper { HdmiControlServiceWrapper.this.oneTouchPlay(callback); } @Override public void toggleAndFollowTvPower() { HdmiControlServiceWrapper.this.toggleAndFollowTvPower(); } @Override public void queryDisplayStatus(IHdmiControlCallback callback) { HdmiControlServiceWrapper.this.queryDisplayStatus(callback); Loading Loading @@ -359,6 +364,9 @@ public final class HdmiControlServiceWrapper { /** @hide */ public void oneTouchPlay(IHdmiControlCallback callback) {} /** @hide */ public void toggleAndFollowTvPower() {} /** @hide */ public void queryDisplayStatus(IHdmiControlCallback callback) {} Loading
core/java/android/hardware/hdmi/IHdmiControlService.aidl +1 −0 Original line number Diff line number Diff line Loading @@ -42,6 +42,7 @@ interface IHdmiControlService { int[] getSupportedTypes(); HdmiDeviceInfo getActiveSource(); void oneTouchPlay(IHdmiControlCallback callback); void toggleAndFollowTvPower(); void queryDisplayStatus(IHdmiControlCallback callback); void addHdmiControlStatusChangeListener(IHdmiControlStatusChangeListener listener); void removeHdmiControlStatusChangeListener(IHdmiControlStatusChangeListener listener); Loading
core/tests/hdmitests/src/android/hardware/hdmi/HdmiAudioSystemClientTest.java +4 −0 Original line number Diff line number Diff line Loading @@ -190,6 +190,10 @@ public class HdmiAudioSystemClientTest { public void oneTouchPlay(final IHdmiControlCallback callback) { } @Override public void toggleAndFollowTvPower() { } @Override public void queryDisplayStatus(final IHdmiControlCallback callback) { } Loading
services/core/java/com/android/server/hdmi/HdmiCecLocalDeviceSource.java +46 −4 Original line number Diff line number Diff line Loading @@ -87,10 +87,14 @@ abstract class HdmiCecLocalDeviceSource extends HdmiCecLocalDevice { @ServiceThreadOnly protected void sendStandby(int deviceId) { assertRunOnServiceThread(); // Send standby to TV only for now int targetAddress = Constants.ADDR_TV; mService.sendCecCommand(HdmiCecMessageBuilder.buildStandby(mAddress, targetAddress)); String sendStandbyOnSleep = mService.getHdmiCecConfig().getStringValue( HdmiControlManager.CEC_SETTING_NAME_SEND_STANDBY_ON_SLEEP); if (sendStandbyOnSleep.equals(HdmiControlManager.SEND_STANDBY_ON_SLEEP_BROADCAST)) { mService.sendCecCommand( HdmiCecMessageBuilder.buildStandby(mAddress, Constants.ADDR_BROADCAST)); return; } mService.sendCecCommand(HdmiCecMessageBuilder.buildStandby(mAddress, Constants.ADDR_TV)); } @ServiceThreadOnly Loading @@ -112,6 +116,44 @@ abstract class HdmiCecLocalDeviceSource extends HdmiCecLocalDevice { addAndStartAction(action); } @ServiceThreadOnly void toggleAndFollowTvPower() { assertRunOnServiceThread(); // Wake up Android framework to take over CEC control from the microprocessor. mService.wakeUp(); mService.queryDisplayStatus(new IHdmiControlCallback.Stub() { @Override public void onComplete(int status) { if (status == HdmiControlManager.POWER_STATUS_UNKNOWN) { Slog.i(TAG, "TV power toggle: TV power status unknown"); sendUserControlPressedAndReleased(Constants.ADDR_TV, HdmiCecKeycode.CEC_KEYCODE_POWER_TOGGLE_FUNCTION); // Source device remains awake. } else if (status == HdmiControlManager.POWER_STATUS_ON || status == HdmiControlManager.POWER_STATUS_TRANSIENT_TO_ON) { Slog.i(TAG, "TV power toggle: turning off TV"); sendStandby(0 /*unused */); // Source device goes to standby, to follow the toggled TV power state. mService.standby(); } else if (status == HdmiControlManager.POWER_STATUS_STANDBY || status == HdmiControlManager.POWER_STATUS_TRANSIENT_TO_STANDBY) { Slog.i(TAG, "TV power toggle: turning on TV"); oneTouchPlay(new IHdmiControlCallback.Stub() { @Override public void onComplete(int result) { if (result != HdmiControlManager.RESULT_SUCCESS) { Slog.w(TAG, "Failed to complete One Touch Play. result=" + result); sendUserControlPressedAndReleased(Constants.ADDR_TV, HdmiCecKeycode.CEC_KEYCODE_POWER_TOGGLE_FUNCTION); } } }); // Source device remains awake, to follow the toggled TV power state. } } }); } @ServiceThreadOnly protected void onActiveSourceLost() { // Nothing to do. Loading