Wed, 31 Dec 2014 06:09:35 +0100
Cloned upstream origin tor-browser at tor-browser-31.3.0esr-4.5-1-build1
revision ID fc1c9ff7c1b2defdbc039f12214767608f46423f for hacking purpose.
1 /* This Source Code Form is subject to the terms of the Mozilla Public
2 * License, v. 2.0. If a copy of the MPL was not distributed with this file,
3 * You can obtain one at http://mozilla.org/MPL/2.0/. */
5 package org.mozilla.gecko.menu;
7 import org.mozilla.gecko.R;
9 import org.xmlpull.v1.XmlPullParser;
10 import org.xmlpull.v1.XmlPullParserException;
12 import android.content.Context;
13 import android.content.res.TypedArray;
14 import android.content.res.XmlResourceParser;
15 import android.os.Build;
16 import android.util.AttributeSet;
17 import android.util.Xml;
18 import android.view.InflateException;
19 import android.view.Menu;
20 import android.view.MenuInflater;
21 import android.view.MenuItem;
22 import android.view.SubMenu;
24 import java.io.IOException;
26 public class GeckoMenuInflater extends MenuInflater {
27 private static final String LOGTAG = "GeckoMenuInflater";
29 private static final String TAG_MENU = "menu";
30 private static final String TAG_ITEM = "item";
31 private static final int NO_ID = 0;
33 private Context mContext;
35 // Private class to hold the parsed menu item.
36 private class ParsedItem {
37 public int id;
38 public int order;
39 public CharSequence title;
40 public int iconRes;
41 public boolean checkable;
42 public boolean checked;
43 public boolean visible;
44 public boolean enabled;
45 public int showAsAction;
46 public boolean hasSubMenu;
47 }
49 public GeckoMenuInflater(Context context) {
50 super(context);
51 mContext = context;
52 }
54 @Override
55 public void inflate(int menuRes, Menu menu) {
57 // This does not check for a well-formed XML.
59 XmlResourceParser parser = null;
60 try {
61 parser = mContext.getResources().getXml(menuRes);
62 AttributeSet attrs = Xml.asAttributeSet(parser);
64 parseMenu(parser, attrs, menu);
66 } catch (XmlPullParserException e) {
67 throw new InflateException("Error inflating menu XML", e);
68 } catch (IOException e) {
69 throw new InflateException("Error inflating menu XML", e);
70 } finally {
71 if (parser != null)
72 parser.close();
73 }
74 }
76 private void parseMenu(XmlResourceParser parser, AttributeSet attrs, Menu menu)
77 throws XmlPullParserException, IOException {
78 ParsedItem item = null;
80 String tag;
81 int eventType = parser.getEventType();
83 do {
84 tag = parser.getName();
86 switch (eventType) {
87 case XmlPullParser.START_TAG:
88 if (tag.equals(TAG_ITEM)) {
89 // Parse the menu item.
90 item = new ParsedItem();
91 parseItem(item, attrs);
92 } else if (tag.equals(TAG_MENU)) {
93 if (item != null) {
94 // Add the submenu item.
95 SubMenu subMenu = menu.addSubMenu(NO_ID, item.id, item.order, item.title);
96 item.hasSubMenu = true;
98 // Set the menu item in main menu.
99 MenuItem menuItem = subMenu.getItem();
100 setValues(item, menuItem);
102 // Start parsing the sub menu.
103 parseMenu(parser, attrs, subMenu);
104 }
105 }
106 break;
108 case XmlPullParser.END_TAG:
109 if (parser.getName().equals(TAG_ITEM)) {
110 if (!item.hasSubMenu) {
111 // Add the item.
112 MenuItem menuItem = menu.add(NO_ID, item.id, item.order, item.title);
113 setValues(item, menuItem);
114 }
115 } else if (tag.equals(TAG_MENU)) {
116 return;
117 }
118 break;
119 }
121 eventType = parser.next();
123 } while (eventType != XmlPullParser.END_DOCUMENT);
124 }
126 public void parseItem(ParsedItem item, AttributeSet attrs) {
127 TypedArray a = mContext.obtainStyledAttributes(attrs, R.styleable.MenuItem);
129 item.id = a.getResourceId(R.styleable.MenuItem_android_id, NO_ID);
130 item.order = a.getInt(R.styleable.MenuItem_android_orderInCategory, 0);
131 item.title = a.getText(R.styleable.MenuItem_android_title);
132 item.iconRes = a.getResourceId(R.styleable.MenuItem_android_icon, 0);
133 item.checkable = a.getBoolean(R.styleable.MenuItem_android_checkable, false);
134 item.checked = a.getBoolean(R.styleable.MenuItem_android_checked, false);
135 item.visible = a.getBoolean(R.styleable.MenuItem_android_visible, true);
136 item.enabled = a.getBoolean(R.styleable.MenuItem_android_enabled, true);
137 item.hasSubMenu = false;
139 if (Build.VERSION.SDK_INT >= 11)
140 item.showAsAction = a.getInt(R.styleable.MenuItem_android_showAsAction, 0);
142 a.recycle();
143 }
145 public void setValues(ParsedItem item, MenuItem menuItem) {
146 menuItem.setChecked(item.checked)
147 .setVisible(item.visible)
148 .setEnabled(item.enabled)
149 .setCheckable(item.checkable)
150 .setIcon(item.iconRes);
152 if (Build.VERSION.SDK_INT >= 11)
153 menuItem.setShowAsAction(item.showAsAction);
154 }
155 }