在 WindowManager 上添加动画视图

发布于 2024-12-23 18:17:22 字数 1639 浏览 2 评论 0原文

我有一个视图(customView)添加到 WindowManager 中。

WindowManager mWm = (WindowManager)activity.getApplicationContext().getSystemService(Context.WINDOW_SERVICE);
WindowManager.LayoutParams(WindowManager.LayoutParams.FILL_PARENT, 0, PixelFormat.TRANSPARENT);
mWl.dimAmount = 0.0f;
mWm.addView(customView, mWl);

在自定义视图中,按下关闭按钮时我将调用翻译动画。

//// 这是动画的处理程序 ////

final Handler translateHandler = new Handler();

final Runnable mtranslateUp = new Runnable() {
    public void run() {
        Log.v("TEST","mtranslateUp Runnable");
        startAnimation(translateUp);
    }
};

//// 这是关闭按钮的监听器 ////

View.OnClickListener closeButtonListener = new View.OnClickListener() {         

    public void onClick(View v) {
        translateHandler.post(mtranslateUp);
    }
};

//// 这是向上平移动画 ////

translateUp = new TranslateAnimation(0,0,0,-200);
translateUp.setFillAfter(true);
translateUp.setDuration(1000);
translateUp.setAnimationListener(new AnimationListener(){
        @Override
        public void onAnimationEnd(Animation animation) {
            Log.v("TEST","translateUp onAnimationEnd");
        }

        @Override
        public void onAnimationRepeat(Animation animation) {
        }

        @Override
        public void onAnimationStart(Animation animation) {
            Log.v("TEST","translateUp onAnimationStart");
        }}
    );

如果添加了 customView对于一项活动,这些代码工作正常!

当customView添加到WindowManager时,onAnimationStart中的Log不显示,但Runnable中的Log可以显示。

任何人都可以告诉如何在添加到 WindowManager 的视图上制作动画吗?

I have a view (customView) added to the WindowManager.

WindowManager mWm = (WindowManager)activity.getApplicationContext().getSystemService(Context.WINDOW_SERVICE);
WindowManager.LayoutParams(WindowManager.LayoutParams.FILL_PARENT, 0, PixelFormat.TRANSPARENT);
mWl.dimAmount = 0.0f;
mWm.addView(customView, mWl);

Inside the custom view, I will call a translate animation when close button is pressed.

//// This is the handler for the animation ////

final Handler translateHandler = new Handler();

final Runnable mtranslateUp = new Runnable() {
    public void run() {
        Log.v("TEST","mtranslateUp Runnable");
        startAnimation(translateUp);
    }
};

//// This is the listener for the close button////

View.OnClickListener closeButtonListener = new View.OnClickListener() {         

    public void onClick(View v) {
        translateHandler.post(mtranslateUp);
    }
};

//// This is the translate up animation ////

translateUp = new TranslateAnimation(0,0,0,-200);
translateUp.setFillAfter(true);
translateUp.setDuration(1000);
translateUp.setAnimationListener(new AnimationListener(){
        @Override
        public void onAnimationEnd(Animation animation) {
            Log.v("TEST","translateUp onAnimationEnd");
        }

        @Override
        public void onAnimationRepeat(Animation animation) {
        }

        @Override
        public void onAnimationStart(Animation animation) {
            Log.v("TEST","translateUp onAnimationStart");
        }}
    );

If the customView is added to an activity, these code works fine!

When the customView is added to a WindowManager, the Log inside the onAnimationStart didn't show but the Log inside the Runnable can be shown.

Can anybody tells how to do animation on a view that is added to the WindowManager?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

倚栏听风 2024-12-30 18:17:22

您应该为视图布局参数设置动画。例如我使用一种方法来更新视图布局:

    public void updateViewLayout(View view, Integer x, Integer y, Integer w, Integer h){
    if (view!=null) {
        WindowManager.LayoutParams lp = (WindowManager.LayoutParams) view.getLayoutParams();

        if(x != null)lp.x=x;
        if(y != null)lp.y=y;
        if(w != null && w>0)lp.width=w;
        if(h != null && h>0)lp.height=h;

        mWindowService.updateViewLayout(view, lp);
    }
}

显然mWindowService是context.getSystemService(Context.WINDOW_SERVICE)。
我在动画中触发这个方法:

    public static void overlayAnimation(final View view2animate, int viewX, int endX) {
    ValueAnimator translateLeft = ValueAnimator.ofInt(viewX, endX);
    translateLeft.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator valueAnimator) {
            int val = (Integer) valueAnimator.getAnimatedValue();
            updateViewLayout(view2animate, val, null, null, null);

        }
    });
    translateLeft.setDuration(ANIMATION_DURATION);
    translateLeft.start();
}

