J'utilise la bibliothèque AppCompat (com.Android.support:appcompat-v7:22.1.0) dans mon application. J'ai créé un ActionBar dans un fragment. Lorsque je clique sur un élément de menu, il affiche une boîte de dialogue d'alerte. Voici mon code:
@Override
public boolean onOptionsItemSelected(MenuItem item) {
// Handle item selection
switch (item.getItemId()) {
case R.id.action_new:
showFilterDialog();
return true;
case R.id.action_send:
new sendInventoryTask().execute();
return true;
default:
return super.onOptionsItemSelected(item);
}
}
Et ma méthode showInventoryDialog:
private void showFilterInventoryDialog() {
AlertDialog.Builder alert = new AlertDialog.Builder(getActivity());
LayoutInflater inflater= getActivity().getLayoutInflater();
View v = inflater.inflate(R.layout.dialog_filter_inventory,null);
alert.setView(v);
alert.setTitle(getResources().getString(R.string.filters));
alert.setPositiveButton(getResources().getString(R.string.filter), new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog, int id) {
// TODO
}
});
alert.setNegativeButton(getResources().getString(R.string.cancel), null);
alert.show();
}
Tout fonctionne bien, mais lorsque je clique sur l'élément de menu, le logcat me montre une erreur:
I/AppCompatDelegate Lay L'usine LayoutInflater de l'activité est déjà installée, nous ne pouvons donc pas installer celle d'AppCompat
Comment résoudre ceci?
Vous devez utiliser le contexte thématique dans ce cas, c.-à-d. Au lieu de
new AlertDialog.Builder (getActivity ());
tu dois faire
new AlertDialog.Builder(getSupportActionBar().getThemedContext());
En outre, vous devez également suivre le thème parent et le conseil windowActionBar donnés ici - support.v7.app.AlertDialog lève NullPointerException lors de son renvoi
D'après ce que je peux dire, appcompat 23.1.1 appelle installViewFactory()
dans AppCompatDelegateImplV7
chaque fois que vous affichez une boîte de dialogue créée par AlertDialog.Builder
.
Call Stack:
à Android.support.v7.app.AppCompatDelegateImplV7.installViewFactory (AppCompatDelegateImplV7.Java:970) à Android.support.v7.app.AppCompatDialog.onCreate (AppCompatDialog.Java:58) sur Android.support.v7.app.AlertDialog.onCreate (AlertDialog.Java:239) sur Android.app.Dialog.dispatchOnCreate (Dialog.Java:361) à Android.app.Dialog.show (Dialog.Java:262) à l'adresse Android.support.v7.app.AlertDialog $ Builder.show (AlertDialog.Java:902)
@Override
public void installViewFactory() {
LayoutInflater layoutInflater = LayoutInflater.from(mContext);
if (layoutInflater.getFactory() == null) {
LayoutInflaterCompat.setFactory(layoutInflater, this);
} else {
Log.i(TAG, "The Activity's LayoutInflater already has a Factory installed"
+ " so we can not install AppCompat's");
}
}
Comme vous pouvez le constater, une fois l’usine définie, il n’enregistre que le message d’information. Il semble assez prudent de l'ignorer, mais cela peut être agaçant lorsqu'il remplit vos journaux.
Solution - L'erreur "L'usine de LayoutInflater de l'activité est déjà installée et nous ne pouvons donc pas installer celle d'AppCompat" peut également être due à un code incorrect. Dans mon cas, le code appelait "super.onCreate (savedInstanceState)" deux fois (erreur de code) et une fois que l'appel en double a été supprimé, l'erreur a été résolue.
Voici mon journal des erreurs:
02-29 04:54:40.706 4417-4417/com.projects.ajay.example2 I/AppCompatDelegate: The Activity's LayoutInflater already has a Factory installed so we can not install AppCompat's
02-29 04:54:40.709 4417-4417/? D/AndroidRuntime: Shutting down VM
02-29 04:54:40.715 4417-4417/? E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.projects.ajay.example2, PID: 4417
Java.lang.RuntimeException: Unable to start activity ComponentInfo{com.projects.ajay.example2/com.projects.ajay.example2.MainActivity}: Java.lang.IllegalStateException: Already attached
at Android.app.ActivityThread.performLaunchActivity(ActivityThread.Java:2331)
at Android.app.ActivityThread.handleLaunchActivity(ActivityThread.Java:2393)
at Android.app.ActivityThread.access$800(ActivityThread.Java:151)
at Android.app.ActivityThread$H.handleMessage(ActivityThread.Java:1309)
at Android.os.Handler.dispatchMessage(Handler.Java:102)
at Android.os.Looper.loop(Looper.Java:135)
at Android.app.ActivityThread.main(ActivityThread.Java:5351)
at Java.lang.reflect.Method.invoke(Native Method)
at Java.lang.reflect.Method.invoke(Method.Java:372)
at com.Android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.Java:908)
at com.Android.internal.os.ZygoteInit.main(ZygoteInit.Java:703)
Caused by: Java.lang.IllegalStateException: Already attached
at Android.support.v4.app.FragmentManagerImpl.attachController(FragmentManager.Java:2025)
at Android.support.v4.app.FragmentController.attachHost(FragmentController.Java:95)
at Android.support.v4.app.FragmentActivity.onCreate(FragmentActivity.Java:276)
at Android.support.v7.app.AppCompatActivity.onCreate(AppCompatActivity.Java:61)
at com.projects.ajay.example2.MainActivity.onCreate(MainActivity.Java:24)
at Android.app.Activity.performCreate(Activity.Java:6020)
at Android.app.Instrumentation.callActivityOnCreate(Instrumentation.Java:1105)
at Android.app.ActivityThread.performLaunchActivity(ActivityThread.Java:2284)
at Android.app.ActivityThread.handleLaunchActivity(ActivityThread.Java:2393)
at Android.app.ActivityThread.access$800(ActivityThread.Java:151)
at Android.app.ActivityThread$H.handleMessage(ActivityThread.Java:1309)
at Android.os.Handler.dispatchMessage(Handler.Java:102)
at Android.os.Looper.loop(Looper.Java:135)
at Android.app.ActivityThread.main(ActivityThread.Java:5351)
at Java.lang.reflect.Method.invoke(Native Method)
at Java.lang.reflect.Method.invoke(Method.Java:372)
at com.Android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.Java:908)
at com.Android.internal.os.ZygoteInit.main(ZygoteInit.Java:703)
02-29 04:54:40.727 4417-4417/? I/Process: Sending signal. PID: 4417 SIG: 9