Error Inflating CollapsingToolbarLayout

2019-01-25 03:56发布

问题:

I recently updated the support design library to the latest version and now every activity that has a CollapsingToolbarLayout throws the following exception:

    java.lang.NoSuchMethodError: No static method setLayoutDirection(Landroid/graphics/drawable/Drawable;I)V in class Landroid/support/v4/graphics/drawable/DrawableCompat; or its super classes (declaration of 'android.support.v4.graphics.drawable.DrawableCompat' appears in /data/data/com.radioafrica.music/files/instant-run/dex/slice-com.android.support-support-v4-24.0.0-beta1_f8cf3ba4c70f87f407a745b9fa14a2205d0b587c-classes.dex)

The full error log is as follows:

java.lang.RuntimeException: Unable to start activity ComponentInfo{com.radioafrica.music/com.radioafrica.music.activity.PlaylistTracks}: android.view.InflateException: Binary XML file line #31: Binary XML file line #31: Error inflating class android.support.design.widget.CollapsingToolbarLayout at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2416)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2476)
    at android.app.ActivityThread.-wrap11(ActivityThread.java) 
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1344) 
    at android.os.Handler.dispatchMessage(Handler.java:102) 
    at android.os.Looper.loop(Looper.java:148) 
    at android.app.ActivityThread.main(ActivityThread.java:5417) 
    at java.lang.reflect.Method.invoke(Native Method) 
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:726) 
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:616)
Caused by: java.lang.NoSuchMethodError: No static method setLayoutDirection(Landroid/graphics/drawable/Drawable;I)V in class Landroid/support/v4/graphics/drawable/DrawableCompat; or its super classes (declaration of 'android.support.v4.graphics.drawable.DrawableCompat' appears in /data/data/com.radioafrica.music/files/instant-run/dex/slice-com.android.support-support-v4-24.0.0-beta1_f8cf3ba4c70f87f407a745b9fa14a2205d0b587c-classes.dex) 
    at android.support.design.widget.CollapsingToolbarLayout.setStatusBarScrim(CollapsingToolbarLayout.java:663) 
    at android.support.design.widget.CollapsingToolbarLayout.<init>(CollapsingToolbarLayout.java:197) 
    at android.support.design.widget.CollapsingToolbarLayout.<init>(CollapsingToolbarLayout.java:132)                                                                         
    at java.lang.reflect.Constructor.newInstance(Native Method)                                                                          
    at android.view.LayoutInflater.createView(LayoutInflater.java:619)                                                                          
    at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:764)                                                                          
    at android.view.LayoutInflater.createViewFromTag(LayoutInflater.java:704)                                                                          
    at android.view.LayoutInflater.rInflate(LayoutInflater.java:835)                                                                          
    at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:798)                                                                          
    at android.view.LayoutInflater.rInflate(LayoutInflater.java:838)                                                                          
    at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:798)                                                                          
    at android.view.LayoutInflater.rInflate(LayoutInflater.java:838)                                                                          
    at android.view.LayoutInflater.rInflateChildren(LayoutInflater.java:798)                                                                          
    at android.view.LayoutInflater.inflate(LayoutInflater.java:515)                                                                         
    at android.view.LayoutInflater.inflate(LayoutInflater.java:423)                                                                          
    at android.view.LayoutInflater.inflate(LayoutInflater.java:374)                                                                          
    at android.support.v7.app.AppCompatDelegateImplV7.setContentView(AppCompatDelegateImplV7.java:280)                                                                          at android.support.v7.app.AppCompatActivity.setContentView(AppCompatActivity.java:140)

  I cant seem to find what the problem is...

The layout file is:

