0

共有要素として画像を使用して、2 つのアクティビティ間にアニメーションを作成したいです。「アクティビティの遷移をカスタマイズする」を参照してください。

私の問題: ソース アクティビティでは、カスタム ビューのキャンバスに画像が描画されます :-(

この画像を共有要素として使用する方法はありますか、それとも実際の ImageView を追加する必要がありますか?

4

1 に答える 1

1

画像のみを共有することはできませんが、カスタム ビュー全体を共有できます。これは、共有要素が起動されたアクティビティに転送されると、呼び出し元のアクティビティからカスタム ビュー全体が消えることを意味します。カスタム ビューに画像しかない場合は問題ありませんが、他のものを描画する場合は悲惨です。

画像のみを共有したい場合は、View (ImageView など) を作成し、そこに画像を移動してから共有する必要があります。そうすれば、共有要素が転送されると、呼び出し元のアクティビティから適切に隠されます。

共有要素は、実際にはビューをアクティビティ間で移動しません。ビューの「スナップショット」をビットマップとして共有し、ビューの位置を共有するだけです。起動されたアクティビティでは、指定された遷移名を持つビューがその位置に配置されます。必要に応じて、スナップショットを使用することも使用しないこともできます。デフォルトでは、スナップショットは使用されません。

したがって、次のようなコードが必要になります。

public void launchActivity(final Intent intent, final CustomView view) {
    final Bitmap bitmap = view.getSharedImage();
    ImageView imageView = new ImageView(view.getContext());
    imageView.setBitmap(bitmap);
    LayoutParams layoutParams = view.createSharedImageLayoutParams();
    final ViewGroup parent = (ViewGroup)view.getParent();
    parent.addView(imageView, layoutParams);
    parent.getViewTreeObserver().addOnPreDrawListener(new OnPreDrawListener() {
        @Override
        public boolean onPreDraw() {
            parent.getViewTreeObserver().removeOnPreDrawListener(this);
            customView.hideSharedImage();
            ActivityOptions activityOptions = ActivityOptions.
                makeSceneTransitionAnimation(this, imageView, "destName");
            startActivity(intent, activityOptions.toBundle();
        }
    });
    setExitSharedElementCallback(new SharedElementCallback() {
        @Override
        public void onSharedElementsArrived(List<String> sharedElementNames,
            List<View> sharedElements, OnSharedElementsReadyListener listener) {
            super.onSharedElementsArrived(sharedElementNames, sharedElements,
                listener);
            parent.removeView(imageView);
            customView.showSharedImage();
        }
    });
}

上記を具体的に試したことはありませんが、それが本質です。新しい onSharedElementsArrived を使用したくない場合は、onVisibilityChanged をリッスンするカスタム ImageView を作成できます。終了トランジションがある場合は、その終了もリッスンできます。ImageView が削除され、カスタム ビューが画像を再度描画するように、状態をリセットするように指示するトリガーが必要なだけです。

上記の例では、カスタム ビューと同じ親に ImageView を配置しました。DecorView に配置することで柔軟性が向上する可能性がありますが、グローバル位置が何であるかを把握する必要があり、画面上のすべてのものもオーバーレイされます。または、ImageView を親に追加したため、すべての親 (ListView、LinearLayout など) では機能しません。ビュー階層を知っているので、それを配置するのに最適な場所を選択する必要があります。

または、カスタム ビューをカスタム ViewGroup に変更し、共有可能な画像を ImageView として含めることもできます。私には簡単に聞こえます。

于 2015-12-04T15:38:50.787 に答える