how to implement cube Transition effect animation on ViewPager in android?

16,137

Solution 1

Check out here

Snapshot:

enter image description here

There you can see the library and related source codes.

MainActivity.java:

package com.ToxicBakery.viewpager.transforms.example;

import java.util.ArrayList;

import android.app.ActionBar;
import android.app.ActionBar.OnNavigationListener;
import android.app.Activity;
import android.app.Fragment;
import android.app.FragmentManager;
import android.os.Bundle;
import android.support.v13.app.FragmentStatePagerAdapter;
import android.support.v4.view.ViewPager;
import android.support.v4.view.ViewPager.PageTransformer;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.TextView;

import com.ToxicBakery.viewpager.transforms.AccordionTransformer;
import com.ToxicBakery.viewpager.transforms.BackgroundToForegroundTransformer;
import com.ToxicBakery.viewpager.transforms.CubeInTransformer;
import com.ToxicBakery.viewpager.transforms.CubeOutTransformer;
import com.ToxicBakery.viewpager.transforms.DefaultTransformer;
import com.ToxicBakery.viewpager.transforms.DepthPageTransformer;
import com.ToxicBakery.viewpager.transforms.FlipHorizontalTransformer;
import com.ToxicBakery.viewpager.transforms.FlipVerticalTransformer;
import com.ToxicBakery.viewpager.transforms.ForegroundToBackgroundTransformer;
import com.ToxicBakery.viewpager.transforms.RotateDownTransformer;
import com.ToxicBakery.viewpager.transforms.RotateUpTransformer;
import com.ToxicBakery.viewpager.transforms.StackTransformer;
import com.ToxicBakery.viewpager.transforms.TabletTransformer;
import com.ToxicBakery.viewpager.transforms.ZoomInTransformer;
import com.ToxicBakery.viewpager.transforms.ZoomOutSlideTransformer;
import com.ToxicBakery.viewpager.transforms.ZoomOutTranformer;
import com.ToxicBakery.viewpager.transforms.example.R;

public class MainActivity extends Activity implements OnNavigationListener {

    private static final String KEY_SELECTED_PAGE = "KEY_SELECTED_PAGE";
    private static final String KEY_SELECTED_CLASS = "KEY_SELECTED_CLASS";
    private static final ArrayList<TransformerItem> TRANSFORM_CLASSES;

