2012-05-31 16:01:50 -07:00
|
|
|
/* This Source Code Form is subject to the terms of the Mozilla Public
|
|
|
|
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
|
|
|
|
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
|
|
|
|
|
|
|
package org.mozilla.gecko;
|
|
|
|
|
|
|
|
import org.xmlpull.v1.XmlPullParser;
|
|
|
|
import org.xmlpull.v1.XmlPullParserException;
|
|
|
|
|
|
|
|
import android.content.Context;
|
|
|
|
import android.content.res.TypedArray;
|
|
|
|
import android.content.res.XmlResourceParser;
|
|
|
|
import android.util.AttributeSet;
|
|
|
|
import android.util.Xml;
|
|
|
|
import android.view.InflateException;
|
|
|
|
import android.view.Menu;
|
|
|
|
import android.view.MenuInflater;
|
|
|
|
import android.view.MenuItem;
|
2012-09-19 10:35:35 -07:00
|
|
|
import android.view.SubMenu;
|
2012-05-31 16:01:50 -07:00
|
|
|
|
2012-07-27 17:53:54 -07:00
|
|
|
import java.io.IOException;
|
|
|
|
|
2012-09-19 10:32:01 -07:00
|
|
|
public class GeckoMenuInflater extends MenuInflater {
|
2012-05-31 16:01:50 -07:00
|
|
|
private static final String LOGTAG = "GeckoMenuInflater";
|
|
|
|
|
2012-09-19 10:35:35 -07:00
|
|
|
private static final String TAG_MENU = "menu";
|
2012-05-31 16:01:50 -07:00
|
|
|
private static final String TAG_ITEM = "item";
|
|
|
|
private static final int NO_ID = 0;
|
|
|
|
|
|
|
|
private Context mContext;
|
|
|
|
|
2012-09-19 10:35:35 -07:00
|
|
|
private boolean isSubMenu;
|
|
|
|
|
2012-07-17 17:54:54 -07:00
|
|
|
// Private class to hold the parsed menu item.
|
|
|
|
private class ParsedItem {
|
2012-05-31 16:01:50 -07:00
|
|
|
public int id;
|
|
|
|
public int order;
|
|
|
|
public CharSequence title;
|
|
|
|
public int iconRes;
|
|
|
|
public boolean checkable;
|
|
|
|
public boolean checked;
|
|
|
|
public boolean visible;
|
|
|
|
public boolean enabled;
|
2012-09-20 11:04:14 -07:00
|
|
|
public int showAsAction;
|
2012-05-31 16:01:50 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
public GeckoMenuInflater(Context context) {
|
|
|
|
super(context);
|
|
|
|
mContext = context;
|
2012-09-19 10:35:35 -07:00
|
|
|
|
|
|
|
isSubMenu = false;
|
2012-05-31 16:01:50 -07:00
|
|
|
}
|
|
|
|
|
|
|
|
public void inflate(int menuRes, Menu menu) {
|
|
|
|
|
2012-09-19 10:35:35 -07:00
|
|
|
// This does not check for a well-formed XML.
|
2012-05-31 16:01:50 -07:00
|
|
|
|
|
|
|
XmlResourceParser parser = null;
|
|
|
|
try {
|
|
|
|
parser = mContext.getResources().getXml(menuRes);
|
|
|
|
AttributeSet attrs = Xml.asAttributeSet(parser);
|
|
|
|
|
|
|
|
ParsedItem item = null;
|
2012-09-19 10:35:35 -07:00
|
|
|
SubMenu subMenu = null;
|
|
|
|
MenuItem menuItem = null;
|
2012-05-31 16:01:50 -07:00
|
|
|
|
|
|
|
String tag;
|
|
|
|
int eventType = parser.getEventType();
|
|
|
|
|
|
|
|
do {
|
|
|
|
tag = parser.getName();
|
|
|
|
|
|
|
|
switch (eventType) {
|
|
|
|
case XmlPullParser.START_TAG:
|
|
|
|
if (tag.equals(TAG_ITEM)) {
|
|
|
|
// Parse the menu item.
|
|
|
|
item = new ParsedItem();
|
|
|
|
parseItem(item, attrs);
|
2012-09-19 10:35:35 -07:00
|
|
|
} else if (tag.equals(TAG_MENU)) {
|
|
|
|
if (item != null) {
|
|
|
|
// Start parsing the sub menu.
|
|
|
|
isSubMenu = true;
|
|
|
|
subMenu = menu.addSubMenu(NO_ID, item.id, item.order, item.title);
|
|
|
|
menuItem = subMenu.getItem();
|
|
|
|
|
|
|
|
// Set the menu item in main menu.
|
|
|
|
setValues(item, menuItem);
|
|
|
|
}
|
|
|
|
}
|
2012-05-31 16:01:50 -07:00
|
|
|
break;
|
|
|
|
|
|
|
|
case XmlPullParser.END_TAG:
|
|
|
|
if (parser.getName().equals(TAG_ITEM)) {
|
2012-09-19 10:35:35 -07:00
|
|
|
if (isSubMenu && subMenu == null) {
|
|
|
|
isSubMenu = false;
|
|
|
|
} else {
|
|
|
|
// Add the item.
|
|
|
|
if (subMenu == null)
|
|
|
|
menuItem = menu.add(NO_ID, item.id, item.order, item.title);
|
|
|
|
else
|
|
|
|
menuItem = subMenu.add(NO_ID, item.id, item.order, item.title);
|
|
|
|
|
|
|
|
setValues(item, menuItem);
|
|
|
|
}
|
|
|
|
} else if (tag.equals(TAG_MENU)) {
|
|
|
|
// End of sub menu.
|
|
|
|
subMenu = null;
|
2012-05-31 16:01:50 -07:00
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
eventType = parser.next();
|
|
|
|
|
|
|
|
} while (eventType != XmlPullParser.END_DOCUMENT);
|
|
|
|
|
|
|
|
} catch (XmlPullParserException e) {
|
|
|
|
throw new InflateException("Error inflating menu XML", e);
|
|
|
|
} catch (IOException e) {
|
|
|
|
throw new InflateException("Error inflating menu XML", e);
|
|
|
|
} finally {
|
|
|
|
if (parser != null)
|
|
|
|
parser.close();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
public void parseItem(ParsedItem item, AttributeSet attrs) {
|
|
|
|
TypedArray a = mContext.obtainStyledAttributes(attrs, R.styleable.MenuItem);
|
|
|
|
|
2012-09-20 11:04:14 -07:00
|
|
|
item.id = a.getResourceId(R.styleable.MenuItem_android_id, NO_ID);
|
|
|
|
item.order = a.getInt(R.styleable.MenuItem_android_orderInCategory, 0);
|
|
|
|
item.title = a.getText(R.styleable.MenuItem_android_title);
|
|
|
|
item.iconRes = a.getResourceId(R.styleable.MenuItem_android_icon, 0);
|
|
|
|
item.checkable = a.getBoolean(R.styleable.MenuItem_android_checkable, false);
|
|
|
|
item.checked = a.getBoolean(R.styleable.MenuItem_android_checked, false);
|
|
|
|
item.visible = a.getBoolean(R.styleable.MenuItem_android_visible, true);
|
|
|
|
item.enabled = a.getBoolean(R.styleable.MenuItem_android_enabled, true);
|
|
|
|
item.showAsAction = a.getInt(R.styleable.MenuItem_android_showAsAction, 0);
|
2012-05-31 16:01:50 -07:00
|
|
|
|
|
|
|
a.recycle();
|
|
|
|
}
|
|
|
|
|
|
|
|
public void setValues(ParsedItem item, MenuItem menuItem) {
|
|
|
|
menuItem.setChecked(item.checked)
|
|
|
|
.setVisible(item.visible)
|
|
|
|
.setEnabled(item.enabled)
|
|
|
|
.setCheckable(item.checkable)
|
|
|
|
.setIcon(item.iconRes)
|
2012-09-20 11:04:14 -07:00
|
|
|
.setShowAsAction(item.showAsAction);
|
2012-05-31 16:01:50 -07:00
|
|
|
}
|
|
|
|
}
|