I am using the following code on a API 15 (Galaxy Nexus) avdevice
The menu_share.xml
<item
android:id="#+id/menu_share"
android:actionProviderClass="android.widget.ShareActionProvider"
android:showAsAction="ifRoom"
android:title="Share"/>
<item
android:id="#+id/item1"
android:orderInCategory="20"
android:showAsAction="always|collapseActionView"
android:title="Refresh">
</item>
The main activity looks like this
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.activity_main, menu);
// Get the ActionProvider
provider = (ShareActionProvider) menu.findItem(R.id.menu_share)
.getActionProvider();
// Initialize the share intent
intent = new Intent(Intent.ACTION_SEND);
intent.putExtra(Intent.EXTRA_TEXT, "This is my text to send.");
intent.setType("text/plain");
provider.setShareIntent(intent);
return true;
}
When I run it on a API 15 (Galaxy Nexus) avd it shows me only the following icon that I cannot click (although it should show me at least the messageing app).
When I run the same code on a API 17 tablet avd I can start the Messaging app offered by the SharedActionProvider - it looks like this
On the tablet how can I make the Messageing app to show in the dropdown list instead like this and how to make the shared action provider on the API15 AVD clickable (first image)?
Thanks.
This is known Android bug. Check related bug report in ActionBarSherlock and android bug itself.
Bug is 1.5 years old and still not fixed.
Related
My old app has one simple menu on the main activity. It has only a few simple options, for instance "About" causing a popup with some info about the app.
It works perfectly on emulator Nexus One (API23), because there is an emulated physical menu button.
However, on most modern phones, there is no button, which means that my menus cannot be accessed.
I actually vaguely remember running it on a phone years ago which didn't have a menu button, yet somehow one could still access the menus. I may remember wrong.
(I started digging into this some days ago, and started modifying my code, the main activity inheriting from something more posh than Activity, which then caused some older API versions to be left out - and things quickly spun out of control. After hours of "maven gradle settings" and "Support Library" stuff and many pages of "AAPT2 errors" and messing up my whole system trying to fix that, I had to throw everything away and get a fresh clone from the repo. Fortunately I could also repair the other changes I had made to the system.)
How does one convert an old-style app menu to work on modern phones? It doesn't have to be fancy.
/** Setup menu */
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.main, menu);
return true;
}
/** Handle menu clicks */
#Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle item selection
switch (item.getItemId()) {
case R.id.action_about:
final SpannableString s =
new SpannableString(getApplicationContext().getText(R.string.about));
Linkify.addLinks(s, Linkify.ALL);
AlertDialog d = new AlertDialog.Builder(this)
.setIcon(android.R.drawable.ic_dialog_info)
.setTitle("About")
.setMessage(s)
//.setView(message)
.show();
((TextView)d.findViewById(android.R.id.message)).setMovementMethod(LinkMovementMethod.getInstance());
return true;
default:
new AlertDialog.Builder(this)
.setIcon(android.R.drawable.ic_dialog_info)
.setTitle("Currently not used.")
.show();
return super.onOptionsItemSelected(item);
}
}
I'll admit that I no longer understand all the details above from years ago.. it worked, so I never paid it much attention. It looks a bit wordy... probably there are simpler ways to do it.
This is menu/main.xml
<menu xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="#+id/action_settings"
android:orderInCategory="100"
android:title="#string/action_settings"/>
<item
android:id="#+id/action_about"
android:orderInCategory="3"
android:title="About"/>
<item
android:id="#+id/action_manual"
android:orderInCategory="4"
android:title="Manual"/>
</menu>
Maybe there is some "theme" to just add somewhere that makes the menu button show up somewhere on the screen, and that's that? (I know I am optimistic. :))
Everything looks fine.
I think your problem is because you are extending Activity.
change Activity to AppComatActivity.
and change your appThem to android:theme="#style/Theme.AppCompat.Light.DarkActionBar"
Note:
To use the AppCompatActivity, make sure you have the Google Support Library downloaded (you can check this in your Tools -> Android -> SDK manager). Then just include the gradle dependency in your app's gradle.build file:
compile 'com.android.support:appcompat-v7:27.0.2'
SOLUTION:
The only way to a solution that I could find was to create a completely new project with default settings in the latest Android Studio. This gives a "latest fashion" setup. Then I moved code in from the old project manually.
Everything now works perfectly!
ISSUES / REASONS:
As mentioned in the comment section above, every attempt I made to modernize the code resulted in a maze of problems. It was an old project, from way back when Android Studio was not even in Beta stage. Hence, it was based on Eclipse. The current Android version back then was Jelly Bean (Kitkat was just released).
In summary, we had an ancient project based on an older IDE. Perhaps it would be doable to convert a modern Eclipse project into Android Studio. Perhaps it would be doable to convert an older AS project into a modern one. However, performing both these major jumps at the same time was too great a challenge for me.
Another issue which has nothing to do with the old code, but which confused the matter greatly is that something called AAPT2 currently for whatever reason assumes american characters only in the search path to the .gradle directory. I use the word "assumes", because if the characters are anything else, you get pages of errors in the build log. None of the errors point very clearly to the reason.
AFAIK I don't even use AAPT2! After some sleepless nights, I solved it by changing the global setting in Android Studio to simply use another path.
I was working around my old ShareAction on my ActionBar and it was working since I updated my Packages on SDK Manager. I saw this doc from Google which says,
To add a "share" action to your activity, put a ShareActionProvider in
the app bar's menu resource. For example:
And I've added the same without adding any Icons:
<item android:id="#+id/action_share"
android:title="#string/share"
app:showAsAction="ifRoom"
app:actionProviderClass="android.support.v7.widget.ShareActionProvider"/>
I was using:
app:actionProviderClass="Mypackagename.ShareActionProvider"
With a custom ShareActionProvider with the following code.you can see it here.
I saw a hack or a trick to do that (with ShareActionProvider-v4) and everything was good since I decided to use android.support.v7.widget.ShareActionProvider.
So, Here is my currently code:
<item
android:id="#+id/shareac"
android:title="#string/share"
app:actionProviderClass="android.support.v7.widget.ShareActionProvider"
app:showAsAction="always" />
I didn't use the Icon because here the doc says,
You do not need to specify an icon, since the ShareActionProvider
widget takes care of its own appearance and behavior. However, you do
need to specify a title with android:title, in case the action ends up
in the overflow menu.
And here is what I've done so far:
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_main_details, menu);
// Locate MenuItem with ShareActionProvider
MenuItem item = menu.findItem(R.id.shareac);
// Fetch and store ShareActionProvider
mShareActionProvider = (ShareActionProvider) MenuItemCompat.getActionProvider(item);
Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
Bundle extra = getIntent().getExtras();
String title = extra.getString("title");
Bundle extraurl = getIntent().getExtras();
String url = extraurl.getString("url");
shareIntent.putExtra(Intent.EXTRA_TEXT, "Check this new project from something : " + title + url);
shareIntent.setType("text/plain");
mShareActionProvider.setShareIntent(shareIntent);
return true;
}
So, here what I see right now in Android Studio 1.5.1 Is,
And if run and compile the app:
As you can see, the size of ShareAction is too much. (It's violating the MaterialDesign guideline I guess).
I forgot to say, I've already tried android:icon="#mipmap/ic_share" which that was working with my previous method/trick. But, check this Preview from AndroidStudio:
And here is after compiled:
Nothing changed!
So, my question: is that a bug or what am I doing wrong here?
Intent.createChooser didn't work also: from: https://stackoverflow.com/a/34797718/4409113
Edit:
The most interesting part, i just saw the same design and the same resutls from Google on the following course and on that app which they've called it SunShine app:
Applink
Course:
https://www.udacity.com//course/viewer#!/c-ud855/l-3961788738/m-4294896397
Okay, As ianhanniballake at this post said,
Icons in material design are 24dp x 24dp, as properly reflected by the
SearchView. However, ShareActionProvider has not yet been updated to
material design by default.
By the way, i've just posted a question/report to code.google.com which you can see it here:
http://code.google.com/p/android/issues/detail?id=200335
It seems that default icon is 24dp x 24dp but it should be like this:
But now, it is like this:
Seems to be a bug and still waiting for accepting or answering about it.I'll update this post if they answered.7 days passed!
UPDATE:
Finally, they've assigned the defect on to the development team and they will update this issue with more information as it becomes available.
Big thanks to ssingamc...#google.com at Google for support.
The answer is available here: http://code.google.com/p/android/issues/detail?id=200335#c10
I will update this answer if any updates or any fixes was available.
UPDATE: http://code.google.com/p/android/issues/detail?id=200335#c12
Hi, The development team has fixed the issue that you have reported
and it will be available in a future build. Thanks
Icons in material design are 24dp x 24dp, as properly reflected by the SearchView. However, ShareActionProvider has not yet been updated to material design by default.
You can set actionModeShareDrawable in your theme to set the share icon in the ShareActionProvider:
<item name="actionModeShareDrawable">#drawable/share_icon</item>
Note that ShareActionProvider is not found anywhere in the material design guidelines and with Android M's Direct Share capability (which requires you use a standard share intent at this time), it is unclear on whether the ShareActionProvider is a suggested pattern any more.
For more detail Visit Here.
AppCompat ShareActionProvider icon is too big compared to other icons
Change the icon Pragmatically
#Override
public boolean onCreateOptionsMenu(Menu menu) {
getMenuInflater().inflate(R.menu.menu_main_details, menu);
// Locate MenuItem with ShareActionProvider
MenuItem item = menu.findItem(R.id.shareac);
// Fetch and store ShareActionProvider
mShareActionProvider = (ShareActionProvider) MenuItemCompat.getActionProvider(item);
Intent shareIntent = new Intent();
shareIntent.setAction(Intent.ACTION_SEND);
Bundle extra = getIntent().getExtras();
String title = extra.getString("title");
Bundle extraurl = getIntent().getExtras();
String url = extraurl.getString("url");
shareIntent.putExtra(Intent.EXTRA_TEXT, "Check this new project from something : " + title + url);
shareIntent.setType("text/plain");
mShareActionProvider.setShareIntent(shareIntent);
//Here
item.setIcon(getResources().getDrawable(R.drawable.ic_share));
return true;
}
or Theme
<item name="actionModeShareDrawable">#drawable/ic_share</item>
If you don't need custom icon for share menu item then try android resource for share menuitem as below:
<item android:id="#+id/action_share"
android:title="#string/share"
app:showAsAction="ifRoom"
android:icon="#android:drawable/ic_share"
app:actionProviderClass="android.support.v7.widget.ShareActionProvider"/>
See here
I am trying to create an app for android and I came across the following problem:
The application crashes in a specific phone when I press the menu button. Let me give you some details first.
The bug occurs to ONLY on LG Optimus L3 II e430 with Android 4.1.2 (tested on four other phones so far)
The application starts with a splash screen and no action bar. At this point menu button just doesn't do anything.
With a simple touch we get past the splash screen and we go to the Main Activity which implements ActionBar activity and has a navigation drawer.
From this point and after, every time I try to click on the menu button the app crashes.
Here is the layout of the menu and the onCreateOptionsMenu function:
res/menu/main.xml
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<item android:id="#+id/action_settings"
android:title="#string/action_settings"
android:orderInCategory="100"
app:showAsAction="never" />
</menu>
Part from MainActivity.java
#Override
public boolean onCreateOptionsMenu(Menu menu) {
if (!mNavigationDrawerFragment.isDrawerOpen()) {
// Only show items in the action bar relevant to this screen
// if the drawer is not showing. Otherwise, let the drawer
// decide what to show in the action bar.
getMenuInflater().inflate(R.menu.main, menu);
restoreActionBar();
return true;
}
return super.onCreateOptionsMenu(menu);
}
Please note that this code is generated from Android Studio.
So far what I've tried:
Tried to look at the file that has the problem from the sdk sources (API Level 16 and 21) but they were not relevant to the stack trace (line shown in the stack trace pointed in a location that didn't make sense).
Tried to install XPosed fix for Google PlayStore crash with menu button bug. Nothing here either.
Found a similar bug report to firefox's bugtracking system so I tried to install Firefox and see if it crashes on my phone when I press Menu Button; firefox didn't crash. (Link to firefox's bug)
Here is the stack trace from LogCat:
10-24 09:08:02.710 4712-4712/com.scaryboxstudios.unrealestateapp E/AndroidRuntime﹕ FATAL EXCEPTION: main
java.lang.NullPointerException
at com.android.internal.policy.impl.PhoneWindow.onKeyUpPanel(PhoneWindow.java:1004)
at com.android.internal.policy.impl.PhoneWindow.onKeyUp(PhoneWindow.java:1712)
at com.android.internal.policy.impl.PhoneWindow$DecorView.dispatchKeyEvent(PhoneWindow.java:2125)
at android.view.ViewRootImpl.deliverKeyEventPostIme(ViewRootImpl.java:3611)
at android.view.ViewRootImpl.handleImeFinishedEvent(ViewRootImpl.java:3581)
at android.view.ViewRootImpl$ViewRootHandler.handleMessage(ViewRootImpl.java:2831)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:137)
at android.app.ActivityThread.main(ActivityThread.java:4929)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:511)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:798)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:565)
at de.robv.android.xposed.XposedBridge.main(XposedBridge.java:132)
at dalvik.system.NativeStart.main(Native Method)
Update: With Appcompat-v7 version 22.0.0, onKeyUp does not seem to fire for the Menu key. The original bug appears to be fixed, so I will likely remove the submenu workaround. Unfortunately I haven't verified the fix on an affected LG 4.1 device.
I ended up doing a workaround for this, which users are reporting has fixed the issue for them.
Implement submenus instead of relying on the overflow menu. The caveat to this is that now every device will see the overflow button in the Action Bar even if they have a Menu key.
The following technique is from https://stackoverflow.com/a/18530179/57490
Convert all overflow options menu items to submenus.
Override onKeyUp in your Activities, have it call Menu.performIdentifierAction(R.id.menu_overflow, 0); and do not call super.onKeyUp for keyCode == KEYCODE_MENU.
After stumbling upon the same problem recently I found the root of the problem. The problem is compatibility issues between older and newer support libraries. It seems that I used depreciated stuff around my code together with newer stuff.
I am sorry for being kind of abstract but this question is 4 months old and I cannot remember what exactly were the incorrect lines of code. If memory serves right, the problem lied upon auto generated methods from Android Studio for application drawer activities. I used the Drawer Application project template from Android Studio and I chose to support very old Android APIs too so Android Studio chose the depreciated Android Support Library.
The point is that I resolved the problem when I refactored the code to use non depreciated techniques only.
If you are fighting against a similar problem I strongly recommend remove everything that Android Studio (I assume that you use Android Studio or Eclipse) marks as depreciated.
Also for catching Menu button can use next:
#Override
public boolean dispatchKeyEvent(KeyEvent event) {
if (event.getKeyCode() == KeyEvent.KEYCODE_MENU) {
// TODO - Your user code
/*
if (event.getAction() == KeyEvent.ACTION_DOWN
&& event.getRepeatCount() == 0) {
// Tell the framework to start tracking this event.
//getKeyDispatcherState().startTracking(event, this);
return true;
} else if (event.getAction() == KeyEvent.ACTION_UP) {
// getKeyDispatcherState().handleUpEvent(event);
if (event.isTracking() && !event.isCanceled()) {
// DO BACK ACTION HERE
return true;
}
}*/
// if you don't want use system listener
// return super.dispatchKeyEvent(event);
return false;
} else {
return super.dispatchKeyEvent(event);
}
}
Worked for lastest AppCompat and SDK version - 22.0
I'm facing a problem when actions intended to be shown in overflow menu in action bar are not there on Galaxy S3. As a consequence the UX is somewhat confusing - my action bar on Galaxy S3 is there to only display app logo and name but offering no extra functionality.
I'd like to have an identical UX on all devices running on Android 4.x with actions in the overflow menu. Is this possible without using third-party components such as ActionBarSherlock?
Thanls
This is a decision made by some manufacturers that requires some "bad" solutions if you really want to do this. The overflow menu is just the "regular" old menu button that all android devices used to have. When the menu button got removed by Google in Honeycomb and ICS some manufacturers decided to keep the menu button. This has lead to great confusion about what the menu button is and does.
You should keep in mind though that the user using a S3 would expect to have a functional menu button as they would not be used to seeing a 3-dot menu. All apps using the built in menu system should appear in a way to the user that they expect. Therefor I would strongly recommend against the urge to have your app look exactly the same on all devices in this matter since it would most likely confuse users more then help them. It should be possible, to both implement the "proper" menu system and a "custom/fake" 3-dot menu if you wish however.
This post seems to have some good guidelines:
https://stackoverflow.com/a/10713860/1068167
There is a quick and dirty way to fake the absence of a hardware menu button using reflection to set a field in your app's ViewConfiguration instance.
The following code snip can be added to your activity and called during onCreate().
private void enableActionBarOverflow() {
try {
ViewConfiguration config = ViewConfiguration.get(this);
Field menuKeyField = ViewConfiguration.class
.getDeclaredField("sHasPermanentMenuKey");
if(menuKeyField != null) {
menuKeyField.setAccessible(true);
menuKeyField.setBoolean(config, false);
}
} catch (Exception e) {
e.printStackTrace();
}
}
Not a clean solution as the implementation of ViewConfiguration could change at some point in the future, and since the sHasPermanentMenuKey field is private, there's no guarantee that the field will always be there.
However, I would only use this as a last resort if you absolutely must have an overflow menu on devices that have a menu key.
Assuming you're minimum API is 11 (Honeycomb) or greater, a better solution would be to make your own overflow menu like so:
Add a menu item for the overflow in your menu.xml, setting it to always show and inflate in your onCreateOptionsMenu()
<menu xmlns:android="http://schemas.android.com/apk/res/android" >
...
<item
android:id="#+id/action_overflow"
android:icon="#drawable/ic_action_settings"
android:title="#string/settings"
android:showAsAction="always">
</item>
</menu>
,
#Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater mi = getMenuInflater();
mi.inflate(R.menu.menu, menu);
return super.onCreateOptionsMenu(menu);
}
Create a separate overflow_menu.xml resource for your choices you want in the overflow menu
<menu xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="#+id/overflow_action1"
android:title="#string/overflow_action1">
</item>
<item
android:id="#+id/overflow_action2"
android:title="#string/overflow_action2">
</item>
</menu>
In your onOptionsItemSelected() method, handle the selection of your overflow menu
#Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
...
case R.id.action_overflow:
PopupMenu popup = new PopupMenu(
this, findViewById(R.id.action_overflow));
MenuInflater inflater = popup.getMenuInflater();
inflater.inflate(R.menu.overflow_menu, popup.getMenu());
popup.setOnMenuItemClickListener(this);
popup.show();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
Implement the PopupMenu.OnMenuItemClickListener interface in your activity to handle the clicks of the overflow items
#Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.overflow_action1:
//do stuff
return true;
case R.id.overflow_action2:
//do stuff
return true;
default:
return false;
}
}
I'd like to have all of the menu items that don't fit into the ActionBar go into the overflow menu (the one that is reached from the Action Bar not the menu button) even on devices that do have a Menu button. This seems much more intuitive for users than throwing them into a separate menu list that requires the user to jump from a touch(screen) interaction to a button based interaction simply because the layout of the ActionBar can't fit them on the bar.
On the emulator I can set the "Hardware Back/Home Keys" value to "no" and get this effect.
I've searched for a way to do this in code for an actual device that has a menu button but can't fine one. Can anyone help me?
You can also use this little hack here:
try {
ViewConfiguration config = ViewConfiguration.get(this);
Field menuKeyField = ViewConfiguration.class.getDeclaredField("sHasPermanentMenuKey");
if (menuKeyField != null) {
menuKeyField.setAccessible(true);
menuKeyField.setBoolean(config, false);
}
} catch (Exception ignored) {
}
Good place to put it would be the onCreate-Method of your Application class.
It will force the App to show the overflow menu. The menu button will still work, but it will open the menu in the top right corner.
[Edit] Since it has come up several times now: This hack only works for the native ActionBar introduced in Android 3.0, not ActionBarSherlock. The latter uses its own internal logic to decide whether to show the overflow menu. If you use ABS, all platforms < 4.0 are handled by ABS and are thus subjected to its logic. The hack will still work for all devices with Android 4.0 or greater (you can safely ignore Android 3.x, since there aren't really any tablets out there with a menu button).
There exists a special ForceOverflow-Theme that will force the menu in ABS, but apperently it is going to be removed in future versions due to complications.
EDIT: Modified to answer for the situation of physical menu button.
This is actually prevented by design. According to the Compatibility Section of the Android Design Guide,
"...the action overflow is available from the menu hardware key. The resulting actions popup... is displayed at the bottom of the screen."
You'll note in the screenshots, phones with a physical menu button don't have an overflow menu in the ActionBar. This avoids ambiguity for the user, essentially having two buttons available to open the exact same menu.
To address the issue of consistency across devices: Ultimately it's more important to the user experience that your app behave consistently with every other app on the same device, than that it behave consistently with itself across all devices.
I use to workaround it by defining my menu like this (also with ActionBarSherlock icon used in my example):
<menu xmlns:android="http://schemas.android.com/apk/res/android" >
<item
android:id="#+id/menu_overflow"
android:icon="#drawable/abs__ic_menu_moreoverflow_normal_holo_light"
android:orderInCategory="11111"
android:showAsAction="always">
<menu>
<item
android:id="#+id/menu_overflow_item1"
android:showAsAction="never"
android:title="#string/overflow_item1_title"/>
<item
android:id="#+id/menu_overflow_item2"
android:showAsAction="never"
android:title="#string/overflow_item2_title"/>
</menu>
</item>
</menu>
I admit that this may require manual "overflow-management" in your xml, but I found this solution useful.
You can also force device to use HW button to open the overflow menu, in your activity:
private Menu mainMenu;
#Override
public boolean onCreateOptionsMenu(Menu menu) {
// TODO: init menu here...
// then:
mainMenu=menu;
return true;
}
#Override
public boolean onKeyUp(int keycode, KeyEvent e) {
switch(keycode) {
case KeyEvent.KEYCODE_MENU:
if (mainMenu !=null) {
mainMenu.performIdentifierAction(R.id.menu_overflow, 0);
}
}
return super.onKeyUp(keycode, e);
}
:-)
If you are using the action bar from the support library (android.support.v7.app.ActionBar), use the following:
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:yorapp="http://schemas.android.com/apk/res-auto" >
<item
android:id="#+id/menu_overflow"
android:icon="#drawable/icon"
yourapp:showAsAction="always"
android:title="">
<menu>
<item
android:id="#+id/item1"
android:title="item1"/>
<item
android:id="#+id/item2"
android:title="item2"/>
</menu>
</item>
</menu>
This kind of method is prevented by the Android Developers Design System, but I found a way to pass it:
Add this to your XML menu file:
<item android:id="#+id/pick_action_provider"
android:showAsAction="always"
android:title="More"
android:icon="#drawable/ic_action_overflow"
android:actionProviderClass="com.example.AppPickActionProvider" />
Next, create a class named 'AppPickActionProvider', and copy the following code to it:
package com.example;
import android.content.Context;
import android.util.Log;
import android.view.ActionProvider;
import android.view.MenuItem;
import android.view.MenuItem.OnMenuItemClickListener;
import android.view.SubMenu;
import android.view.View;
public class AppPickActionProvider extends ActionProvider implements
OnMenuItemClickListener {
static final int LIST_LENGTH = 3;
Context mContext;
public AppPickActionProvider(Context context) {
super(context);
mContext = context;
}
#Override
public View onCreateActionView() {
Log.d(this.getClass().getSimpleName(), "onCreateActionView");
return null;
}
#Override
public boolean onPerformDefaultAction() {
Log.d(this.getClass().getSimpleName(), "onPerformDefaultAction");
return super.onPerformDefaultAction();
}
#Override
public boolean hasSubMenu() {
Log.d(this.getClass().getSimpleName(), "hasSubMenu");
return true;
}
#Override
public void onPrepareSubMenu(SubMenu subMenu) {
Log.d(this.getClass().getSimpleName(), "onPrepareSubMenu");
subMenu.clear();
subMenu.add(0, 1, 1, "Item1")
.setIcon(R.drawable.ic_action_home).setOnMenuItemClickListener(this);
subMenu.add(0, 2, 1, "Item2")
.setIcon(R.drawable.ic_action_downloads).setOnMenuItemClickListener(this);
}
#Override
public boolean onMenuItemClick(MenuItem item) {
switch(item.getItemId())
{
case 1:
// What will happen when the user presses the first menu item ( 'Item1' )
break;
case 2:
// What will happen when the user presses the second menu item ( 'Item2' )
break;
}
return true;
}
}
Well I think that Alexander Lucas has provided the (unfortunately) correct answer so I'm marking it as the "correct" one. The alternative answer I'm adding here is simply to point any new readers to this post in the Android Developers blog as a rather complete discussion of the topic with some specific suggestions as to how to deal with your code when transitioning from pre-level 11 to the new Action Bar.
I still believe it was a design mistake not have the menu button behave as a redundant "Action Overflow" button in menu button enabled devices as a better way to transition the user experience but its water under the bridge at this point.
I'm not sure if this is what you're looking for, but I built a Submenu within the ActionBar's Menu and set its icon to match the Overflow Menu's Icon. Although it wont have items automatically sent to it, (IE you have to choose what's always visible and what's always overflowed) it seems to me that this approach may help you.
In the gmail app that comes with ICS pre-installed, the menu button is disabled when you have multiple items selected. The overflow menu is here "forced" to be triggered by the use of the overflow button instead of the physical menu button. Theres a 3rd-party lib called ActionBarSherlock which lets you "force" the overflow menu. But this will only work on API level 14 or lower(pre-ICS)
If you use Toolbar, you can show the overflow on all versions and all devices, I've tried on some 2.x devices, it works.
Sorry if this problem is dead.
Here is what I did to resolve the error. I went to layouts and created two ones containing toolbars. One was a layout for sdk version 8 and the other was for sdk version 21. On version 8, I used the android.support.v7.widget.Toolbar while I used android.widget.Toolbar on the sdk 21 layout.
Then I inflate the toolbar in my activity. I check the sdk to see if it was 21 or higher. I then inflate the corresponding layout. This forces the hardware button to map onto the toolbar you actually designed.
For anyone using the new Toolbar:
private Toolbar mToolbar;
#Override
protected void onCreate(Bundle bundle) {
super.onCreate(bundle);
mToolbar = (Toolbar) findViewById(R.id.toolbar);
setSupportActionBar(mToolbar);
...
}
#Override
public boolean onKeyUp(int keycode, KeyEvent e) {
switch(keycode) {
case KeyEvent.KEYCODE_MENU:
mToolbar.showOverflowMenu();
return true;
}
return super.onKeyUp(keycode, e);
}