`

<android.support.design.widget.AppBarLayout
    android:id="@+id/app_bar_layout"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"
    android:fitsSystemWindows="true"
    android:theme="@style/ThemeOverlay.AppCompat.Dark.ActionBar">

    <android.support.design.widget.CollapsingToolbarLayout
        android:id="@+id/collapsing_toolbar"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:fitsSystemWindows="true"
        app:contentScrim="?attr/colorPrimary"
        app:expandedTitleMarginEnd="64dp"
        app:expandedTitleMarginStart="48dp"
        app:layout_scrollFlags="scroll|exitUntilCollapsed">

        <ImageView
            android:id="@+id/header"
            android:layout_width="match_parent"
            android:layout_height="280dip"
            android:fitsSystemWindows="true"
            android:scaleType="centerCrop"
            android:src="@drawable/no_cover"
            android:transitionName="avatar"
            app:layout_collapseMode="parallax" />

        <android.support.v7.widget.Toolbar
            android:id="@+id/toolbar"
            android:layout_width="match_parent"
            android:layout_height="?attr/actionBarSize"
            app:layout_collapseMode="pin"
            app:popupTheme="@style/ThemeOverlay.AppCompat.Light" />
    </android.support.design.widget.CollapsingToolbarLayout>
</android.support.design.widget.AppBarLayout>

<RelativeLayout
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    app:layout_behavior="@string/appbar_scrolling_view_behavior">

    <com.github.glomadrian.loadingballs.BallView
        android:id="@+id/ballView"
        android:layout_width="100dp"
        android:layout_height="100dp"
        android:layout_centerHorizontal="true"
        android:layout_gravity="center"
        android:layout_marginTop="150dip"
        lib:ball_colors="@array/color"
        lib:balls="5"
        lib:enable_size_animation="true"
        lib:max_ball_size="12dp"
        lib:min_ball_size="5dp"
        lib:movement_cycle_time="1500"
        lib:size_cycle_time="500" />

    <android.support.v4.widget.NestedScrollView
        android:id="@+id/nestedScrollView"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:clipToPadding="false"
        android:visibility="gone"
        app:layout_behavior="@string/appbar_scrolling_view_behavior">

        <LinearLayout
            android:layout_width="match_parent"
            android:layout_height="wrap_content"
            android:orientation="vertical">

            <android.support.v7.widget.CardView xmlns:android="http://schemas.android.com/apk/res/android"
                xmlns:card_view="http://schemas.android.com/apk/res-auto"
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                card_view:cardCornerRadius="0dip"
                card_view:cardElevation="2dip"
                card_view:cardPreventCornerOverlap="true">

                <LinearLayout
                    android:id="@+id/layout"
                    android:layout_width="match_parent"
                    android:layout_height="wrap_content"
                    android:orientation="vertical"
                    android:padding="10dip">

                    <TextView
                        android:id="@+id/name"
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:textAppearance="@style/TextAppearance.AppCompat.Large"
                        android:textColor="#fff"
                        android:layout_marginBottom="10dip"
                        android:textStyle="bold" />

                    <TextView
                        android:layout_width="wrap_content"
                        android:layout_height="wrap_content"
                        android:id="@+id/owner"
                        android:textAppearance="@style/TextAppearance.AppCompat.Medium"
                        android:textColor="#e2e2e2" />
                </LinearLayout>

            </android.support.v7.widget.CardView>

            <com.radioafrica.music.view.ExpandableHeightListView
                android:id="@+id/top_tracks"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:divider="#90ffffff"
                android:dividerHeight="1dip"
                android:focusable="false"
                android:footerDividersEnabled="true"
                android:headerDividersEnabled="true" />

        </LinearLayout>

    </android.support.v4.widget.NestedScrollView>

</RelativeLayout>

<android.support.design.widget.FloatingActionButton
    android:id="@+id/floatingPlayButton"
    style="@style/FabStyle"
    app:layout_anchor="@id/app_bar_layout"
    app:layout_anchorGravity="bottom|right|end" />

<include layout="@layout/mini_player" />

`

The code for the activity is:

