1 /* 2 * Copyright (C) 2014 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 package com.android.cts.verifier.tv; 18 19 import android.app.SearchableInfo; 20 import android.content.Context; 21 import android.content.Intent; 22 import android.media.tv.TvContract; 23 import android.media.tv.TvInputManager; 24 import android.os.AsyncTask; 25 import android.view.View; 26 27 import com.android.cts.verifier.R; 28 29 /** 30 * Tests for verifying TV app behavior for third-party TV input apps. 31 */ 32 public class TvInputDiscoveryTestActivity extends TvAppVerifierActivity 33 implements View.OnClickListener { 34 private static final String TAG = "TvInputDiscoveryTestActivity"; 35 36 private static final Intent TV_APP_INTENT = new Intent(Intent.ACTION_VIEW, 37 TvContract.Channels.CONTENT_URI); 38 private static final Intent EPG_INTENT = new Intent(Intent.ACTION_VIEW, 39 TvContract.Programs.CONTENT_URI); 40 private static final Intent TV_TRIGGER_SETUP_INTENT = new Intent( 41 TvInputManager.ACTION_SETUP_INPUTS); 42 43 private static final long TIMEOUT_MS = 5l * 60l * 1000l; // 5 mins. 44 45 private View mGoToSetupItem; 46 private View mVerifySetupItem; 47 private View mTuneToChannelItem; 48 private View mVerifyTuneItem; 49 private View mVerifyOverlayViewItem; 50 private View mVerifyGlobalSearchItem; 51 private View mVerifyOverlayViewSizeChanged; 52 private View mGoToEpgItem; 53 private View mVerifyEpgItem; 54 private View mTriggerSetupItem; 55 private View mVerifyTriggerSetupItem; 56 private View mSupportThirdPartyInputYesItem; 57 private View mSupportThirdPartyInputNoItem; 58 private boolean mTuneVerified; 59 private boolean mOverlayViewVerified; 60 private boolean mGlobalSearchVerified; 61 private boolean mOverlayViewSizeChangedVerified; 62 63 @Override onClick(View v)64 public void onClick(View v) { 65 final View postTarget = getPostTarget(); 66 67 if (containsButton(mSupportThirdPartyInputYesItem, v)) { 68 setPassState(mSupportThirdPartyInputYesItem, true); 69 setButtonEnabled(mSupportThirdPartyInputNoItem, false); 70 setButtonEnabled(mGoToSetupItem, true); 71 return; 72 } else if (containsButton(mSupportThirdPartyInputNoItem, v)){ 73 setPassState(mSupportThirdPartyInputYesItem, true); 74 setButtonEnabled(mSupportThirdPartyInputNoItem, false); 75 getPassButton().setEnabled(true); 76 return; 77 } else if (containsButton(mGoToSetupItem, v)) { 78 final Runnable failCallback = new Runnable() { 79 @Override 80 public void run() { 81 setPassState(mVerifySetupItem, false); 82 } 83 }; 84 postTarget.postDelayed(failCallback, TIMEOUT_MS); 85 MockTvInputSetupActivity.expectLaunch(postTarget, new Runnable() { 86 @Override 87 public void run() { 88 postTarget.removeCallbacks(failCallback); 89 setPassState(mGoToSetupItem, true); 90 setPassState(mVerifySetupItem, true); 91 setButtonEnabled(mTuneToChannelItem, true); 92 } 93 }); 94 startActivity(TV_APP_INTENT); 95 } else if (containsButton(mTuneToChannelItem, v)) { 96 final Runnable failCallback = new Runnable() { 97 @Override 98 public void run() { 99 setPassState(mVerifyTuneItem, false); 100 } 101 }; 102 postTarget.postDelayed(failCallback, TIMEOUT_MS); 103 MockTvInputService.expectTune(postTarget, new Runnable() { 104 @Override 105 public void run() { 106 setPassState(mTuneToChannelItem, true); 107 setPassState(mVerifyTuneItem, true); 108 109 mTuneVerified = true; 110 goToNextState(postTarget, failCallback); 111 } 112 }); 113 MockTvInputService.expectedVideoAspectRatio(postTarget, new Runnable() { 114 @Override 115 public void run() { 116 postTarget.removeCallbacks(failCallback); 117 setPassState(mVerifyOverlayViewSizeChanged, true); 118 119 mOverlayViewSizeChangedVerified = true; 120 goToNextState(postTarget, failCallback); 121 } 122 }); 123 MockTvInputService.expectOverlayView(postTarget, new Runnable() { 124 @Override 125 public void run() { 126 postTarget.removeCallbacks(failCallback); 127 setPassState(mVerifyOverlayViewItem, true); 128 129 mOverlayViewVerified = true; 130 goToNextState(postTarget, failCallback); 131 } 132 }); 133 verifyGlobalSearch(postTarget, failCallback); 134 startActivity(TV_APP_INTENT); 135 } else if (containsButton(mGoToEpgItem, v)) { 136 startActivity(EPG_INTENT); 137 setPassState(mGoToEpgItem, true); 138 setButtonEnabled(mVerifyEpgItem, true); 139 } else if (containsButton(mVerifyEpgItem, v)) { 140 setPassState(mVerifyEpgItem, true); 141 setButtonEnabled(mTriggerSetupItem, true); 142 } else if (containsButton(mTriggerSetupItem, v)) { 143 startActivity(TV_TRIGGER_SETUP_INTENT); 144 setPassState(mTriggerSetupItem, true); 145 setButtonEnabled(mVerifyTriggerSetupItem, true); 146 } else if (containsButton(mVerifyTriggerSetupItem, v)) { 147 setPassState(mVerifyTriggerSetupItem, true); 148 getPassButton().setEnabled(true); 149 } 150 } 151 152 @Override createTestItems()153 protected void createTestItems() { 154 mSupportThirdPartyInputYesItem = createUserItem( 155 R.string.tv_input_discover_test_third_party_tif_input_support, 156 R.string.tv_yes, this); 157 setButtonEnabled(mSupportThirdPartyInputYesItem, true); 158 mSupportThirdPartyInputNoItem = createButtonItem(R.string.tv_no, this); 159 setButtonEnabled(mSupportThirdPartyInputNoItem, true); 160 mGoToSetupItem = createUserItem(R.string.tv_input_discover_test_go_to_setup, 161 R.string.tv_launch_tv_app, this); 162 mVerifySetupItem = createAutoItem(R.string.tv_input_discover_test_verify_setup); 163 mTuneToChannelItem = createUserItem(R.string.tv_input_discover_test_tune_to_channel, 164 R.string.tv_launch_tv_app, this); 165 mVerifyTuneItem = createAutoItem(R.string.tv_input_discover_test_verify_tune); 166 mVerifyOverlayViewItem = createAutoItem( 167 R.string.tv_input_discover_test_verify_overlay_view); 168 mVerifyOverlayViewSizeChanged = createAutoItem( 169 R.string.tv_input_discover_test_verify_size_changed); 170 mVerifyGlobalSearchItem = createAutoItem( 171 R.string.tv_input_discover_test_verify_global_search); 172 mGoToEpgItem = createUserItem(R.string.tv_input_discover_test_go_to_epg, 173 R.string.tv_launch_epg, this); 174 mVerifyEpgItem = createUserItem(R.string.tv_input_discover_test_verify_epg, 175 R.string.tv_yes, this); 176 mTriggerSetupItem = createUserItem(R.string.tv_input_discover_test_trigger_setup, 177 R.string.tv_launch_setup, this); 178 mVerifyTriggerSetupItem = createUserItem( 179 R.string.tv_input_discover_test_verify_trigger_setup, R.string.tv_yes, this); 180 } 181 182 @Override setInfoResources()183 protected void setInfoResources() { 184 setInfoResources(R.string.tv_input_discover_test, 185 R.string.tv_input_discover_test_info, -1); 186 } 187 goToNextState(View postTarget, Runnable failCallback)188 private void goToNextState(View postTarget, Runnable failCallback) { 189 if (mTuneVerified && mOverlayViewVerified 190 && mGlobalSearchVerified && mOverlayViewSizeChangedVerified) { 191 postTarget.removeCallbacks(failCallback); 192 setButtonEnabled(mGoToEpgItem, true); 193 } 194 } 195 verifyGlobalSearch(final View postTarget, final Runnable failCallback)196 private void verifyGlobalSearch(final View postTarget, final Runnable failCallback) { 197 new AsyncTask<Void, Void, Boolean>() { 198 @Override 199 protected Boolean doInBackground(Void... params) { 200 Context context = TvInputDiscoveryTestActivity.this; 201 for (SearchableInfo info : SearchUtil.getSearchableInfos(context)) { 202 if (SearchUtil.verifySearchResult(context, info, 203 MockTvInputSetupActivity.CHANNEL_NAME, 204 MockTvInputSetupActivity.PROGRAM_TITLE) 205 && SearchUtil.verifySearchResult(context, info, 206 MockTvInputSetupActivity.PROGRAM_TITLE, 207 MockTvInputSetupActivity.PROGRAM_TITLE)) { 208 return true; 209 } 210 } 211 return false; 212 } 213 214 @Override 215 protected void onPostExecute(Boolean result) { 216 super.onPostExecute(result); 217 setPassState(mVerifyGlobalSearchItem, result); 218 mGlobalSearchVerified = result; 219 goToNextState(postTarget, failCallback); 220 } 221 }.execute(); 222 } 223 } 224