Home | History | Annotate | Download | only in menu
      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 
     17 package android.view.menu;
     18 
     19 import android.util.ListScenario;
     20 import com.android.internal.view.menu.MenuBuilder;
     21 import com.android.internal.view.menu.MenuBuilder.MenuAdapter;
     22 
     23 import android.app.Activity;
     24 import android.os.Bundle;
     25 import android.util.SparseArray;
     26 import android.view.Menu;
     27 import android.view.MenuItem;
     28 import android.view.View;
     29 
     30 /**
     31  * Utility base class for creating various Menu scenarios. Configurable by the
     32  * number of menu items. Used @link {@link ListScenario} as a reference.
     33  */
     34 public class MenuScenario extends Activity implements MenuItem.OnMenuItemClickListener {
     35     private Params mParams = new Params();
     36     private Menu mMenu;
     37     private MenuItem[] mItems;
     38     private boolean[] mWasItemClicked;
     39     private MenuAdapter[] mMenuAdapters = new MenuAdapter[MenuBuilder.NUM_TYPES];
     40 
     41     @Override
     42     protected void onCreate(Bundle icicle) {
     43         super.onCreate(icicle);
     44 
     45         dispatchInitParams();
     46     }
     47 
     48     private void dispatchInitParams() {
     49         onInitParams(mParams);
     50         onParamsChanged();
     51     }
     52 
     53     public void setParams(Params params) {
     54         mParams = params;
     55         onParamsChanged();
     56     }
     57 
     58     public void onParamsChanged() {
     59         mItems = new MenuItem[mParams.numItems];
     60         mWasItemClicked = new boolean[mParams.numItems];
     61     }
     62 
     63     @Override
     64     public boolean onCreateOptionsMenu(Menu menu) {
     65         // Safe to hold on to
     66         mMenu = menu;
     67 
     68         if (!mParams.shouldShowMenu) return false;
     69 
     70         MenuItem item;
     71         for (int i = 0; i < mParams.numItems; i++) {
     72             if ((item = onAddMenuItem(menu, i)) == null) {
     73                 // Add a default item for this position if the subclasses
     74                 // haven't
     75                 CharSequence givenTitle = mParams.itemTitles.get(i);
     76                 item = menu.add(0, 0, 0, (givenTitle != null) ? givenTitle : ("Item " + i));
     77             }
     78 
     79             if (item != null) {
     80                 mItems[i] = item;
     81 
     82                 if (mParams.listenForClicks) {
     83                     item.setOnMenuItemClickListener(this);
     84                 }
     85             }
     86 
     87         }
     88 
     89         return true;
     90     }
     91 
     92     @Override
     93     public boolean onPrepareOptionsMenu(Menu menu) {
     94         // Safe to hold on to
     95         mMenu = menu;
     96 
     97         return mParams.shouldShowMenu;
     98     }
     99 
    100     /**
    101      * Override this to add an item to the menu.
    102      *
    103      * @param itemPosition The position of the item to add (only for your
    104      *            reference).
    105      * @return The item that was added to the menu, or null if nothing was
    106      *         added.
    107      */
    108     protected MenuItem onAddMenuItem(Menu menu, int itemPosition) {
    109         return null;
    110     }
    111 
    112     /**
    113      * Override this to set the parameters for the scenario. Call through to super first.
    114      *
    115      * @param params
    116      */
    117     protected void onInitParams(Params params) {
    118     }
    119 
    120     public Menu getMenu() {
    121         return mMenu;
    122     }
    123 
    124     public boolean onMenuItemClick(MenuItem item) {
    125         final int position = findItemPosition(item);
    126         if (position < 0) return false;
    127 
    128         mWasItemClicked[position] = true;
    129 
    130         return true;
    131     }
    132 
    133     public boolean wasItemClicked(int position) {
    134         return mWasItemClicked[position];
    135     }
    136 
    137     /**
    138      * Finds the position for a given Item.
    139      *
    140      * @param item The item to find.
    141      * @return The position, or -1 if not found.
    142      */
    143     public int findItemPosition(MenuItem item) {
    144         // Could create reverse mapping, but optimizations aren't important (yet :P)
    145         for (int i = 0; i < mParams.numItems; i++) {
    146             if (mItems[i] == item) return i;
    147         }
    148 
    149         return -1;
    150     }
    151 
    152     /**
    153      * @see MenuBuilder#getMenuAdapter(int)
    154      */
    155     public MenuAdapter getMenuAdapter(int menuType) {
    156         if (mMenuAdapters[menuType] == null) {
    157             mMenuAdapters[menuType] = ((MenuBuilder) mMenu).getMenuAdapter(menuType);
    158         }
    159 
    160         return mMenuAdapters[menuType];
    161     }
    162 
    163     /**
    164      * Gets a menu view. Call this after you're sure it has been shown,
    165      * otherwise it may not have the proper layout_* attributes set.
    166      *
    167      * @param menuType The type of menu.
    168      * @return The MenuView for that type.
    169      */
    170     public View getMenuView(int menuType) {
    171         return ((MenuBuilder) mMenu).getMenuView(menuType, null);
    172     }
    173 
    174     /**
    175      * Gets the menu item view for a given position.
    176      *
    177      * @param menuType The type of menu.
    178      * @param position The position of the item.
    179      * @return The menu item view for the given item in the given menu type.
    180      */
    181     public View getItemView(int menuType, int position) {
    182         return getMenuAdapter(menuType).getView(position, null, null);
    183     }
    184 
    185     public static class Params {
    186         // Using as data structure, so no m prefix
    187         private boolean shouldShowMenu = true;
    188         private int numItems = 10;
    189         private boolean listenForClicks = true;
    190         private SparseArray<CharSequence> itemTitles = new SparseArray<CharSequence>();
    191 
    192         public Params setShouldShowMenu(boolean shouldShowMenu) {
    193             this.shouldShowMenu = shouldShowMenu;
    194             return this;
    195         }
    196 
    197         public Params setNumItems(int numItems) {
    198             this.numItems = numItems;
    199             return this;
    200         }
    201 
    202         public Params setListenForClicks(boolean listenForClicks) {
    203             this.listenForClicks = listenForClicks;
    204             return this;
    205         }
    206 
    207         public Params setItemTitle(int itemPos, CharSequence title) {
    208             itemTitles.put(itemPos, title);
    209             return this;
    210         }
    211     }
    212 }
    213