    static {
        TRANSFORM_CLASSES = new ArrayList<TransformerItem>();
        TRANSFORM_CLASSES.add(new TransformerItem(DefaultTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(AccordionTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(BackgroundToForegroundTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(CubeInTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(CubeOutTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(DepthPageTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(FlipHorizontalTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(FlipVerticalTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(ForegroundToBackgroundTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(RotateDownTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(RotateUpTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(StackTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(TabletTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(ZoomInTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(ZoomOutSlideTransformer.class));
        TRANSFORM_CLASSES.add(new TransformerItem(ZoomOutTranformer.class));
    }

    private int mSelectedItem;
    private ViewPager mPager;
    private PageAdapter mAdapter;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        int selectedPage = 0;
        if (savedInstanceState != null) {
            mSelectedItem = savedInstanceState.getInt(KEY_SELECTED_CLASS);
            selectedPage = savedInstanceState.getInt(KEY_SELECTED_PAGE);
        }

        final ArrayAdapter<TransformerItem> actionBarAdapter = new ArrayAdapter<TransformerItem>(
                getApplicationContext(), android.R.layout.simple_list_item_1, android.R.id.text1, TRANSFORM_CLASSES);

        final ActionBar actionBar = getActionBar();
        actionBar.setListNavigationCallbacks(actionBarAdapter, this);
        actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_LIST);

        //noinspection ResourceType
        actionBar.setDisplayOptions(actionBar.getDisplayOptions() ^ ActionBar.DISPLAY_SHOW_TITLE);

        setContentView(R.layout.activity_main);

        mAdapter = new PageAdapter(getFragmentManager());

        mPager = (ViewPager) findViewById(R.id.container);
        mPager.setAdapter(mAdapter);
        mPager.setCurrentItem(selectedPage);

        actionBar.setSelectedNavigationItem(mSelectedItem);
    }

    @Override
    public boolean onNavigationItemSelected(int position, long itemId) {
        mSelectedItem = position;
        try {
            mPager.setPageTransformer(true, TRANSFORM_CLASSES.get(position).clazz.newInstance());
        } catch (Exception e) {
            throw new RuntimeException(e);
        }

        return true;
    }

    protected void onSaveInstanceState(Bundle outState) {
        outState.putInt(KEY_SELECTED_CLASS, mSelectedItem);
        outState.putInt(KEY_SELECTED_PAGE, mPager.getCurrentItem());
    }

    public static class PlaceholderFragment extends Fragment {

        private static final String EXTRA_POSITION = "EXTRA_POSITION";
        private static final int[] COLORS = new int[] { 0xFF33B5E5, 0xFFAA66CC, 0xFF99CC00, 0xFFFFBB33, 0xFFFF4444 };

        @Override
        public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
            final int position = getArguments().getInt(EXTRA_POSITION);
            final TextView textViewPosition = (TextView) inflater.inflate(R.layout.fragment_main, container, false);
            textViewPosition.setText(Integer.toString(position));
            textViewPosition.setBackgroundColor(COLORS[position - 1]);

            return textViewPosition;
        }

    }

    private static final class PageAdapter extends FragmentStatePagerAdapter {

        public PageAdapter(FragmentManager fragmentManager) {
            super(fragmentManager);
        }

        @Override
        public Fragment getItem(int position) {
            final Bundle bundle = new Bundle();
            bundle.putInt(PlaceholderFragment.EXTRA_POSITION, position + 1);

            final PlaceholderFragment fragment = new PlaceholderFragment();
            fragment.setArguments(bundle);

            return fragment;
        }

        @Override
        public int getCount() {
            return 5;
        }

    }

    private static final class TransformerItem {

        final String title;
        final Class<? extends PageTransformer> clazz;

        public TransformerItem(Class<? extends PageTransformer> clazz) {
            this.clazz = clazz;
            title = clazz.getSimpleName();
        }

        @Override
        public String toString() {
            return title;
        }

    }

}

Solution 2

I've written a ViewPager.PageTransformer specifically just for the Cube Transformation Effect.

Feel free to adjust the deltaY to fine tune your vertical transformation. Cheers mate.

https://gist.github.com/delacrixmorgan/6b05ab74d1acb01b471fcc3151d70703

Solution 3

This is Morgan Koh's answer but in Java and using ViewPager2.

position is the distance betweeen the seam (between the two panels displayed) and the edge of the screen. (This fires many times as you drag the seam across.)

public class CubeTransformer implements ViewPager2.PageTransformer {
    @Override
    public void transformPage(@NonNull View page, float position) {
        float deltaY = 0.5f;
        float pivotX = position < 0f ? page.getWidth() : 0f;
        float pivotY = page.getHeight() * deltaY;
        float rotationY = 45f * position;

        page.setPivotX(pivotX);
        page.setPivotY(pivotY);
        page.setRotationY(rotationY);
    }
}

And then in your activity:

ViewPager2 vp = findViewById(R.id.swipe_frame);
vp.setAdapter(new SwipeAdapter());
vp.setPageTransformer(new CubeTransformer());
Share:
16,137
Ashish Wadatkar
Author by

Ashish Wadatkar

Updated on June 17, 2022

Comments

  • Ashish Wadatkar
    Ashish Wadatkar almost 2 years

    I want to implement cube Transition effect animation in Android View Pager.

    can anyone have an idea about cube animation in android.

    enter image description here

    Image is attached for example.

  • Bala Saikrupa Puram
    Bala Saikrupa Puram over 8 years
    how to use this library can you help me.
  • Steve
    Steve over 8 years
    @saikrupa download and import that sample in studio.Then check what are the things you need to add it in your real time project.
  • Bala Saikrupa Puram
    Bala Saikrupa Puram over 8 years
    is this a library or some sample project
  • Pinkesh Darji
    Pinkesh Darji over 6 years
    How to do this between two activities?
  • Morgan Koh
    Morgan Koh about 6 years
    Just visit their GitHub Repo on this, ToxicBakery. github.com/ToxicBakery/ViewPagerTransforms
  • Rishabh Saxena
    Rishabh Saxena almost 6 years
    HI there is extra spacing while transformation , can you please help me in modifying this? @DelacrixMorgan
  • Morgan Koh
    Morgan Koh over 5 years
    @RishabhSaxena I've created a gist down below for you to fine tune your Cube Transformation.
  • Rishabh Saxena
    Rishabh Saxena over 5 years
    @DelacrixMorgan Thanks :)
  • SammyT
    SammyT over 4 years
    @Luffy I have 4 screens, it would be great if it just kept paging (infinite scroll) ie 1 --> 2 --> 3 --> 4 --> 1 and have the animation keep going in the correct direction. Also have it working in both directions ie. 1 backwards to 4. I can get the scrolling working, just not the animation.