作者: 乔克斯
查看: 86494|回复: 134

【360动画效果】仿360杀毒-页面切换动画效果(C#源码)

  [复制链接]
乔克斯 发表于 2017-1-24 11:53:03 | 显示全部楼层 |阅读模式
查看: 86494|回复: 134
说明:
C#winform版 《仿360杀毒》页面切换动画效果昨天跟一个同事聊天,谈到了360杀毒的页面效果不错,我们所做的winform页面都是拖控件还是拖控件,不能吸引客户的注意力,想改成360的样式。
今天活不多,抽空仿做了两个360杀毒的页面切换效果,其实原理很简单,这里分享出来,希望能给大家带来帮助。期间滑动的时候,窗体是不能拖动或者点击其他的功能,这里可能是用了单线程进行了页面切换。

功能详解:
滑动效果
“功能大全功能”的切换效果是右到左滑入,从最右侧,迅速往左侧滑入,当快要完成切换时,有个稍微停顿的效果,接着缓冲效果到页面完全显示。
页面进入部分

页面退出时,也是右侧到左侧滑出,和滑入一样,前期是迅速往左侧滑出,当快要完成切出时,也是有个稍微的停顿效果,接着缓冲效果到页面完全消失。
页面移出部分

这个动画效果,用单线程实现就好了,实例化滑动的窗体,初始化窗体原坐标为窗口最右侧(form.Width,0),之后使用for,while,Timer,BackgroundWork等等都可以。
我这里用了While进行单线程切换:
[C#] 纯文本查看 复制代码
        private void AnimationX(Control ctrl, int x, int milliseconds)
        {
            Point startPoint = ctrl.Location;
            int vector = x >= ctrl.Location.X ? 1 : -1;
            int length = Math.Abs(startPoint.X - x);
            if (Math.Abs(vector * length) > milliseconds)
                vector = vector * length / milliseconds;


            while ((ctrl.Location.X - x) > 0)
            {
                ctrl.Location = new Point(ctrl.Location.X + vector, ctrl.Location.Y);
                Application.DoEvents();
                if (x < 0)
                    System.Threading.Thread.Sleep(5);
            }
            ctrl.Location = new Point(x, ctrl.Location.Y);
        }


上下分页效果
“查杀功能”的切换效果是上下分离,页面从中间横线出分裂开,上部分向上打开,下半部分向下打开,最后显示第二个页面,这样完成了页面的切换功能。
这里如果在用单线程的话,就会出现,先上半部分向上打开后,在下半部分向下打开,这样不能够实现上下部分同时打开效果,如果在同一个方法内操作两个部分,这样就会是代码出现冗余情况。你不觉得这样写很不好吗,而且维护的话也很难,看起来也有点费劲是吧。呵呵 ^ ^
这里我用了BackgroundWork:
动画方法:
[C#] 纯文本查看 复制代码
        private void AnimationY(Control ctrl, int y, int milliseconds, bool IsUp)
        {
            Point startPoint = ctrl.Location;
            int vector = y >= ctrl.Location.Y ? 1 : -1;
            int length = Math.Abs(startPoint.Y - y);
            if (Math.Abs(vector * length) > milliseconds)
                vector = vector * length / milliseconds;

            while ((IsUp && (ctrl.Location.Y + vector) > y) || (!IsUp && (ctrl.Location.Y + vector) < y))
            {
                ctrl.Location = new Point(ctrl.Location.X, ctrl.Location.Y + vector);

                System.Threading.Thread.Sleep(10);
                Application.DoEvents();
            }
            ctrl.Location = new Point(ctrl.Location.X, y);
        }


上半部分的BackgroundWork:
[C#] 纯文本查看 复制代码
        private void bgwTop_DoWork(object sender, DoWorkEventArgs e)
        {
            int[] tem=e.Argument as int[];
            int Y = tem[0];
            int y = tem[1];
            int milliseconds = tem[2];
            bool IsUp = Convert.ToBoolean(tem[3]);

            int vector = y >= tem[0] ? 1 : -1;
            int length = Math.Abs(Y - y);
            if (Math.Abs(vector * length) > milliseconds)
                vector = vector * length / milliseconds;

            while ((IsUp && (Y + vector) > y) || (!IsUp && (Y + vector) < y))
            {
                bgwTop.ReportProgress(Y + vector, null);
                System.Threading.Thread.Sleep(25);
                //Application.DoEvents();
                Y=Y + vector;
            }
            bgwTop.ReportProgress(y, null);
        }

        private void bgwTop_ProgressChanged(object sender, ProgressChangedEventArgs e)
        {
            this.lblTop.Location = new Point(this.lblTop.Location.X, e.ProgressPercentage);
        }


下半部分的BackgroundWork:
[C#] 纯文本查看 复制代码
        private void bgwBottom_DoWork(object sender, DoWorkEventArgs e)
        {
            int[] tem = e.Argument as int[];
            int Y = tem[0];
            int y = tem[1];
            int milliseconds = tem[2];
            bool IsUp = Convert.ToBoolean(tem[3]);

            int vector = y >= tem[0] ? 1 : -1;
            int length = Math.Abs(Y - y);
            if (Math.Abs(vector * length) > milliseconds)
                vector = vector * length / milliseconds;

            while ((IsUp && (Y + vector) > y) || (!IsUp && (Y + vector) < y))
            {
                bgwBottom.ReportProgress(Y + vector, null);
                System.Threading.Thread.Sleep(25);
                //Application.DoEvents();
                Y = Y + vector;
            }
            bgwBottom.ReportProgress(y, null);
        }

        private void bgwBottom_ProgressChanged(object sender, ProgressChangedEventArgs e)
        {
            this.lblBottom.Location = new Point(this.lblBottom.Location.X, e.ProgressPercentage);
        }


作品效果图:


案例源码下载:


评分

参与人数 2金钱 +2 收起 理由
FSHA + 1 感谢分享,LZ辛苦了~
LguoF + 1 很给力!

查看全部评分

回复 论坛版权

使用道具 举报

mqzzzz 发表于 2017-1-24 13:46:38 | 显示全部楼层
6666666666666666666666666666
zimistan 发表于 2017-1-25 16:52:54 | 显示全部楼层
谢谢了 楼主
贰佰伍 发表于 2017-1-26 21:59:02 | 显示全部楼层
这个就很厉害了
eddieiat 发表于 2017-2-2 17:05:52 | 显示全部楼层
乔克斯根本是大神啊
罗布斯 发表于 2017-2-8 14:57:36 | 显示全部楼层
厉害了,好东西
sas 发表于 2017-2-9 14:58:15 | 显示全部楼层
厉害了,好东西
qq541717868 发表于 2017-2-10 09:31:09 | 显示全部楼层
好厉害啊
回复

使用道具 举报

123456mnk 发表于 2017-2-10 11:07:34 | 显示全部楼层
厉害,界面能做的再精致点就更完美了。
无醉 发表于 2017-2-14 09:41:23 | 显示全部楼层
谢谢了 楼主
您需要登录后才可以回帖 登录 | 加入CSkin博客

本版积分规则

QQ|申请友链|小黑屋|手机版|Archiver|CSkin ( 粤ICP备13070794号

Powered by Discuz! X3.2  © 2001-2013 Comsenz Inc.  Designed by ARTERY.cn
GMT+8, 2024-3-28 16:17, Processed in 0.677612 second(s), 36 queries , Gzip On.

快速回复 返回顶部 返回列表