content: package com.alexjlockwood.activity.transitions;
  
  import android.app.Activity;
  import android.app.ActivityOptions;
  import android.app.SharedElementCallback;
  import android.content.Intent;
  import android.os.Bundle;
  import android.support.v7.widget.GridLayoutManager;
  import android.support.v7.widget.RecyclerView;
  import android.view.LayoutInflater;
  import android.view.View;
  import android.view.ViewGroup;
  import android.view.ViewTreeObserver;
  import android.widget.ImageView;
  
  import com.squareup.picasso.Picasso;
  
  import java.util.List;
  import java.util.Map;
  
  import static com.alexjlockwood.activity.transitions.Constants.ALBUM_IMAGE_URLS;
  import static com.alexjlockwood.activity.transitions.Constants.ALBUM_NAMES;
  
  public class MainActivity extends Activity {
      private static final String TAG = MainActivity.class.getSimpleName();
      private static final boolean DEBUG = false;
  
      static final String EXTRA_STARTING_ALBUM_POSITION = "extra_starting_item_position";
      static final String EXTRA_CURRENT_ALBUM_POSITION = "extra_current_item_position";
  
      private RecyclerView mRecyclerView;
      private Bundle mTmpReenterState;
      private boolean mIsDetailsActivityStarted;
  
      private final SharedElementCallback mCallback = new SharedElementCallback() {
          @Override
          public void onMapSharedElements(List<String> names, Map<String, View> sharedElements) {
              if (mTmpReenterState != null) {
                  int startingPosition = mTmpReenterState.getInt(EXTRA_STARTING_ALBUM_POSITION);
                  int currentPosition = mTmpReenterState.getInt(EXTRA_CURRENT_ALBUM_POSITION);
                  if (startingPosition != currentPosition) {
                      // If startingPosition != currentPosition the user must have swiped to a
                      // different page in the DetailsActivity. We must update the shared element
                      // so that the correct one falls into place.
                      String newTransitionName = ALBUM_NAMES[currentPosition];
                      View newSharedElement = mRecyclerView.findViewWithTag(newTransitionName);
                      if (newSharedElement != null) {
                          names.clear();
                          names.add(newTransitionName);
                          sharedElements.clear();
                          sharedElements.put(newTransitionName, newSharedElement);
                      }
                  }
  
                  mTmpReenterState = null;
              } else {
                  // If mTmpReenterState is null, then the activity is exiting.
                  View navigationBar = findViewById(android.R.id.navigationBarBackground);
                  View statusBar = findViewById(android.R.id.statusBarBackground);
                  if (navigationBar != null) {
                      names.add(navigationBar.getTransitionName());
                      sharedElements.put(navigationBar.getTransitionName(), navigationBar);
                  }
                  if (statusBar != null) {
                      names.add(statusBar.getTransitionName());
                      sharedElements.put(statusBar.getTransitionName(), statusBar);
                  }
              }
          }
      };
  
      @Override
      protected void onCreate(Bundle savedInstanceState) {
          super.onCreate(savedInstanceState);
          setContentView(R.layout.activity_main);
          setExitSharedElementCallback(mCallback);
  
          mRecyclerView = (RecyclerView) findViewById(R.id.recycler_view);
          mRecyclerView.setLayoutManager(new GridLayoutManager(this,
                  getResources().getInteger(R.integer.activity_main_num_grid_columns)));
          mRecyclerView.setAdapter(new CardAdapter());
      }
  
      @Override
      protected void onResume() {
          super.onResume();
          mIsDetailsActivityStarted = false;
      }
  
      @Override
      public void onActivityReenter(int requestCode, Intent data) {
          super.onActivityReenter(requestCode, data);
          mTmpReenterState = new Bundle(data.getExtras());
          int startingPosition = mTmpReenterState.getInt(EXTRA_STARTING_ALBUM_POSITION);
          int currentPosition = mTmpReenterState.getInt(EXTRA_CURRENT_ALBUM_POSITION);
          if (startingPosition != currentPosition) {
              mRecyclerView.scrollToPosition(currentPosition);
          }
          postponeEnterTransition();
          mRecyclerView.getViewTreeObserver().addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
              @Override
              public boolean onPreDraw() {
                  mRecyclerView.getViewTreeObserver().removeOnPreDrawListener(this);
                  // TODO: figure out why it is necessary to request layout here in order to get a smooth transition.
                  mRecyclerView.requestLayout();
                  startPostponedEnterTransition();
                  return true;
              }
          });
      }
  
      private class CardAdapter extends RecyclerView.Adapter<CardHolder> {
          private final LayoutInflater mInflater;
  
          public CardAdapter() {
              mInflater = LayoutInflater.from(MainActivity.this);
          }
  
          @Override
          public CardHolder onCreateViewHolder(ViewGroup viewGroup, int viewType) {
              return new CardHolder(mInflater.inflate(R.layout.album_image_card, viewGroup, false));
          }
  
          @Override
          public void onBindViewHolder(CardHolder holder, int position) {
              holder.bind(position);
          }
  
          @Override
          public int getItemCount() {
              return ALBUM_IMAGE_URLS.length;
          }
      }
  
      private class CardHolder extends RecyclerView.ViewHolder implements View.OnClickListener {
          private final ImageView mAlbumImage;
          private int mAlbumPosition;
  
          public CardHolder(View itemView) {
              super(itemView);
              itemView.setOnClickListener(this);
              mAlbumImage = (ImageView) itemView.findViewById(R.id.main_card_album_image);
          }
  
          public void bind(int position) {
              Picasso.with(MainActivity.this).load(ALBUM_IMAGE_URLS[position]).into(mAlbumImage);
              mAlbumImage.setTransitionName(ALBUM_NAMES[position]);
              mAlbumImage.setTag(ALBUM_NAMES[position]);
              mAlbumPosition = position;
          }
  
          @Override
          public void onClick(View v) {
              // TODO: is there a way to prevent user from double clicking and starting activity twice?
              Intent intent = new Intent(MainActivity.this, DetailsActivity.class);
              intent.putExtra(EXTRA_STARTING_ALBUM_POSITION, mAlbumPosition);
  
              if (!mIsDetailsActivityStarted) {
                  mIsDetailsActivityStarted = true;
                  startActivity(intent, ActivityOptions.makeSceneTransitionAnimation(MainActivity.this,
                          mAlbumImage, mAlbumImage.getTransitionName()).toBundle());
              }
          }
      }
  }
  