Welcome to our website.

Frame-by-Frame Animation and String Helpers in EasyX

Playing an animation from individual images

EasyX does not provide a built-in function for loading and playing GIF animations. A practical workaround is to extract the GIF into a sequence of frame images, then display those images one after another.

The example below uses 92 PNG frames, named 1.png through 92.png and stored in the ../gif/ directory. Each frame is loaded into an IMAGE object at a size of 1080 × 810 pixels. The isLoaded flag keeps the image-loading step from running again on subsequent calls to loading().

#include <graphics.h>
#include <conio.h>
#include <stdio.h>
#include <iostream>
IMAGE images[92];//92张关键帧
bool isLoaded = 0;
void loadImg()
{
    wchar_t filename[20];
    for (int i = 0; i < 92; i++)
    {
        //这里我是将原有的gif图拆分为了92张关键帧
        wsprintf(filename, _T("../gif/%d.png"), i + 1);
        loadimage(&images[i], filename, 1080, 810);//读相关图片,并设置读入大小为1080*810
    }
}
void loading()
{
    std::cout << "窗口初始化中..." << std::endl;
    // 加载关键帧图片
    if (!isLoaded)
    {
        isLoaded = 1;
        loadImg();
    }
    HWND hwnd = initgraph(1080, 810); // 初始化绘图窗口大小
    MoveWindow(hwnd, 380, 200, 1096, 849, false);
    //采用批量绘制,防闪烁
    BeginBatchDraw();//批量绘制开始
    for (int i = 0; i < 92; i++)
    {
        cleardevice(); // 清空屏幕
        putimage(0, 0, &images[i]); // 绘制当前帧图片
        FlushBatchDraw(); // 批量绘制刷新
        Sleep(25); // 控制每帧显示时间,单位为毫秒
    }
    EndBatchDraw();//批量绘制结束
    std::cout << "窗口初始化完毕" << std::endl;
}

The drawing area is initialized at 1080 × 810 pixels. MoveWindow then positions the window at (380, 200) and sets its overall dimensions to 1096 × 849.

Playback runs inside a batch-drawing session to reduce flicker. For each frame, the program clears the drawing area, places the image at the top-left corner, and calls FlushBatchDraw() to display the update. Sleep(25) adds a 25-millisecond pause before the next frame. This loop plays the 92-frame sequence once, then ends batch drawing and prints the completion message.

Helpers for narrow and wide strings

The supporting code includes two conversion functions: wstringTostring() converts a std::wstring into a std::string, while stringTowstring() performs the reverse conversion. Both use _bstr_t as an intermediate object and copy the resulting character data into the returned string.

The snippet also includes the library-linking directive for comsuppw.lib and a _MIN macro that selects the smaller of two values.

#include <codecvt>
#include <comutil.h>
#include <string>
#pragma comment(lib, "comsuppw.lib")
#define _MIN(x,y) (((x)<(y))?(x):(y))
//wstring转string
std::string wstringTostring(const std::wstring& ws)
{
    _bstr_t t = ws.c_str();
    char* pchar = (char*)t;
    std::string result = pchar;
    return result;
}
//string转wstring
std::wstring stringTowstring(const std::string& s)
{
    _bstr_t t = s.c_str();
    wchar_t* pwchar = (wchar_t*)t;
    std::wstring result = pwchar;
    return result;
}

Related Posts