Java tutorial
/* * Copyright 2015 GDG Minsk * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package by.gdgminsk.animationguide; import android.content.Intent; import android.content.res.Configuration; import android.os.Build; import android.os.Bundle; import android.support.design.widget.AppBarLayout; import android.support.v4.view.ViewCompat; import android.support.v7.app.ActionBar; import android.support.v7.widget.RecyclerView; import android.support.v7.widget.Toolbar; import android.transition.CircularPropagation; import android.transition.Explode; import android.util.Log; import android.view.View; import android.widget.ImageView; import com.squareup.picasso.Callback; import com.squareup.picasso.Picasso; import by.gdgminsk.animationguide.adapter.ContactDetailsAdapter; import by.gdgminsk.animationguide.data.Contact; import by.gdgminsk.animationguide.util.AnimUtils; import by.gdgminsk.animationguide.widget.ObservableCollapsingToolbarLayout; public class ContactDetailsActivity extends BaseActivity { private static final String LOG_TAG = "ContactDetailsActivity"; public static final String EXTRA_CONTACT = "contact"; private static final String KEY_INITIAL_ORIENTATION = "initial_orientation"; private View mOverlay; private AppBarLayout mAppBarLayout; private ImageView mPhotoView; private int mCurrentOrientation; private int mInitialOrientation; private float mCurrentCollapsingRate; private final View.OnClickListener mPhotoClickListener = new View.OnClickListener() { @Override public void onClick(View v) { mAppBarLayout.setExpanded(mCurrentCollapsingRate != 0); } }; private final ObservableCollapsingToolbarLayout.OnScrollListener mOnScrollListener = new ObservableCollapsingToolbarLayout.OnScrollListener() { @Override public void onScroll(float collapsingRate, ObservableCollapsingToolbarLayout.ScrollDirection direction) { mCurrentCollapsingRate = collapsingRate; if (collapsingRate < 0.5) { mOverlay.setVisibility(View.GONE); } else { mOverlay.setVisibility(View.VISIBLE); mOverlay.setAlpha(2 * collapsingRate - 1); } } }; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP && getResources().getBoolean(R.bool.translucent_status)) { int flags = View.SYSTEM_UI_FLAG_LAYOUT_STABLE | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN; getWindow().getDecorView().setSystemUiVisibility(flags); } setContentView(R.layout.activity_contact_details); mCurrentOrientation = getResources().getConfiguration().orientation; boolean land = mCurrentOrientation == Configuration.ORIENTATION_LANDSCAPE; if (savedInstanceState == null) { mInitialOrientation = mCurrentOrientation; } else { mInitialOrientation = savedInstanceState.getInt(KEY_INITIAL_ORIENTATION); } Toolbar toolbar = (Toolbar) findViewById(R.id.toolbar); setSupportActionBar(toolbar); ActionBar ab = getSupportActionBar(); // getSupportActionBar() can't return null here because we set it one row above //noinspection ConstantConditions ab.setDisplayHomeAsUpEnabled(true); Intent intent = getIntent(); Contact contact = intent.getParcelableExtra(EXTRA_CONTACT); if (contact == null) { Log.e(LOG_TAG, "contact is not provided"); finish(); return; } mAppBarLayout = (AppBarLayout) findViewById(R.id.app_bar); mOverlay = findViewById(R.id.overlay); mPhotoView = (ImageView) findViewById(R.id.contact_photo); RecyclerView detailsList = (RecyclerView) findViewById(R.id.details_list); detailsList.setAdapter(new ContactDetailsAdapter(contact, this)); if (!land) { ObservableCollapsingToolbarLayout collapsingToolbar = (ObservableCollapsingToolbarLayout) findViewById( R.id.toolbar_layout); collapsingToolbar.setOnScrollListener(mOnScrollListener); mPhotoView.setOnClickListener(mPhotoClickListener); } ab.setTitle(contact.getName()); loadPhoto(contact); } @Override protected void onSaveInstanceState(Bundle outState) { super.onSaveInstanceState(outState); outState.putInt(KEY_INITIAL_ORIENTATION, mInitialOrientation); } @Override public boolean onSupportNavigateUp() { exit(); return true; } @Override public void onBackPressed() { exit(); } private void loadPhoto(final Contact contact) { Picasso.with(this).load(contact.getPhotoPreview()).noFade().into(mPhotoView, new Callback() { @Override public void onSuccess() { Picasso.with(ContactDetailsActivity.this).load(contact.getPhoto()).noFade().noPlaceholder() .into(mPhotoView); } @Override public void onError() { Log.e(LOG_TAG, "Unable to load image for contact = " + contact); } }); } private void exit() { if (mInitialOrientation != mCurrentOrientation || mCurrentCollapsingRate > 0.9f) { // remove tranistion name on exit to let activity explode insted of playing // reverse shared element animation. Better override return transition and // not to play shared element back because if returning activity recreated // there is a glitch because the end coordinate of shared element may not exist ViewCompat.setTransitionName(mPhotoView, null); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { Explode transition = new Explode(); transition.setPropagation(new CircularPropagation()); transition.setDuration(getResources().getInteger(R.integer.duration_explode)); transition.setInterpolator(AnimUtils.EASE_OUT_INTERPOLATOR); getWindow().setReturnTransition(transition); } } supportFinishAfterTransition(); } }