You should animate the view LayoutParameters. For example I use a method to update the view layout:

    public void updateViewLayout(View view, Integer x, Integer y, Integer w, Integer h){
    if (view!=null) {
        WindowManager.LayoutParams lp = (WindowManager.LayoutParams) view.getLayoutParams();

        if(x != null)lp.x=x;
        if(y != null)lp.y=y;
        if(w != null && w>0)lp.width=w;
        if(h != null && h>0)lp.height=h;

        mWindowService.updateViewLayout(view, lp);
    }
}

Obviously mWindowService is context.getSystemService(Context.WINDOW_SERVICE).
I trigger this method in the animation:

    public static void overlayAnimation(final View view2animate, int viewX, int endX) {
    ValueAnimator translateLeft = ValueAnimator.ofInt(viewX, endX);
    translateLeft.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {
        @Override
        public void onAnimationUpdate(ValueAnimator valueAnimator) {
            int val = (Integer) valueAnimator.getAnimatedValue();
            updateViewLayout(view2animate, val, null, null, null);

        }
    });
    translateLeft.setDuration(ANIMATION_DURATION);
    translateLeft.start();
}
找回味觉 2024-12-30 18:17:22

我在附加到 WindowManager 的视图时遇到了类似的问题。尝试将 ViewGroup 添加到 WindoManager 而不是直接添加视图。它应该有效。

I was facing similar problem with a View attached to WindowManager.Try adding ViewGroup to WindoManager than View directly. It should work.

流殇 2024-12-30 18:17:22

windowManager需要android系统的动画。所以自定义动画将不起作用

windowManager need a animation by android system. so the custom animation will not work

柠檬色的秋千 2024-12-30 18:17:22

我有一个问题。

当我在 onAnimationUpdate 中使用 updateViewLayout 并设置 LayoutParams 的宽度时,动画丢帧。

但我设置了LayoutParams的x或y,动画就可以了。

就像下面的代码:

        mViewWidth = 800;
        mViewHeight = 800;
        final int oldX = mFloatWindowParams.x;
        final int oldWidth = mFloatWindowParams.width;
        final int oldHeight = mFloatWindowParams.height;
        final int deltaWidth = mViewWidth - oldWidth;
        final int deltaHeight = mViewHeight - oldHeight;
        final boolean isWidthLarger = deltaWidth > deltaHeight;
        int first = isWidthLarger ? oldWidth : oldHeight;
        int end = isWidthLarger ? mViewWidth : mViewHeight;
        ValueAnimator va = ValueAnimator.ofInt(first, end);

        va.setDuration(1000);
        va.setInterpolator(new LinearInterpolator());
        va.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            public void onAnimationUpdate(ValueAnimator animation) {
                int value = (Integer) animation.getAnimatedValue();
                float fraction = animation.getAnimatedFraction();
                Log.i("onAnimationUpdate", value + "");
                if (isWidthLarger) {
                    mFloatWindowParams.width = value;
                    mFloatWindowParams.height = oldHeight + (int) (deltaHeight * fraction);
                } else {
                    mFloatWindowParams.width = oldWidth + (int) (deltaWidth * fraction);
                    mFloatWindowParams.height = value;
                }
                mFloatWindowParams.x = oldX - (int) (deltaWidth * fraction);

                mWindowManager.updateViewLayout(mRootView, mFloatWindowParams);
            }
        });
        va.start();

I had a problem.

When i use updateViewLayout in onAnimationUpdate, and i set the LayoutParams's width, the animation has dropped frames.

But i set the LayoutParams's x or y, the animation is ok.

like the below code:

        mViewWidth = 800;
        mViewHeight = 800;
        final int oldX = mFloatWindowParams.x;
        final int oldWidth = mFloatWindowParams.width;
        final int oldHeight = mFloatWindowParams.height;
        final int deltaWidth = mViewWidth - oldWidth;
        final int deltaHeight = mViewHeight - oldHeight;
        final boolean isWidthLarger = deltaWidth > deltaHeight;
        int first = isWidthLarger ? oldWidth : oldHeight;
        int end = isWidthLarger ? mViewWidth : mViewHeight;
        ValueAnimator va = ValueAnimator.ofInt(first, end);

        va.setDuration(1000);
        va.setInterpolator(new LinearInterpolator());
        va.addUpdateListener(new ValueAnimator.AnimatorUpdateListener() {

            public void onAnimationUpdate(ValueAnimator animation) {
                int value = (Integer) animation.getAnimatedValue();
                float fraction = animation.getAnimatedFraction();
                Log.i("onAnimationUpdate", value + "");
                if (isWidthLarger) {
                    mFloatWindowParams.width = value;
                    mFloatWindowParams.height = oldHeight + (int) (deltaHeight * fraction);
                } else {
                    mFloatWindowParams.width = oldWidth + (int) (deltaWidth * fraction);
                    mFloatWindowParams.height = value;
                }
                mFloatWindowParams.x = oldX - (int) (deltaWidth * fraction);

                mWindowManager.updateViewLayout(mRootView, mFloatWindowParams);
            }
        });
        va.start();
~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文