问题
Trying to use ShareActionProvider
from the support library (v7), my app works fine if I don't set the showAsAction
attribute for the menu item. My intention is to display this menu item as an icon and not as an overflow item.
If, however, I set it to show always, the app crashes with NullPointerException
.
07-30 01:23:37.778: E/AndroidRuntime(25853): java.lang.NullPointerException: Attempt to invoke virtual method 'void android.widget.ImageView.setImageDrawable(android.graphics.drawable.Drawable)' on a null object reference
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.internal.widget.ActivityChooserView.updateAppearance(ActivityChooserView.java:510)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.internal.widget.ActivityChooserView$3.onChanged(ActivityChooserView.java:247)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.database.DataSetObservable.notifyChanged(DataSetObservable.java:37)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.widget.BaseAdapter.notifyDataSetChanged(BaseAdapter.java:50)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.internal.widget.ActivityChooserView$ActivityChooserViewAdapter.setDataModel(ActivityChooserView.java:647)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.internal.widget.ActivityChooserView.setActivityChooserModel(ActivityChooserView.java:260)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.widget.ShareActionProvider.onCreateActionView(ShareActionProvider.java:182)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v4.view.ActionProvider.onCreateActionView(ActionProvider.java:109)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.support.v7.internal.view.menu.MenuItemWrapperJB$ActionProviderWrapperJB.onCreateActionView(MenuItemWrapperJB.java:44)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.MenuItemImpl.getActionView(MenuItemImpl.java:583)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.ActionMenuPresenter.getItemView(ActionMenuPresenter.java:161)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.ActionMenuPresenter.flagActionItems(ActionMenuPresenter.java:438)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.MenuBuilder.flagActionItems(MenuBuilder.java:1062)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.BaseMenuPresenter.updateMenuView(BaseMenuPresenter.java:87)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.ActionMenuPresenter.updateMenuView(ActionMenuPresenter.java:216)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.MenuBuilder.dispatchPresenterUpdate(MenuBuilder.java:244)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.MenuBuilder.onItemsChanged(MenuBuilder.java:956)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.view.menu.MenuBuilder.startDispatchingItemsChanged(MenuBuilder.java:979)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.policy.impl.PhoneWindow.preparePanel(PhoneWindow.java:479)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.policy.impl.PhoneWindow.doInvalidatePanelMenu(PhoneWindow.java:800)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.policy.impl.PhoneWindow$1.run(PhoneWindow.java:221)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.view.Choreographer.doCallbacks(Choreographer.java:574)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.view.Choreographer.doFrame(Choreographer.java:543)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:747)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.os.Handler.handleCallback(Handler.java:733)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.os.Handler.dispatchMessage(Handler.java:95)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.os.Looper.loop(Looper.java:136)
07-30 01:23:37.778: E/AndroidRuntime(25853): at android.app.ActivityThread.main(ActivityThread.java:5001)
07-30 01:23:37.778: E/AndroidRuntime(25853): at java.lang.reflect.Method.invoke(Native Method)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:785)
07-30 01:23:37.778: E/AndroidRuntime(25853): at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
My menu layout: main.xml
<menu xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
tools:context="com.example.myapp.MainActivity" >
<item
android:id="@+id/menu_item_share"
android:title="Share"
app:actionProviderClass="android.support.v7.widget.ShareActionProvider"
app:showAsAction="always"/>
</menu>
My inflation code in the activity:
import android.support.v7.app.ActionBarActivity;
import android.support.v7.widget.ShareActionProvider;
public class MainActivity extends ActionBarActivity
{
...
@Override
public boolean onCreateOptionsMenu(Menu menu)
{
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
// Locate MenuItem with ShareActionProvider
MenuItem item = menu.findItem(R.id.menu_item_share);
// Fetch and store ShareActionProvider
_shareActionProvider = (ShareActionProvider) MenuItemCompat.getActionProvider(item);
setShareIntent();
return true;
}
}
Thanks.
回答1:
Today I have met this problem, this is a support v7 lib bug.
I found two ways to solve this problem if you have to use support v7 lib.
update your support lib to the latest version. the current latest is android 5.0 v7 lib, I have test this lib have fix this bug.
If you don't want to update support v7 lib, you should change app:showAsAction to android:showAsAction in your share item menu xml. I spend lots of time to found this solution.
回答2:
I think your shareintent isn't set properly (but am only guessing from the code you posted). You should call setShareIntent on the actionprovider itself, where you are now calling some unknown function setShareIntent() on a line by itself. Instead, try
_shareActionProvider().setShareIntent(/*some intent*/);
I think that the NPE is when the shareintent provider tries to load the icon for the first share option, and can't handle having no intents to pull an image from. You only have this issue if the provider is displayed in the action bar.
回答3:
set the xml item like this:
<item
android:id="@+id/menu_item_share"
android:title="Share"
support:actionProviderClass="android.support.v7.widget.ShareActionProvider"
support:showAsAction="always"/>
回答4:
the xml item
<item
android:id="@+id/action_share"
android:title="@string/anction_share"
android:orderInCategory="2"
app:showAsAction="always"
app:actionProviderClass="android.support.v7.widget.ShareActionProvider" />
The value declaration
private android.support.v7.widget.ShareActionProvider shareActionProvider;
In code use
MenuItem menuItem = menu.findItem(R.id.action_share);
shareActionProvider = (android.support.v7.widget.ShareActionProvider) MenuItemCompat.getActionProvider(menuItem);
setIntent("Example text.");
setIntent method
private void setIntent(String text){
Intent shareIntent = new Intent(Intent.ACTION_SEND);
shareIntent.setType("text/plain");
shareIntent.putExtra(Intent.EXTRA_TEXT, text);
shareActionProvider.setShareIntent(shareIntent);
}
来源:https://stackoverflow.com/questions/25026225/support-v7-shareactionprovider-crashes-if-showasaction-always