ActionBarCompat: java.lang.IllegalStateException: Musisz użyć Theme.AppCompat

102

Otrzymuję RuntimeException na Androidzie 2.3.5, ale ja jestem za pomocą Theme.AppCompat (RES / wartości / themes.xml). To jest telefon: http://www.gsmarena.com/samsung_galaxy_y_s5360-4117.php

 <!-- res/values/themes.xml -->
 <?xml version="1.0" encoding="utf-8"?>
 <resources>

     <style name="Theme.Styled" parent="@style/Theme.AppCompat">
         <item name="actionBarStyle">@style/QueryActionBar</item>
         <item name="android:actionBarStyle">@style/QueryActionBar</item>
     </style>

     <style name="QueryActionBar" parent="@style/Widget.AppCompat.ActionBar">
         <item name="background">@color/blueback</item>
         <item name="android:background">@color/blueback</item>
         <item name="backgroundSplit">@color/blueback</item>
         <item name="android:backgroundSplit">@color/blueback</item>
     </style>

 </resources>

Oto plik wartości-v11.

 <!-- res/values-v11/themes.xml -->
 <?xml version="1.0" encoding="utf-8"?>
 <resources>
    <style name="QueryTheme" parent="@android:style/Theme.Holo">
    <!-- Any customizations for your app running on devices with Theme.Holo here -->
    </style>
 </resources>

Oto błąd.

 java.lang.RuntimeException: Unable to start activity ComponentInfo{com.txt2lrn.www/com.txt2lrn.www.LandingActivity}: java.lang.IllegalStateException: You need to use a Theme.AppCompat theme (or descendant) with this activity.
 at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1651)
 at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:1667)
 at android.app.ActivityThread.access$1500(ActivityThread.java:117)
 at android.app.ActivityThread$H.handleMessage(ActivityThread.java:935)
 at android.os.Handler.dispatchMessage(Handler.java:99)
 at android.os.Looper.loop(Looper.java:130)
 at android.app.ActivityThread.main(ActivityThread.java:3687)
 at java.lang.reflect.Method.invokeNative(Native Method)
 at java.lang.reflect.Method.invoke(Method.java:507)
 at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:867)
 at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:625)
 at dalvik.system.NativeStart.main(Native Method)
 Caused by: java.lang.IllegalStateException: You need to use a Theme.AppCompat theme (or descendant) with this activity.
 at android.support.v7.app.ActionBarActivityDelegate.onCreate(ActionBarActivityDelegate.java:102)
 at android.support.v7.app.ActionBarActivity.onCreate(ActionBarActivity.java:98)
 at com.txt2lrn.www.LandingActivity.onCreate(LandingActivity.java:95)
 at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1047)
 at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:1615)
 ... 11 more

Przepraszam, mam też android: theme = "@ style / Theme.Styled" zdefiniowany w AndroidManifest.xml.

OS1
źródło
1
Czy twój manifest się odnosi Theme.Styled?
CommonsWare,
3
czy masz inny folder wartości, który odwołuje się do Theme.Styled, ale nie używa motywu AppCompat?
tyczj
@tyczj Dodałem plik res / values-v11 / themes.xml i nie odwołuje się do Theme.Styled
AG1
@tyczj Możesz użyć swojego komentarza jako odpowiedzi, ponieważ może to być częsty problem (ja też)
Valentino Dell'Aica

Odpowiedzi:

96

Jeśli rozszerzasz ActionBarActivity w swoim MainActivity, będziesz musiał również zmienić motyw nadrzędny w values-v11.
Więc style.xml w values-v11 będzie -

 <!-- res/values-v11/themes.xml -->
 <?xml version="1.0" encoding="utf-8"?>
 <resources>
    <style name="QueryTheme" parent="@style/Theme.AppCompat">
    <!-- Any customizations for your app running on devices with Theme.Holo here -->
    </style>
 </resources>

EDYCJA: Zalecam zaprzestanie używania ActionBar i rozpoczęcie korzystania z układu AppBar zawartego w bibliotece Android Design Support Library

Nishad
źródło
5
Świetnie, tęskniłem za tym. Nie zapomnij również o wszystkich innych folderach -vXX, w przeciwnym razie będzie działać dobrze w twoim testowym środowisku env, tylko po to, aby cię ugryźć, gdy ktoś użyje jednej z tych wersji.
falstro
1
Dzięki! Właśnie zmieniłem ActionBarActivity na Activity! :)
Inoy
66

Aby po prostu dodać ActionBar Compat, swoją aktywność lub aplikację należy użyć motywu @ style / Theme.AppCompat w AndroidManifest.xml w następujący sposób:

   <activity
        ...
        android:theme="@style/Theme.AppCompat" />

Spowoduje to dodanie paska akcji do aktywności (lub wszystkich działań, jeśli dodałeś ten motyw do aplikacji)


Ale zwykle musisz dostosować pasek akcji. Aby to zrobić, musisz utworzyć dwa style za pomocą elementu nadrzędnego Theme.AppCompat, na przykład „@ style / Theme.AppCompat.Light”. Pierwsza będzie dla api 11> = (wersje Androida z wbudowanym paskiem akcji android), druga dla api 7-10 (brak kompilacji w pasku akcji).

