• 风火轮 –动画效果:浮入与劈裂


    今天花了一个半小时,实现两个动画效果:浮入与劈裂。

    1. 浮入效果

    头文件

    enum CbwFloatDirection { // 浮入方向

        cfdUp = 0, // 上浮

            cfdDown = 1 // 下浮

        };

    /**

    * @class TCbwAnimationEffect_ FloatIn

    * @brief 动画基类

    *

    * 处理浮入动画效果

    * @author 陈斌文

    * @version 1.0

    * @date 2015-03-05

    * @QQ: 282397369

    */

    class TCbwAnimationEffect_FloatIn : public TCbwAnimationEffect { // 浮入

        virtual TRect __fastcall BuildDisplayRect(OBJECTMAT * m);

        virtual void __fastcall BuildDisplayMat(cv::Mat& destMat, cv::Mat& srcMat, TRect displayRect);

    public:

        __fastcall TCbwAnimationEffect_FloatIn();

        static TCbwAnimationEffect * Build();

    };

    实现代码:

    // ***************************** 浮入效果 **************************************

    __fastcall TCbwAnimationEffect_FloatIn::TCbwAnimationEffect_FloatIn()

        : TCbwAnimationEffect() {

        EffectType = cetFloatIn;

    }

    TCbwAnimationEffect * TCbwAnimationEffect_FloatIn::Build() {

        return new TCbwAnimationEffect_FloatIn;

    }

    浮入过程中,位置将渐次变化,重载BuildDisplayRect处理:

    TRect __fastcall TCbwAnimationEffect_FloatIn::BuildDisplayRect(OBJECTMAT * m) {

        TPoint startPos(m->LeftTopPosition.x, m->LeftTopPosition.y),

            endPos(m->LeftTopPosition.x, m->LeftTopPosition.y);

        int delta = 100;

        if (cfdUp == EffectOptionType) // 上浮

                startPos.y = endPos.y + delta;

        if (cfdDown == EffectOptionType) // 下浮

                startPos.y = endPos.y - delta;

        int x = startPos.x + (endPos.x - startPos.x) * (FCurrentIndex + 1)

            / FPeriodLength;

        int y = startPos.y + (endPos.y - startPos.y) * (FCurrentIndex + 1)

            / FPeriodLength;

        TRect result(x, y, x + m->Mat.cols, y + m->Mat.rows);

        return result;

    }

    为了更增加动画效果,可以在变换过程中加入对像素的控制,即淡出效果

    void __fastcall TCbwAnimationEffect_FloatIn::BuildDisplayMat(cv::Mat& destMat,

        cv::Mat& srcMat, TRect displayRect) {

        InnerTrans_FadeOut(destMat, srcMat);

    }

    // ***************************** 浮入效果 **************************************

    配置资源:

    最终效果:

    1. 劈裂效果

    头文件

    enum CbwSplitDirection { // 劈裂方向

        csdVertCollapse = 0, // 上下向中央收缩

            csdVertExpand = 1, // 中央向上下展开

            csdHorzCollapse = 2, // 左右向中央收缩

            csdHorzExpand = 3 // 中央向左右展开

        };

    /**

    * @class TCbwAnimationEffect_Split

    * @brief 动画基类

    *

    * 处理浮入动画效果

    * @author 陈斌文

    * @version 1.0

    * @date 2015-03-05

    * @QQ: 282397369

    */

    class TCbwAnimationEffect_Split : public TCbwAnimationEffect { // 劈裂

        virtual void __fastcall BuildMaskMat(cv::Mat& destMat, cv::Mat& srcMat, TRect displayRect);

    public:

        __fastcall TCbwAnimationEffect_Split();

        static TCbwAnimationEffect * Build();

    };

    实现代码:

    // ***************************** 劈裂效果 **************************************

    __fastcall TCbwAnimationEffect_Split::TCbwAnimationEffect_Split()

        : TCbwAnimationEffect() {

        EffectType = cetSplit;

    }

    TCbwAnimationEffect * TCbwAnimationEffect_Split::Build() {

        return new TCbwAnimationEffect_Split;

    }

    劈裂过程,可通过控制屏蔽矩阵来达到效果,即控制将拷贝的区域

    void __fastcall TCbwAnimationEffect_Split::BuildMaskMat(cv::Mat& destMat,

        cv::Mat& srcMat, TRect displayRect) {

        TRect wholeRect(0, 0, displayRect.right - displayRect.left,

            displayRect.bottom - displayRect.top);

        TRect partRect = wholeRect;

        double cx = partRect.right / 2.0, cy = partRect.bottom / 2.0;

        bool vertFlag = (EffectOptionType <= csdVertExpand);

        double delta = double(FCurrentIndex + 1) / FPeriodLength * (vertFlag ?

            cy : cx);

        if (csdVertExpand == EffectOptionType) { // 上下向中央收缩

            partRect.top = cy - delta;

            partRect.bottom = cy + delta;

        }

        if (csdVertCollapse == EffectOptionType) { // 中央向上下展开

            partRect.top = delta;

            partRect.bottom = 2 * cy - delta;

        }

        if (csdHorzExpand == EffectOptionType) { // 左右向中央收缩

            partRect.left = cx - delta;

            partRect.right = cx + delta;

        }

        if (csdHorzCollapse == EffectOptionType) { // 中央向左右展开

            partRect.left = delta;

            partRect.right = 2 * cx - delta;

        }

        bool expandFlag =

            (csdVertExpand == EffectOptionType ||

            csdHorzExpand == EffectOptionType);

        BYTE * pSrc = srcMat.data;

        BYTE * pDst = destMat.data;

        for (int row = 0; row < destMat.rows; ++row)

            for (int col = 0; col < destMat.cols; ++col) {

                bool hasValueFlag = (*pSrc++ != 0);

                if (!hasValueFlag)

                    * pDst = 0;

                int y = (row - partRect.top) * (partRect.bottom - row);

                int x = (col - partRect.left) * (partRect.right - col);

                bool inFlag = (y >= 0 && x >= 0);

                if(!expandFlag)

                    inFlag = (y > 0 && x > 0);

                bool setFlag = (inFlag == expandFlag);

                *pDst++ = (setFlag ? 255 : 0);

            }

    }

    // ***************************** 劈裂效果 **************************************

    配置资源

    运行效果

     

    回头再看一下,PPT中大概还有40个效果,如果按每天2个效果来实现的话,需要20天。加油。

  • 相关阅读:
    160309_Qt Essentials
    160309_Qt Reference Documentation
    160308_Signals & Slots
    160308_Helloworld_Gui Application
    网络爬虫(14)-动态页面爬取
    数据分析(6)-Pandas日期数据处理
    mysql基础(2)-excel功能在excel中如何实现?
    数据分析(5)-数据可视化常用图表类型和使用场景
    财经数据(6)-Python多进程爬虫东方财富个股盘口异动数据
    财经数据(5)-开盘啦股票标签数据爬虫
  • 原文地址:https://www.cnblogs.com/drgraph/p/4315183.html
Copyright © 2020-2023  润新知