public class AlbumInfo extends AppCompatActivity implements AdapterView.OnItemClickListener, View.OnClickListener {

public static final String ALBUM = "album";

private ExpandableHeightListView expandableHeightListView;
private NestedScrollView nestedScrollView;
private ImageView header;
private BallView ballView;
private LinearLayout layout;
private LinearLayout miniPlayer;
private TextView title, artistTextView;
private ImageButton playPause;
private ImageView artwork;
private CollapsingToolbarLayout collapsingToolbarLayout;

ImageButton previous;
ImageButton next;
TextView name;
TextView owner;
FloatingActionButton fab;

String songTitle;
String singer;
String art;
boolean playing = false;

private ArrayList<Track> trackList;
private Album album;

@Subscribe(threadMode = ThreadMode.MAIN)
public void onEvent(UIEvent uiEvent) {
    miniPlayer.setVisibility(View.VISIBLE);
    miniPlayer.setClickable(true);

    songTitle = uiEvent.title;
    singer = uiEvent.artist;
    art = uiEvent.art;
    playing = uiEvent.playing;

    togglePlayButtonState();

    updateViews();
}

private void updateViews() {
    Picasso.with(this).load(art).fit().centerCrop().placeholder(R.drawable.no_cover).error(R.drawable.no_cover).into(artwork);

    if (NakedGroove.getMediaType().equals(NakedGroove.RADIO)) {
        artistTextView.setText(Html.fromHtml(singer));
        title.setText(songTitle);
    } else {
        artistTextView.setText(singer);
        title.setText(songTitle);
    }
}

@Subscribe(threadMode = ThreadMode.MAIN)
public void onEvent(TracksEvent tracksEvent) {
    trackList = tracksEvent.tracks;

    if (trackList.size() != 0) {
        ArtistTracksAdapter artistTracksAdapter = new ArtistTracksAdapter(AlbumInfo.this, R.layout.album_tracks_layout, trackList);
        expandableHeightListView.setAdapter(artistTracksAdapter);

        if (ballView != null) {
            ballView.setVisibility(View.GONE);
            nestedScrollView.setVisibility(View.VISIBLE);
        }
    }
}

private Target target = new Target() {

    @Override
    public void onBitmapLoaded(Bitmap bitmap, Picasso.LoadedFrom from) {
        header.setImageBitmap(bitmap);
        setColors(bitmap);
    }

    @Override
    public void onBitmapFailed(Drawable errorDrawable) {
        Picasso.with(AlbumInfo.this).load(album.getAlbumArt()).into(target);
    }

    @Override
    public void onPrepareLoad(Drawable placeHolderDrawable) {
        Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.no_cover);
        header.setImageBitmap(bitmap);
        setColors(bitmap);
    }
};

@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
    initActivityTransitions();
    setStatusBarColor();

    super.onCreate(savedInstanceState);
    setContentView(R.layout.album);

    Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar);
    setSupportActionBar(toolbar);

    assert getSupportActionBar() != null;
    getSupportActionBar().setHomeButtonEnabled(true);
    getSupportActionBar().setDisplayHomeAsUpEnabled(true);

    album = getIntent().getParcelableExtra(ALBUM);

    fetchAlbumTracks(album.getId());

    expandableHeightListView = (ExpandableHeightListView) findViewById(R.id.top_tracks);
    nestedScrollView = (NestedScrollView) findViewById(R.id.nestedScrollView);
    header = (ImageView) findViewById(R.id.header);
    ballView = (BallView) findViewById(R.id.ballView);
    name = (TextView) findViewById(R.id.name);
    owner = (TextView) findViewById(R.id.owner);
    layout = (LinearLayout) findViewById(R.id.layout);
    fab = (FloatingActionButton) findViewById(R.id.floatingPlayButton);
    collapsingToolbarLayout = (CollapsingToolbarLayout) findViewById(R.id.collapsing_toolbar);

    title = (TextView) findViewById(R.id.title);
    artistTextView = (TextView) findViewById(R.id.artist);
    previous = (ImageButton) findViewById(R.id.notification_base_previous);
    playPause = (ImageButton) findViewById(R.id.notification_base_play);
    next = (ImageButton) findViewById(R.id.notification_base_next);
    artwork = (ImageView) findViewById(R.id.notification_base_image);
    miniPlayer = (LinearLayout) findViewById(R.id.mini_player);

    collapsingToolbarLayout.setTitle(album.getTitle());
    collapsingToolbarLayout.setExpandedTitleColor(getResources().getColor(android.R.color.transparent));

    owner.setText(album.getArtist());
    name.setText(album.getTitle());

    fab.setOnClickListener(this);
    fab.setRippleColor(getResources().getColor(R.color.app_theme_dark));

    miniPlayer.setOnClickListener(this);
    previous.setOnClickListener(this);
    next.setOnClickListener(this);
    playPause.setOnClickListener(this);

    expandableHeightListView.setExpanded(true);
    expandableHeightListView.setOnItemClickListener(this);

    if (album.getAlbumArt().length() != 0)
        Picasso.with(this).load(album.getAlbumArt()).into(target);
    else
        Picasso.with(this).load(R.drawable.no_cover).into(target);

    if (NakedGroove.isPlaying() || NakedGroove.isPaused()) {
        miniPlayer.setVisibility(View.VISIBLE);
        togglePlayButtonState();
    } else {
        miniPlayer.setVisibility(View.GONE);
    }
}