Spójrzmy na pierwszy styl. Będzie się znajdować w res / values-v11 / styles.xml . Będzie to wyglądać tak:

<style name="Theme.Styled" parent="@style/Theme.AppCompat.Light">
    <!-- Setting values in the android namespace affects API levels 11+ -->
    <item name="android:actionBarStyle">@style/Widget.Styled.ActionBar</item>
</style>

<style name="Widget.Styled.ActionBar" parent="@style/Widget.AppCompat.Light.ActionBar">
    <!-- Setting values in the android namespace affects API levels 11+ -->
    <item name="android:background">@drawable/ab_custom_solid_styled</item>
    <item name="android:backgroundStacked"
      >@drawable/ab_custom_stacked_solid_styled</item>
    <item name="android:backgroundSplit"
      >@drawable/ab_custom_bottom_solid_styled</item>
</style>

I musisz mieć ten sam styl dla API 7-10. Będzie znajdował się w res / values ​​/ styles.xml , ALE ponieważ poziomy api nie wiedzą jeszcze o oryginalnych elementach w stylu paska akcji systemu Android, powinniśmy użyć jednego, dostarczonego przez bibliotekę wsparcia. Elementy ActionBar Compat są zdefiniowane tak samo jak w oryginalnym systemie Android, ale bez części „android:” na początku:

<style name="Theme.Styled" parent="@style/Theme.AppCompat.Light">
    <!-- Setting values in the default namespace affects API levels 7-11 -->
    <item name="actionBarStyle">@style/Widget.Styled.ActionBar</item>
</style>

<style name="Widget.Styled.ActionBar" parent="@style/Widget.AppCompat.Light.ActionBar">
    <!-- Setting values in the default namespace affects API levels 7-11 -->
    <item name="background">@drawable/ab_custom_solid_styled</item>
    <item name="backgroundStacked">@drawable/ab_custom_stacked_solid_styled</item>
    <item name="backgroundSplit">@drawable/ab_custom_bottom_solid_styled</item>
</style>

Proszę zaznaczyć, że nawet jeśli poziomy api wyższe niż 10 mają już pasek akcji, nadal powinieneś używać stylów AppCompat. Jeśli tego nie zrobisz, pojawi się ten błąd podczas uruchamiania Acitvity na urządzeniach z Androidem 3.0 i nowszym:

java.lang.IllegalStateException: w tym działaniu należy użyć motywu Theme.AppCompat (lub elementu podrzędnego).

Oto link do tego oryginalnego artykułu http://android-developers.blogspot.com/2013/08/actionbarcompat-and-io-2013-app-source.html napisanego przez Chrisa Banesa.

PS Przepraszam za mój angielski

molokoka
źródło
przybił to! WYBUCHOWANE
tony gil
20

Sprawdź i upewnij się, że nie masz innego folderu wartości, który odwołuje się do theme.styled i nie używa motywu AppCompat

ie values-v11folder

tyczj
źródło
To też był mój problem. Miałem projekt biblioteki i musiałem zaimportować bibliotekę appcompat-v7 i sprawić, by wszystkie motywy rozszerzały motywy AppCompat. Chodzi o to, że mój główny projekt ma narzędzia: replace = "android: icon, android: theme" opcja dodana do <application> i powinien pomijać style z innych projektów. Z jakiegoś powodu to nie działało.
speedynomads
16

Spróbuj tego...

style.xml

<resources>
 <style name="Theme.AppCompat.Light.NoActionBar" parent="@style/Theme.AppCompat.Light">
    <item name="android:windowNoTitle">true</item>
 </style>
</resources>

AndroidManifest.xml

   <activity
        android:name="com.example.Home"
        android:label="@string/app_name" 
        android:theme="@style/Theme.AppCompat.Light.NoActionBar"
        >
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
Silambarasan Poonguti
źródło
11

Twój Activityrozszerza się, ActionBarActivityco wymaga AppCompat.themezastosowania. Zmień ActionBarActivityna Activitylub FragmentActivity, rozwiąże to problem.

Jorgesys
źródło
4

Po prostu zrób to Kompiluj -> Wyczyść projekt. Myślę, że to rozwiąże twój problem.

Valeriy Bilyk
źródło
3

Mój manifest nie odwołuje się do żadnych tematów ... nie powinien mieć AFAIK

Jasne, że tak. Nic w magiczny sposób nie zastosuje się Theme.Styleddo czynności. Musisz zadeklarować swoje działania - lub całą swoją aplikację - wykorzystuje Theme.Stylednp .:

<application
    android:icon="@drawable/ic_launcher"
    android:label="@string/app_name"
    android:theme="@style/Theme.Styled">
CommonsWare
źródło
Pomyliłem się, mam android: theme = "@ style / Theme.Styled" w moim AndroidManifest.xml (nie widziałem tego za pierwszym razem).
AG1
3

