164 lines
5.8 KiB
Java
164 lines
5.8 KiB
Java
/*
|
|
* Copyright (C) 2018 The Android Open Source Project
|
|
*
|
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
|
* you may not use this file except in compliance with the License.
|
|
* You may obtain a copy of the License at
|
|
*
|
|
* http://www.apache.org/licenses/LICENSE-2.0
|
|
*
|
|
* Unless required by applicable law or agreed to in writing, software
|
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
* See the License for the specific language governing permissions and
|
|
* limitations under the License.
|
|
*/
|
|
package android.hardware.hdmi;
|
|
|
|
import android.annotation.NonNull;
|
|
import android.annotation.Nullable;
|
|
import android.os.Handler;
|
|
import android.os.Looper;
|
|
import android.os.RemoteException;
|
|
import android.util.Log;
|
|
|
|
import com.android.internal.annotations.VisibleForTesting;
|
|
import com.android.internal.annotations.VisibleForTesting.Visibility;
|
|
|
|
/**
|
|
* HdmiAudioSystemClient represents HDMI-CEC logical device of type Audio System in the Android
|
|
* system which acts as an audio system device such as sound bar.
|
|
*
|
|
* <p>HdmiAudioSystemClient provides methods that control, get information from TV/Display device
|
|
* connected through HDMI bus.
|
|
*
|
|
* @hide
|
|
*/
|
|
public final class HdmiAudioSystemClient extends HdmiClient {
|
|
private static final String TAG = "HdmiAudioSystemClient";
|
|
|
|
private static final int REPORT_AUDIO_STATUS_INTERVAL_MS = 500;
|
|
|
|
private final Handler mHandler;
|
|
private boolean mCanSendAudioStatus = true;
|
|
private boolean mPendingReportAudioStatus;
|
|
|
|
private int mLastVolume;
|
|
private int mLastMaxVolume;
|
|
private boolean mLastIsMute;
|
|
|
|
@VisibleForTesting(visibility = Visibility.PACKAGE)
|
|
public HdmiAudioSystemClient(IHdmiControlService service) {
|
|
this(service, null);
|
|
}
|
|
|
|
@VisibleForTesting(visibility = Visibility.PACKAGE)
|
|
public HdmiAudioSystemClient(IHdmiControlService service, @Nullable Handler handler) {
|
|
super(service);
|
|
mHandler = handler == null ? new Handler(Looper.getMainLooper()) : handler;
|
|
}
|
|
|
|
/**
|
|
* Callback interface used to get the set System Audio Mode result.
|
|
*
|
|
* @hide
|
|
*/
|
|
public interface SetSystemAudioModeCallback {
|
|
/**
|
|
* Called when the input was changed.
|
|
*
|
|
* @param result the result of the set System Audio Mode
|
|
*/
|
|
void onComplete(int result);
|
|
}
|
|
|
|
/** @hide */
|
|
@Override
|
|
public int getDeviceType() {
|
|
return HdmiDeviceInfo.DEVICE_AUDIO_SYSTEM;
|
|
}
|
|
|
|
/**
|
|
* Sends a Report Audio Status HDMI CEC command to TV devices when necessary.
|
|
*
|
|
* According to HDMI CEC specification, an audio system can report its audio status when System
|
|
* Audio Mode is on, so that the TV can display the audio status of external amplifier.
|
|
*
|
|
* @hide
|
|
*/
|
|
public void sendReportAudioStatusCecCommand(boolean isMuteAdjust, int volume, int maxVolume,
|
|
boolean isMute) {
|
|
if (isMuteAdjust) {
|
|
// always report audio status when it's muted/unmuted
|
|
try {
|
|
mService.reportAudioStatus(getDeviceType(), volume, maxVolume, isMute);
|
|
} catch (RemoteException e) {
|
|
// do nothing. Reporting audio status is optional.
|
|
}
|
|
return;
|
|
}
|
|
|
|
mLastVolume = volume;
|
|
mLastMaxVolume = maxVolume;
|
|
mLastIsMute = isMute;
|
|
if (mCanSendAudioStatus) {
|
|
try {
|
|
mService.reportAudioStatus(getDeviceType(), volume, maxVolume, isMute);
|
|
mCanSendAudioStatus = false;
|
|
mHandler.postDelayed(new Runnable() {
|
|
@Override
|
|
public void run() {
|
|
if (mPendingReportAudioStatus) {
|
|
// report audio status if there is any pending message
|
|
try {
|
|
mService.reportAudioStatus(getDeviceType(), mLastVolume,
|
|
mLastMaxVolume, mLastIsMute);
|
|
mHandler.postDelayed(this, REPORT_AUDIO_STATUS_INTERVAL_MS);
|
|
} catch (RemoteException e) {
|
|
mCanSendAudioStatus = true;
|
|
} finally {
|
|
mPendingReportAudioStatus = false;
|
|
}
|
|
} else {
|
|
mCanSendAudioStatus = true;
|
|
}
|
|
}
|
|
}, REPORT_AUDIO_STATUS_INTERVAL_MS);
|
|
} catch (RemoteException e) {
|
|
// do nothing. Reporting audio status is optional.
|
|
}
|
|
} else {
|
|
// if audio status cannot be sent, send it latter
|
|
mPendingReportAudioStatus = true;
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Set System Audio Mode on/off with audio system device.
|
|
*
|
|
* @param state true to set System Audio Mode on. False to set off.
|
|
* @param callback callback offer the setting result.
|
|
*
|
|
* @hide
|
|
*/
|
|
public void setSystemAudioMode(boolean state, @NonNull SetSystemAudioModeCallback callback) {
|
|
// TODO(b/217509829): implement this when needed.
|
|
}
|
|
|
|
/**
|
|
* When device is switching to an audio only source, this method is called to broadcast
|
|
* a setSystemAudioMode on message to the HDMI CEC system without querying Active Source or
|
|
* TV supporting System Audio Control or not. This is to get volume control passthrough
|
|
* from STB even if TV does not support it.
|
|
*
|
|
* @hide
|
|
*/
|
|
public void setSystemAudioModeOnForAudioOnlySource() {
|
|
try {
|
|
mService.setSystemAudioModeOnForAudioOnlySource();
|
|
} catch (RemoteException e) {
|
|
Log.d(TAG, "Failed to set System Audio Mode on for Audio Only source");
|
|
}
|
|
}
|
|
}
|