Я пытаюсь выполнить переход общих элементов Android 5.0 в ситуации Master Detail из ListView. Я отправляю изображение.
Я столкнулся с ошибкой при переходе входа, когда изображение вообще не перемещается, пока происходит переход основного действия. После загрузки действия Detail изображение запускается в верхнем левом углу экрана и анимируется в его окончательном месте. Обратный переход работает отлично - изображение анимируется из своего детального положения в правильное положение в мастере.
Вот как это выглядит: https://www.youtube.com/watch?v=AzyA8i27qWc < / а>
Я считаю, что правильно настроил разрешения и указал переход:
<item name="android:windowContentTransitions">true</item>
<item name="android:windowAllowEnterTransitionOverlap">true</item>
<item name="android:windowAllowReturnTransitionOverlap">true</item>
<!-- specify shared element transitions -->
<item name="android:windowSharedElementEnterTransition">
@transition/change_image_transform</item>
<item name="android:windowSharedElementExitTransition">
@transition/change_image_transform</item>
Этот переход определяется как:
<transitionSet xmlns:android="http://schemas.android.com/apk/res/android">
<changeImageTransform/>
<changeBounds/>
<changeTransform/>
</transitionSet>
Я дал двум представлениям один и тот же уникальный атрибут transitionName в зависимости от их позиции в списке.
Я использую makeSceneTransitionAnimation для анимации:
View photo = (View) adapter.getView(position, null, listView).findViewById(R.id.photo);
View navigationBar = findViewById(android.R.id.navigationBarBackground);
ActivityOptions options = ActivityOptions.makeSceneTransitionAnimation(this,
Pair.create(photo, photo.getTransitionName()),
Pair.create(navigationBar, Window.NAVIGATION_BAR_BACKGROUND_TRANSITION_NAME));
Bundle extras = new Bundle();
Patient selectedPatient = patientList.get(position);
extras.putParcelable("patient", selectedPatient);
extras.putInt("position", position);
Intent intent = new Intent(PatientListActivity.this, PatientActivity_.class);
intent.putExtras(extras);
startActivity(intent, options.toBundle());
(Я также указываю навигационную панель как общую, чтобы она не исчезла, что отлично работает)
Я не понимаю, почему обратный переход работает нормально, а входной - нет. Я видел и другие вопросы, решение которых заключалось в том, чтобы отложить переход на вход, что я пытался сделать, но проблема осталась. Вот что я добавил к onCreate в моем действии Detail:
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_patient);
patient = getIntent().getExtras().getParcelable("patient");
patient = app.getPatientByName(patient.getName());
patientPhotoView.setImageDrawable(patient.getPhoto());
/* Set up transition functionality */
position = getIntent().getExtras().getInt("position");
patientPhotoView.setTransitionName("patientPhoto" + position);
patientNameView.setTransitionName("patientName" + position);
postponeEnterTransition();
final ViewTreeObserver observer = getWindow().getDecorView().getViewTreeObserver();
observer.addOnPreDrawListener(new ViewTreeObserver.OnPreDrawListener() {
@Override
public boolean onPreDraw() {
final ViewTreeObserver observer = getWindow().getDecorView().getViewTreeObserver();
observer.removeOnPreDrawListener(this);
startPostponedEnterTransition();
return true;
}
});
В моем действии Detail нет элемента transitionName, но я устанавливаю его в коде. Соответствующая часть входящей активности (Деталь):
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/drawer_layout"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".PatientActivity">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="200dip"
android:orientation="vertical"
android:id="@+id/patient_top_layout">
<ImageView
android:id="@+id/patientPhoto"
android:layout_width="92dip"
android:layout_height="92dip"
android:layout_below="@+id/connectionBar"
android:layout_marginRight="12dip"
android:layout_marginTop="12dip"
android:contentDescription="Patient photo"
android:src="@drawable/ic_profile_default" />
</RelativeLayout>
</LinearLayout>
</RelativeLayout
Рад разместить другой соответствующий код. Любые идеи?
Решено
Пользователь Chris P с + страницы Android Development понял это для меня. В моем основном действии в методе onClick у меня было:
View photo = (View) adapter.getView(position, null, listView).findViewById(R.id.photo);
Решением было заменить эту строку на:
View photo = (View) listView.getChildAt(position).findViewById(R.id.photo);
Я предполагаю, что вызов метода getView адаптера был воссозданием самого представления - я предполагаю, что этот метод должен вызываться ТОЛЬКО при первом создании списка.
@transition/change_image_transform
на@transition/change_image_transform
? Есть ли разница, если вы изменитеgetWindow().getDecorView()
на объектImageView
совместно используемого элемента? - person Alex Lockwood   schedule 05.03.2015getWindow().getDecorView()
наpatientPhotoView
(после установки названия перехода и фотографии). - person clay_to_n   schedule 05.03.2015@transition/change_image_transform
на@android:transition/move
? - person Alex Lockwood   schedule 05.03.2015