Napotkałem ten błąd, gdy próbowałem utworzyć DialogBox, gdy w klasie CustomAdapter wykonywana jest pewna akcja. To nie było działanie, ale klasa adaptera. Po 36 godzinach wysiłków i szukaniu rozwiązań wpadłem na to.

Wyślij działanie jako parametr podczas wywoływania CustomAdapter.

CustomAdapter ca = new CustomAdapter(MyActivity.this,getApplicationContext(),records);

Zdefiniuj zmienne w niestandardowym adapterze.

Activity parentActivity;
Context context;

Wywołaj konstruktora w ten sposób.

public CustomAdapter(Activity parentActivity,Context context,List<Record> records){
    this.parentActivity=parentActivity;
    this.context=context;
    this.records=records;
}

I na koniec podczas tworzenia okna dialogowego w klasie adaptera zrób to w ten sposób.

AlertDialog ad = new AlertDialog.Builder(parentActivity).setTitle("Your title");

and so on..

mam nadzieję, że to Ci pomoże

Harshit Koolwal
źródło
2

Po prostu otrzymuję przeniesienie mojej aplikacji z ActionBarSherlock do ActionBarCompat. Spróbuj zadeklarować swój stary motyw w następujący sposób:

<style name="Theme.Event" parent="Theme.AppCompat">

Następnie ustaw motyw w pliku AndroidManifest.xml:

<application
    android:debuggable="true"
    android:name=".activity.MyApplication"
    android:allowBackup="true"
    android:icon="@drawable/ic_launcher"
    android:label="@string/app_name"
    android:theme="@style/Theme.Event.Home"
     >
Tsung Goh
źródło
2

Miałem taką awarię urządzeniach Samsung , mimo że aktywność korzystała z Theme.AppCompat . Główna przyczyna była związana z dziwnymi optymalizacjami po stronie Samsunga:

- if one activity of your app has theme not inherited from Theme.AppCompat
- and it has also `android:launchMode="singleTask"`
- then all the activities that are launched from it will share the same Theme

Moje rozwiązanie polegało na usunięciu android:launchMode="singleTask"

gorgona
źródło
1
Czy masz źródło tego? Od jakiegoś czasu szukam podobnego błędu w mojej aplikacji i brzmi to jak obiecujący trop.
Dmitry Brant
To samo tutaj! Chciałbym dowiedzieć się więcej na ten temat! Śledziłem podobny błąd w mojej aplikacji. Niestety nie używam android:launchMode="singleTask".
acrespo
Obserwuję ten sam problem. Dzieje się to dla Galaxy Tab A 10.1 (Android 7.0, niezrootowany i SM-A320FL (Android 7.0, nie zrootowany). Nie używam android:launchMode="singleTask"i wszystkie moje działania wykorzystują motyw AppCompat: /
user2990759
2

w moim przypadku utworzyłem niestandardowy widok, który dodałem do konstruktora widoku niestandardowego

new RoomView(getAplicationContext());

poprawnym kontekstem jest aktywność, więc zmieniono go na:

new RoomView(getActivity());

lub

new RoomView(this);
amorenew
źródło
1

W moim widoku listy używam niestandardowego adaptera, który rozszerza ArrayAdapter. w listiview mam 2 przyciski, jeden z przycisków jako Custom AlertDialogBox. Np .: aktywność parentActivity; Konstruktor adaptera `

public CustomAdapter(ArrayList<Contact> data, Activity parentActivity,Context context) {
        super(context,R.layout.listdummy,data);
        this.mContext   =   context;
        this.parentActivity  =   parentActivity;
    }

`wywołując Adapter z MainActivty

adapter = new CustomAdapter(dataModels,MainActivity.this,this);

teraz wpisz ur alertdialog w przycisku ur, który jest w klasie Adapter

viewHolder.update.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(final View view) {
            

                AlertDialog.Builder alertDialog =   new AlertDialog.Builder(parentActivity);
                alertDialog.setTitle("Updating");
                alertDialog.setCancelable(false);

                LayoutInflater layoutInflater   = (LayoutInflater) mContext.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
                 @SuppressLint("InflateParams") final View view1   =   layoutInflater.inflate(R.layout.dialog,null);
                alertDialog.setView(view1);
                alertDialog.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialogInterface, int i) {
                        dialogInterface.cancel();
                    }
                });
                alertDialog.setPositiveButton("Update", new DialogInterface.OnClickListener() {
                    @Override
                    public void onClick(DialogInterface dialogInterface, int i) {

                    //ur logic
                            }
                    }
                });
                  alertDialog.create().show();

            }
        });

Ramesh Kumar
źródło
-2

para resolver o meu problema, eu apenas adicionei na minha MainActivity ("Theme = Aby rozwiązać mój problem, właśnie dodałem go do mojego MainActivity (" Theme = "@ style / MyTheme" "), gdzie MyTheme to nazwa mojego motywu

[Activity(Label = "Name Label", MainLauncher = true, Icon = "@drawable/icon", LaunchMode = LaunchMode.SingleTop, Theme = "@style/MyTheme")]
Deyvidy
źródło