private void setStatusBarColor() {
    Window window = getWindow();
    if (Build.VERSION.SDK_INT >= 19 && Build.VERSION.SDK_INT < 21)
        window.setFlags(WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS, WindowManager.LayoutParams.FLAG_TRANSLUCENT_STATUS);
    if (Build.VERSION.SDK_INT >= 21)
        getWindow().setStatusBarColor(getResources().getColor(android.R.color.transparent));
}

private void fetchAlbumTracks(String id) {
    startService(new Intent(this, RefresherService.class).setAction(RefresherService.FETCH_ALBUM_TRACKS).putExtra(RefresherService.ALBUM_ID, id));
}

@Override
public boolean onOptionsItemSelected(MenuItem item) {
    switch (item.getItemId()) {
        case android.R.id.home:
            super.onBackPressed();
            return true;
        default:
            return super.onOptionsItemSelected(item);
    }
}

@Override
public void onPause() {
    super.onPause();
}

@Override
protected void onResume() {
    super.onResume();

    togglePlayButtonState();

    if (NakedGroove.getMediaType() != null && !NakedGroove.getMediaType().equals(NakedGroove.NOTHING)) {
        updateViews();
    }
}

@Override
public void onSaveInstanceState(Bundle outState) {
    super.onSaveInstanceState(outState);
    outState.putString(ALBUM, album.getTitle());
}

@Override
public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
    NakedGroove.setCurrentPlaylist(trackList);
    NakedGroove.setCurrentIndex(position);

    if (Build.VERSION.SDK_INT >= 16)
        startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_URL));
    else
        startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_URL));
}

private void playPauseMusic() {
    if (NakedGroove.isPlaying()) {
        if (Build.VERSION.SDK_INT >= 16)
            startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_PAUSE));
        else
            startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_PAUSE));
    } else {
        if (Build.VERSION.SDK_INT >= 16)
            startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_PLAY));
        else
            startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_PLAY));
    }
}

@Override
public void onClick(View view) {
    switch (view.getId()) {
        case R.id.mini_player:
            startActivity(new Intent(this, MusicPlayer.class));
            break;
        case R.id.notification_base_play:
            playPauseMusic();
            break;
        case R.id.notification_base_next:
            if (Build.VERSION.SDK_INT >= 16)
                startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_SKIP));
            else
                startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_SKIP));
            break;
        case R.id.notification_base_previous:
            if (Build.VERSION.SDK_INT >= 16)
                startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_PREVIOUS));
            else
                startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_PREVIOUS));
            break;
        case R.id.floatingPlayButton:
            if (trackList.size() != 0) {
                NakedGroove.setCurrentPlaylist(trackList);
                NakedGroove.setCurrentIndex(0);

                if (Build.VERSION.SDK_INT >= 16)
                    startService(new Intent(this, PlayerService.class).setAction(PlayerService.ACTION_URL));
                else
                    startService(new Intent(this, MusicService.class).setAction(MusicService.ACTION_URL));
            }
            break;
    }
}

private void togglePlayButtonState() {
    if (playing) {
        playPause.setImageResource(R.drawable.ic_music_pause);
    } else {
        playPause.setImageResource(R.drawable.ic_music_play);
    }
}

private void initActivityTransitions() {
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
        ChangeBounds transition = new ChangeBounds();
        transition.excludeTarget(android.R.id.statusBarBackground, true);
        getWindow().setEnterTransition(transition);
        getWindow().setReturnTransition(transition);
    }
}

