Futureproof
Futureproof

Reputation: 375

Shared Element Transition issue between two Activities

I'm having issues creating a basic shared element transition. The transition from one activity to the next seems to glitch and reproduce the first activity instead of the resulting activity.

Overview:

I have two activities: A MainActivity and a DetailActivity.

MainActivity hosts a RecyclerView with a CardView layout. The onclicklistener for each cardview position set an object as an intent extra, and starts the DetailActivity. This basic implementation works so far.

Problem:

Now I'm trying to introduce a shared element transition into the mix:

Original: (works without the transition animation)

public void onObjectClick(View v, int position) {
    Word detailWord = mRepository.getWord(position);
    Intent i = new Intent(mContext, DetailActivity.class);
    i.putExtra(WORD_OBJECT, detailWord);
     //animateTransition(v,i);  -doesn't work
    mContext.startActivity(i);

Problem Method:

private void animateTransition(View view, Intent intent){
        String transitionName = mContext.getString(R.string.transition_word);
        ActivityOptionsCompat options = ActivityOptionsCompat
                .makeSceneTransitionAnimation(
                        baseView.getActivity()
                        ,view
                        ,transitionName
                );
        mContext.startActivity(
                intent
                ,options.toBundle());
    }

When I uncomment the animateTransition(v,i) method from the above click-method, I get some strange behavior: The MainActivity fades out as it should by default, but then comes back into view. The DetailActivity still loads from the intent but is invisible. Pressing the back button appears to do nothing (still seeing MainActivity) but it stops the DetailActivity.

So far, I've done the following to hook all of this up:

Card_view_layout.xml

<?xml version="1.0" encoding="utf-8"?>
<android.support.v7.widget.CardView
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:id="@+id/card_view"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:layout_margin="4dp"
    android:onClick="animateIntent"
    android:clickable="true"
    android:transitionName="@string/transition_word"
>

detail_activity.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent"
    android:layout_height="match_parent" android:paddingLeft="@dimen/activity_horizontal_margin"
    android:paddingRight="@dimen/activity_horizontal_margin"
    android:paddingTop="@dimen/activity_vertical_margin"
    android:paddingBottom="@dimen/activity_vertical_margin" tools:context=".DetailActivity"
    android:transitionName="@string/transition_word">

Upvotes: 3

Views: 4366

Answers (2)

Futureproof
Futureproof

Reputation: 375

The issue was how the activity backstack was declared in the android manifest. First of all, the parent and child activities must be declared for proper back-navigation:

<activity
        android:name=".ui.activity.HomeActivity"
        android:label="@string/app_name" >
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />
            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
    <activity android:name=".ui.activity.DetailActivity"
        android:launchMode="singleTask"
        android:parentActivityName=".ui.activity.HomeActivity"
        android:label="@string/app_name">
        <meta-data
            android:name="android.support.PARENT_ACTIVITY"
            android:value="ui.activity.HomeActivity"/>
</activity>

Second, the child activity must have a launch mode of "singleTask". I had previously set this as "singleInstance". The difference is that the latter is always the only member of it's task. If you minimize your application while on this child fragment and resume it later, the back button won't remember your parent activity.

Both parent activity navigation and sceneTransitionAnimation work with a singleTask launchMode attribute.

Upvotes: 3

Ashish Agrawal
Ashish Agrawal

Reputation: 1977

Please try with this

 private void animateTransition(View view, Intent intent){
 String transitionName = mContext.getString(R.string.transition_word);      
        Pair<View, String> pair = Pair.create((View) view, transitionName);

        ActivityOptionsCompat options = ActivityOptionsCompat
                .makeSceneTransitionAnimation(
                        MainActivity.this
                        ,pair
                );
        mContext.startActivity(
                intent
                ,options.toBundle());
    }

Upvotes: 1

Related Questions