1. ホーム
  2. android

新たな活動への移行を明らかにするサーキュラー

2023-08-26 09:01:15

質問

以下の通りです。 https://developer.android.com/training/material/animations.html

ViewAnimationUtils.createCircularReveal() メソッドを使用すると クリッピングサークルをアニメーション化し、ビューを表示または非表示にすることができます。

この効果を使用して、以前は見えなかったビューを明らかにする。

// previously invisible view
View myView = findViewById(R.id.my_view);

// get the center for the clipping circle
int cx = (myView.getLeft() + myView.getRight()) / 2;
int cy = (myView.getTop() + myView.getBottom()) / 2;

// get the final radius for the clipping circle
int finalRadius = Math.max(myView.getWidth(), myView.getHeight());

// create the animator for this view (the start radius is zero)
Animator anim =
    ViewAnimationUtils.createCircularReveal(myView, cx, cy, 0, finalRadius);

// make the view visible and start the animation
myView.setVisibility(View.VISIBLE);
anim.start();

これはビューを明らかにするためのものです。これを使用して、共有要素なしで、アクティビティ全体を循環的に表示するにはどうすればよいですか?

具体的には、私のsearchActivityが、ツールバーの検索アクションボタンから円形に明らかにすることを希望しています。

どのように解決するのですか?

半日ほど解決策を探しましたが、結果が出なかったので、独自の実装を思いつきました。私は、一致するルート レイアウトを持つ透明なアクティビティを使用しています。 ルート レイアウトはビューで、次のように明らかにすることができます。 createCircularReveal() .

私のコードはこのような感じです。

styles.xmlのテーマ定義

<style name="Theme.Transparent" parent="Theme.AppCompat.Light.NoActionBar">
    <item name="android:windowIsTranslucent">true</item>
    <item name="android:statusBarColor">@android:color/transparent</item>
    <item name="android:windowBackground">@android:color/transparent</item>
</style>

AndroidManifest.xmlのアクティビティ定義です。

<activity
        android:name=".ui.CircularRevealActivity"
        android:theme="@style/Theme.Transparent"
        android:launchMode="singleTask"
        />

それから、私は自分の活動のためのレイアウトを宣言しました(私はNavDrawerを持つことができるように、DrawerLayoutを選択しました。すべてのレイアウトがここで動作するはずです)。

<android.support.v4.widget.DrawerLayout
    android:id="@+id/drawer_layout"
    xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    >

    <FrameLayout
        android:id="@+id/root_layout"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="@color/honey_melon"
        >

        <!-- Insert your actual layout here -->

    </FrameLayout>

</android.support.v4.widget.DrawerLayout>

重要なのは、FrameLayoutのidが root_layout . このビューはアクティビティで公開されます。

最後に、私は CircularRevealActivity を実装し onCreate() :

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    overridePendingTransition(R.anim.do_not_move, R.anim.do_not_move);

    setContentView(R.layout.activity_reveal_circular);

    if (savedInstanceState == null) {
        rootLayout.setVisibility(View.INVISIBLE);

        ViewTreeObserver viewTreeObserver = rootLayout.getViewTreeObserver();
        if (viewTreeObserver.isAlive()) {
            viewTreeObserver.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
                @Override
                public void onGlobalLayout() {
                    circularRevealActivity();
                    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN) {
                        rootLayout.getViewTreeObserver().removeGlobalOnLayoutListener(this);
                    } else {
                        rootLayout.getViewTreeObserver().removeOnGlobalLayoutListener(this);
                    } 
                }
            });
        }
    }
}

を置くことが重要でした。 circularRevealActivity() の中に OnGlobalLayoutListener というのは、アニメーションのためにビューを描画する必要があるからです。

circularRevealActivity() は、Ishaanの提案のように見えます。

private void circularRevealActivity() {

    int cx = rootLayout.getWidth() / 2;
    int cy = rootLayout.getHeight() / 2;

    float finalRadius = Math.max(rootLayout.getWidth(), rootLayout.getHeight());

    // create the animator for this view (the start radius is zero)
    Animator circularReveal = ViewAnimationUtils.createCircularReveal(rootLayout, cx, cy, 0, finalRadius);
    circularReveal.setDuration(1000);

    // make the view visible and start the animation
    rootLayout.setVisibility(View.VISIBLE);
    circularReveal.start();
}

編集1

の定義は R.anim.do_not_move の定義が追加されました。しかし、デザインでアクティビティのデフォルトの遷移を指定していない場合は、この行なしでも動作するはずです。教えてください。

R.anim.do_not_move:

<set xmlns:android="http://schemas.android.com/apk/res/android">
<translate
    android:fromYDelta="0"
    android:toYDelta="0"
    android:duration="@android:integer/config_mediumAnimTime"
    />
</set>