/* * Copyright (C) 2016 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 com.android.tv.settings.system; import android.content.Context; import android.hardware.hdmi.HdmiControlManager; import android.icu.text.MessageFormat; import android.media.tv.TvInputInfo; import android.media.tv.TvInputManager; import android.os.Bundle; import android.os.UserHandle; import android.text.TextUtils; import androidx.annotation.Keep; import androidx.preference.Preference; import androidx.preference.PreferenceGroup; import androidx.preference.TwoStatePreference; import com.android.tv.settings.R; import com.android.tv.settings.SettingsPreferenceFragment; import java.util.HashMap; import java.util.Locale; import java.util.Map; import java.util.Set; /** * Fragment to control TV input settings. */ @Keep public class InputsFragment extends SettingsPreferenceFragment { private static final String KEY_CONNECTED_INPUTS = "connected_inputs"; private static final String KEY_STANDBY_INPUTS = "standby_inputs"; private static final String KEY_DISCONNECTED_INPUTS = "disconnected_inputs"; private static final String KEY_HDMI_CONTROL = "hdmi_control"; private static final String KEY_DEVICE_AUTO_OFF = "device_auto_off"; private static final String KEY_TV_AUTO_ON = "tv_auto_on"; private static final String ICU_PLURAL_COUNT = "count"; private PreferenceGroup mConnectedGroup; private PreferenceGroup mStandbyGroup; private PreferenceGroup mDisconnectedGroup; private TwoStatePreference mHdmiControlPref; private TwoStatePreference mDeviceAutoOffPref; private TwoStatePreference mTvAutoOnPref; private TvInputManager mTvInputManager; private HdmiControlManager mHdmiControlManager; private Map mCustomLabels; private Set mHiddenIds; public static InputsFragment newInstance() { return new InputsFragment(); } @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); mTvInputManager = (TvInputManager) getContext().getSystemService(Context.TV_INPUT_SERVICE); mHdmiControlManager = getContext().getSystemService(HdmiControlManager.class); } @Override public void onResume() { super.onResume(); final Context context = getContext(); mCustomLabels = TvInputInfo.TvInputSettings.getCustomLabels(context, UserHandle.USER_SYSTEM); mHiddenIds = TvInputInfo.TvInputSettings.getHiddenTvInputIds(context, UserHandle.USER_SYSTEM); refresh(); } @Override public void onCreatePreferences(Bundle savedInstanceState, String rootKey) { setPreferencesFromResource(R.xml.inputs, null); mConnectedGroup = (PreferenceGroup) findPreference(KEY_CONNECTED_INPUTS); mStandbyGroup = (PreferenceGroup) findPreference(KEY_STANDBY_INPUTS); mDisconnectedGroup = (PreferenceGroup) findPreference(KEY_DISCONNECTED_INPUTS); mHdmiControlPref = (TwoStatePreference) findPreference(KEY_HDMI_CONTROL); mDeviceAutoOffPref = (TwoStatePreference) findPreference(KEY_DEVICE_AUTO_OFF); mTvAutoOnPref = (TwoStatePreference) findPreference(KEY_TV_AUTO_ON); } private void refresh() { mHdmiControlPref.setChecked(mHdmiControlManager.getHdmiCecEnabled() == HdmiControlManager.HDMI_CEC_CONTROL_ENABLED); mDeviceAutoOffPref.setChecked(mHdmiControlManager.getTvSendStandbyOnSleep() == HdmiControlManager.TV_SEND_STANDBY_ON_SLEEP_ENABLED); mTvAutoOnPref.setChecked(mHdmiControlManager.getTvWakeOnOneTouchPlay() == HdmiControlManager.TV_WAKE_ON_ONE_TOUCH_PLAY_ENABLED); for (TvInputInfo info : mTvInputManager.getTvInputList()) { if (info.getType() == TvInputInfo.TYPE_TUNER || !TextUtils.isEmpty(info.getParentId())) { continue; } int state; try { state = mTvInputManager.getInputState(info.getId()); } catch (IllegalArgumentException e) { // Input is gone while iterating. Ignore. continue; } InputPreference inputPref = (InputPreference) findPreference(makeInputPrefKey(info)); if (inputPref == null) { inputPref = new InputPreference(getPreferenceManager().getContext()); } inputPref.refresh(info); switch (state) { case TvInputManager.INPUT_STATE_CONNECTED: mStandbyGroup.removePreference(inputPref); mDisconnectedGroup.removePreference(inputPref); mConnectedGroup.addPreference(inputPref); break; case TvInputManager.INPUT_STATE_CONNECTED_STANDBY: mConnectedGroup.removePreference(inputPref); mDisconnectedGroup.removePreference(inputPref); mStandbyGroup.addPreference(inputPref); break; case TvInputManager.INPUT_STATE_DISCONNECTED: mConnectedGroup.removePreference(inputPref); mStandbyGroup.removePreference(inputPref); mDisconnectedGroup.addPreference(inputPref); break; } } final int connectedCount = mConnectedGroup.getPreferenceCount(); MessageFormat msgFormat = new MessageFormat( getResources().getString(R.string.inputs_header_connected_input), Locale.getDefault()); Map arguments = new HashMap<>(); arguments.put(ICU_PLURAL_COUNT, connectedCount); String songsFound = msgFormat.format(arguments); mConnectedGroup.setTitle(msgFormat.format(arguments)); mConnectedGroup.setVisible(connectedCount > 0); final int standbyCount = mStandbyGroup.getPreferenceCount(); msgFormat = new MessageFormat( getResources().getString(R.string.inputs_header_standby_input), Locale.getDefault()); arguments = new HashMap<>(); arguments.put(ICU_PLURAL_COUNT, standbyCount); mStandbyGroup.setTitle(msgFormat.format(arguments)); mStandbyGroup.setVisible(standbyCount > 0); final int disconnectedCount = mDisconnectedGroup.getPreferenceCount(); msgFormat = new MessageFormat( getResources().getString(R.string.inputs_header_disconnected_input), Locale.getDefault()); arguments = new HashMap<>(); arguments.put(ICU_PLURAL_COUNT, disconnectedCount); mDisconnectedGroup.setTitle(msgFormat.format(arguments)); mDisconnectedGroup.setVisible(disconnectedCount > 0); } @Override public boolean onPreferenceTreeClick(Preference preference) { final String key = preference.getKey(); if (key == null) { return super.onPreferenceTreeClick(preference); } switch (key) { case KEY_HDMI_CONTROL: mHdmiControlManager.setHdmiCecEnabled(mHdmiControlPref.isChecked() ? HdmiControlManager.HDMI_CEC_CONTROL_ENABLED : HdmiControlManager.HDMI_CEC_CONTROL_DISABLED); return true; case KEY_DEVICE_AUTO_OFF: mHdmiControlManager.setTvSendStandbyOnSleep(mDeviceAutoOffPref.isChecked() ? HdmiControlManager.TV_SEND_STANDBY_ON_SLEEP_ENABLED : HdmiControlManager.TV_SEND_STANDBY_ON_SLEEP_DISABLED); return true; case KEY_TV_AUTO_ON: mHdmiControlManager.setTvWakeOnOneTouchPlay(mTvAutoOnPref.isChecked() ? HdmiControlManager.TV_WAKE_ON_ONE_TOUCH_PLAY_ENABLED : HdmiControlManager.TV_WAKE_ON_ONE_TOUCH_PLAY_DISABLED); return true; } return super.onPreferenceTreeClick(preference); } private class InputPreference extends Preference { public InputPreference(Context context) { super(context); } public void refresh(TvInputInfo inputInfo) { setKey(makeInputPrefKey(inputInfo)); setTitle(inputInfo.loadLabel(getContext())); String customLabel; if (mHiddenIds.contains(inputInfo.getId())) { customLabel = getString(R.string.inputs_hide); } else { customLabel = mCustomLabels.get(inputInfo.getId()); if (TextUtils.isEmpty(customLabel)) { customLabel = inputInfo.loadLabel(getContext()).toString(); } } setSummary(customLabel); setFragment(InputOptionsFragment.class.getName()); InputOptionsFragment.prepareArgs(getExtras(), inputInfo); } } public static String makeInputPrefKey(TvInputInfo inputInfo) { return "InputPref:" + inputInfo.getId(); } }