@Override
protected void attachBaseContext(Context newBase) {
    super.attachBaseContext(CalligraphyContextWrapper.wrap(newBase));
}

@Override
protected void onStart() {
    super.onStart();
    EventBus.getDefault().register(this);
}

@Override
protected void onStop() {
    EventBus.getDefault().unregister(this);
    super.onStop();
}

private void setColors(Bitmap bitmap) {
    Palette.from(bitmap).generate(new Palette.PaletteAsyncListener() {
        @Override
        public void onGenerated(Palette palette) {
            if (palette.getVibrantSwatch() != null) {
                Palette.Swatch vibrantSwatch = palette.getVibrantSwatch();
                float[] vibrant = vibrantSwatch.getHsl();

                nestedScrollView.setBackgroundColor(Color.HSVToColor(vibrant));
                layout.setBackgroundColor(Color.HSVToColor(vibrant));
                collapsingToolbarLayout.setContentScrimColor(Color.HSVToColor(vibrant));
                collapsingToolbarLayout.setStatusBarScrimColor(Color.HSVToColor(vibrant));
            } else if (palette.getDarkVibrantSwatch() != null) {
                Palette.Swatch darkVibrantSwatch = palette.getDarkVibrantSwatch();
                float[] darkVibrant = darkVibrantSwatch.getHsl();

                nestedScrollView.setBackgroundColor(Color.HSVToColor(darkVibrant));
                layout.setBackgroundColor(Color.HSVToColor(darkVibrant));
                collapsingToolbarLayout.setContentScrimColor(Color.HSVToColor(darkVibrant));
                collapsingToolbarLayout.setStatusBarScrimColor(Color.HSVToColor(darkVibrant));
            } else if (palette.getDarkMutedSwatch() != null) {
                Palette.Swatch darkMutedSwatch = palette.getDarkMutedSwatch();
                float[] darkMuted = darkMutedSwatch.getHsl();

                nestedScrollView.setBackgroundColor(Color.HSVToColor(darkMuted));
                layout.setBackgroundColor(Color.HSVToColor(darkMuted));
                collapsingToolbarLayout.setContentScrimColor(Color.HSVToColor(darkMuted));
                collapsingToolbarLayout.setStatusBarScrimColor(Color.HSVToColor(darkMuted));
            } else {
                nestedScrollView.setBackgroundColor(getResources().getColor(R.color.DeepGrey));
                layout.setBackgroundColor(getResources().getColor(R.color.DeepGrey));
                collapsingToolbarLayout.setContentScrimColor(getResources().getColor(R.color.DeepGrey));
                collapsingToolbarLayout.setStatusBarScrimColor(getResources().getColor(R.color.DeepGrey));
            }

            supportStartPostponedEnterTransition();
        }
    });
}

}

回答1:

I answered a similar post here Error inflating class CollapsingToolbarLayout

I know there is an accepted answer already, BUT it is not working (or no longer working).

I spend a couple of hours researching on this error, what I came up is this.

First, due to initial release of Android Nougat also known as Android 7.0 (API 24) compileSdkVersion 24 is now available. To do that you have to update your sdk. Step 1

Second, is to update your gradle files (internet connection required). Step 2

Also Update this part of app.gradle

Third (optional) Clean Project, Build Project (Both under Build Tab)

I hope this help someone out there and save some few hours of researching.

Cheers / Happy coding

Hope it helps.



回答2:

Found solution. Just add

app:statusBarScrim="@null"

to your CollapsingToolbarLayout



回答3:

Turns out I had another dependency that had a conflicting support library. When i removed the dependency, the project built and ran successfully.



回答4:

Try updating all of your support libraries to the 24.0.0-beta1 version. Then clean, rebuild and run your project again. That hopefully should fix your problem.



回答5:

Try updating a com.android.support:design dependency to the same version as other support libraries. I have just resolved this issue in my own project. I did not add it explicitly in my build.gradle since I use a library which uses support-design library. Gradle task androidDependencies showed that support design still had lower version after update of other libraries, so I added it explicitly and it worked like a charm.