StkMenuActivity.java revision 3e34a8ad0ff494f6e5abc618acecdcc075d0be83
1/* 2 * Copyright (C) 2007 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 17package com.android.stk; 18 19import android.app.ListActivity; 20import android.content.Context; 21import android.content.Intent; 22import android.os.Bundle; 23import android.os.Handler; 24import android.os.Message; 25import android.view.ContextMenu; 26import android.view.ContextMenu.ContextMenuInfo; 27import android.view.KeyEvent; 28import android.view.MenuItem; 29import android.view.View; 30import android.view.Window; 31import android.widget.AdapterView; 32import android.widget.ImageView; 33import android.widget.ListView; 34import android.widget.ProgressBar; 35import android.widget.TextView; 36 37import com.android.internal.telephony.cat.Item; 38import com.android.internal.telephony.cat.Menu; 39import com.android.internal.telephony.cat.CatLog; 40 41/** 42 * ListActivity used for displaying STK menus. These can be SET UP MENU and 43 * SELECT ITEM menus. This activity is started multiple times with different 44 * menu content. 45 * 46 */ 47public class StkMenuActivity extends ListActivity implements View.OnCreateContextMenuListener { 48 private Context mContext; 49 private Menu mStkMenu = null; 50 private int mState = STATE_MAIN; 51 private boolean mAcceptUsersInput = true; 52 53 private TextView mTitleTextView = null; 54 private ImageView mTitleIconView = null; 55 private ProgressBar mProgressView = null; 56 57 StkAppService appService = StkAppService.getInstance(); 58 59 // Internal state values 60 static final int STATE_MAIN = 1; 61 static final int STATE_SECONDARY = 2; 62 63 // message id for time out 64 private static final int MSG_ID_TIMEOUT = 1; 65 private static final int CONTEXT_MENU_HELP = 0; 66 67 Handler mTimeoutHandler = new Handler() { 68 @Override 69 public void handleMessage(Message msg) { 70 switch(msg.what) { 71 case MSG_ID_TIMEOUT: 72 mAcceptUsersInput = false; 73 sendResponse(StkAppService.RES_ID_TIMEOUT); 74 break; 75 } 76 } 77 }; 78 79 @Override 80 public void onCreate(Bundle icicle) { 81 super.onCreate(icicle); 82 83 CatLog.d(this, "onCreate"); 84 // Remove the default title, customized one is used. 85 requestWindowFeature(Window.FEATURE_NO_TITLE); 86 // Set the layout for this activity. 87 setContentView(R.layout.stk_menu_list); 88 89 mTitleTextView = (TextView) findViewById(R.id.title_text); 90 mTitleIconView = (ImageView) findViewById(R.id.title_icon); 91 mProgressView = (ProgressBar) findViewById(R.id.progress_bar); 92 mContext = getBaseContext(); 93 94 initFromIntent(getIntent()); 95 mAcceptUsersInput = true; 96 97 getListView().setOnCreateContextMenuListener(this); 98 } 99 100 @Override 101 protected void onNewIntent(Intent intent) { 102 super.onNewIntent(intent); 103 104 CatLog.d(this, "onNewIntent"); 105 initFromIntent(intent); 106 mAcceptUsersInput = true; 107 } 108 109 @Override 110 protected void onListItemClick(ListView l, View v, int position, long id) { 111 super.onListItemClick(l, v, position, id); 112 113 if (!mAcceptUsersInput) { 114 return; 115 } 116 117 Item item = getSelectedItem(position); 118 if (item == null) { 119 return; 120 } 121 sendResponse(StkAppService.RES_ID_MENU_SELECTION, item.id, false); 122 mAcceptUsersInput = false; 123 mProgressView.setVisibility(View.VISIBLE); 124 mProgressView.setIndeterminate(true); 125 } 126 127 @Override 128 public boolean onKeyDown(int keyCode, KeyEvent event) { 129 130 if (!mAcceptUsersInput) { 131 return true; 132 } 133 134 switch (keyCode) { 135 case KeyEvent.KEYCODE_BACK: 136 switch (mState) { 137 case STATE_SECONDARY: 138 cancelTimeOut(); 139 mAcceptUsersInput = false; 140 sendResponse(StkAppService.RES_ID_BACKWARD); 141 return true; 142 case STATE_MAIN: 143 break; 144 } 145 break; 146 } 147 return super.onKeyDown(keyCode, event); 148 } 149 150 @Override 151 public void onResume() { 152 super.onResume(); 153 154 appService.indicateMenuVisibility(true); 155 mStkMenu = appService.getMenu(); 156 if (mStkMenu == null) { 157 finish(); 158 return; 159 } 160 displayMenu(); 161 startTimeOut(); 162 // whenever this activity is resumed after a sub activity was invoked 163 // (Browser, In call screen) switch back to main state and enable 164 // user's input; 165 if (!mAcceptUsersInput) { 166 mState = STATE_MAIN; 167 mAcceptUsersInput = true; 168 } 169 // make sure the progress bar is not shown. 170 mProgressView.setIndeterminate(false); 171 mProgressView.setVisibility(View.GONE); 172 } 173 174 @Override 175 public void onPause() { 176 super.onPause(); 177 178 appService.indicateMenuVisibility(false); 179 cancelTimeOut(); 180 } 181 182 @Override 183 public void onDestroy() { 184 getListView().setOnCreateContextMenuListener(null); 185 super.onDestroy(); 186 187 CatLog.d(this, "onDestroy"); 188 } 189 190 @Override 191 public boolean onCreateOptionsMenu(android.view.Menu menu) { 192 super.onCreateOptionsMenu(menu); 193 menu.add(0, StkApp.MENU_ID_END_SESSION, 1, R.string.menu_end_session); 194 menu.add(0, StkApp.MENU_ID_HELP, 2, R.string.help); 195 return true; 196 } 197 198 @Override 199 public boolean onPrepareOptionsMenu(android.view.Menu menu) { 200 super.onPrepareOptionsMenu(menu); 201 boolean helpVisible = false; 202 boolean mainVisible = false; 203 204 if (mState == STATE_SECONDARY) { 205 mainVisible = true; 206 } 207 if (mStkMenu != null) { 208 helpVisible = mStkMenu.helpAvailable; 209 } 210 211 menu.findItem(StkApp.MENU_ID_END_SESSION).setVisible(mainVisible); 212 menu.findItem(StkApp.MENU_ID_HELP).setVisible(helpVisible); 213 214 return true; 215 } 216 217 @Override 218 public boolean onOptionsItemSelected(MenuItem item) { 219 if (!mAcceptUsersInput) { 220 return true; 221 } 222 switch (item.getItemId()) { 223 case StkApp.MENU_ID_END_SESSION: 224 cancelTimeOut(); 225 mAcceptUsersInput = false; 226 // send session end response. 227 sendResponse(StkAppService.RES_ID_END_SESSION); 228 return true; 229 case StkApp.MENU_ID_HELP: 230 cancelTimeOut(); 231 mAcceptUsersInput = false; 232 int position = getSelectedItemPosition(); 233 Item stkItem = getSelectedItem(position); 234 if (stkItem == null) { 235 break; 236 } 237 // send help needed response. 238 sendResponse(StkAppService.RES_ID_MENU_SELECTION, stkItem.id, true); 239 return true; 240 } 241 return super.onOptionsItemSelected(item); 242 } 243 244 @Override 245 public void onCreateContextMenu(ContextMenu menu, View v, 246 ContextMenuInfo menuInfo) { 247 CatLog.d(this, "onCreateContextMenu"); 248 boolean helpVisible = false; 249 if (mStkMenu != null) { 250 helpVisible = mStkMenu.helpAvailable; 251 } 252 if (helpVisible) { 253 CatLog.d(this, "add menu"); 254 menu.add(0, CONTEXT_MENU_HELP, 0, R.string.help); 255 } 256 } 257 258 @Override 259 public boolean onContextItemSelected(MenuItem item) { 260 AdapterView.AdapterContextMenuInfo info; 261 try { 262 info = (AdapterView.AdapterContextMenuInfo) item.getMenuInfo(); 263 } catch (ClassCastException e) { 264 return false; 265 } 266 switch (item.getItemId()) { 267 case CONTEXT_MENU_HELP: 268 cancelTimeOut(); 269 mAcceptUsersInput = false; 270 int position = info.position; 271 CatLog.d(this, "Position:" + position); 272 Item stkItem = getSelectedItem(position); 273 if (stkItem != null) { 274 CatLog.d(this, "item id:" + stkItem.id); 275 sendResponse(StkAppService.RES_ID_MENU_SELECTION, stkItem.id, true); 276 } 277 return true; 278 279 default: 280 return super.onContextItemSelected(item); 281 } 282 } 283 284 @Override 285 protected void onSaveInstanceState(Bundle outState) { 286 outState.putInt("STATE", mState); 287 outState.putParcelable("MENU", mStkMenu); 288 } 289 290 @Override 291 protected void onRestoreInstanceState(Bundle savedInstanceState) { 292 mState = savedInstanceState.getInt("STATE"); 293 mStkMenu = savedInstanceState.getParcelable("MENU"); 294 } 295 296 private void cancelTimeOut() { 297 mTimeoutHandler.removeMessages(MSG_ID_TIMEOUT); 298 } 299 300 private void startTimeOut() { 301 if (mState == STATE_SECONDARY) { 302 // Reset timeout. 303 cancelTimeOut(); 304 mTimeoutHandler.sendMessageDelayed(mTimeoutHandler 305 .obtainMessage(MSG_ID_TIMEOUT), StkApp.UI_TIMEOUT); 306 } 307 } 308 309 // Bind list adapter to the items list. 310 private void displayMenu() { 311 312 if (mStkMenu != null) { 313 String title = mStkMenu.title == null ? getString(R.string.app_name) : mStkMenu.title; 314 // Display title & title icon 315 if (mStkMenu.titleIcon != null) { 316 mTitleIconView.setImageBitmap(mStkMenu.titleIcon); 317 mTitleIconView.setVisibility(View.VISIBLE); 318 mTitleTextView.setVisibility(View.INVISIBLE); 319 if (!mStkMenu.titleIconSelfExplanatory) { 320 mTitleTextView.setText(title); 321 mTitleTextView.setVisibility(View.VISIBLE); 322 } 323 } else { 324 mTitleIconView.setVisibility(View.GONE); 325 mTitleTextView.setVisibility(View.VISIBLE); 326 mTitleTextView.setText(title); 327 } 328 // create an array adapter for the menu list 329 StkMenuAdapter adapter = new StkMenuAdapter(this, 330 mStkMenu.items, mStkMenu.itemsIconSelfExplanatory); 331 // Bind menu list to the new adapter. 332 setListAdapter(adapter); 333 // Set default item 334 setSelection(mStkMenu.defaultItem); 335 } 336 } 337 338 private void initFromIntent(Intent intent) { 339 340 if (intent != null) { 341 mState = intent.getIntExtra("STATE", STATE_MAIN); 342 } else { 343 finish(); 344 } 345 } 346 347 private Item getSelectedItem(int position) { 348 Item item = null; 349 if (mStkMenu != null) { 350 try { 351 item = mStkMenu.items.get(position); 352 } catch (IndexOutOfBoundsException e) { 353 if (StkApp.DBG) { 354 CatLog.d(this, "Invalid menu"); 355 } 356 } catch (NullPointerException e) { 357 if (StkApp.DBG) { 358 CatLog.d(this, "Invalid menu"); 359 } 360 } 361 } 362 return item; 363 } 364 365 private void sendResponse(int resId) { 366 sendResponse(resId, 0, false); 367 } 368 369 private void sendResponse(int resId, int itemId, boolean help) { 370 Bundle args = new Bundle(); 371 args.putInt(StkAppService.OPCODE, StkAppService.OP_RESPONSE); 372 args.putInt(StkAppService.RES_ID, resId); 373 args.putInt(StkAppService.MENU_SELECTION, itemId); 374 args.putBoolean(StkAppService.HELP, help); 375 mContext.startService(new Intent(mContext, StkAppService.class) 376 .putExtras(args)); 377 } 378} 379