背景

需要封装一个LVGL播放帧动画的组件,在下献丑了,封装了一个帧动画播放器。先看效果(没法录屏,只能手机录像):

在这里插入图片描述

代码如下

  • 头文件
/*
 * @Author: 
 * @Date: 2024-03-28 13:35:11
 * @LastEditors: 
 * @LastEditTime: 2024-03-28 14:55:55
 * @FilePath:/components/framePlayer.h
 * @Description: 帧动画播放器
 */
#ifndef FRAME_PLAYER_H
#define FRAME_PLAYER_H

#include"lvgl.h"
#include"iostream"
#include "string"

class FramePlayer {
public:
    FramePlayer(lv_obj_t *root);
    // 设置前缀
    void setPrefix(std::string prefix);
    // 设置后缀
    void setSuffix(std::string suffix);
    // 设置起始文件名编号
    void setStartIndex(int index);
    // 设置结束图片文件名编号
    void setEndIndex(int index);
    // 设计师提供的图画有的经过了抽帧,文件名编号不连续,可以通过设置间隔和起始编号实现播放偶数帧,奇数帧等
    void setIndexGap(int gap);
    // 设置大小
    void setSize(lv_coord_t w, lv_coord_t h);
    // 设置位置
    void setPos(lv_coord_t x, lv_coord_t y);
    // 设置时间,即多久播放下一帧
    void setPeriod(int period);
    // 开始播放
    void play();
    // 定时器回调,固定刷新图片
    static void onTimer(lv_timer_t* timer);
    ~FramePlayer();
    lv_obj_t *root;
    lv_obj_t *img;
    std::string prefix;
    std::string suffix;
    int startIndex;
    int currIndex;
    int endIndex;
    int indexGap;
    int period;
    lv_coord_t w;
    lv_coord_t h;
    lv_coord_t x;
    lv_coord_t y;
    lv_timer_t *timer;
};
#endif
  • cpp文件
/*
 * @Author:
 * @Date: 2024-03-28 10:34:14
 * @LastEditors: 
 * @LastEditTime: 2024-03-29 11:28:04
 * @FilePath: /components/framePlayer.cpp
 * @Description: 帧动画播放器
 */
#include "framePlayer.h"
FramePlayer::FramePlayer(lv_obj_t * root)
{
    this->root = root;
}

void FramePlayer::setPrefix(std::string prefix){
    this->prefix = prefix;
}
void FramePlayer::setSuffix(std::string suffix){
    this->suffix = suffix;
}
void FramePlayer::setStartIndex(int index){
    this->startIndex = index;
    this->currIndex=index;
}
void FramePlayer::setEndIndex(int index){
    this->endIndex = index;
}
void FramePlayer::setSize(lv_coord_t w, lv_coord_t h){
    this->w = w;
    this->h = h;
}
void FramePlayer::setPos(lv_coord_t x, lv_coord_t y){
    this->x = x;
    this->y = y;
}
void FramePlayer::setIndexGap(int gap){
    this->indexGap = gap;
}
void FramePlayer::setPeriod(int period){
    this->period = period;
}
void FramePlayer::play(){
   this->img  = lv_img_create(root);
    lv_obj_set_size(img, w, h);
    lv_obj_set_pos(img, x, y);
    this->timer  = lv_timer_create(onTimer, 100, this);
    lv_obj_set_style_bg_opa(img, LV_OPA_TRANSP,0);
    lv_timer_set_repeat_count(timer, -1);
    lv_timer_set_period(timer, this->period);
    lv_timer_enable(timer);
}
void FramePlayer::onTimer(lv_timer_t* timer){
    FramePlayer * framePlayer = (FramePlayer*)timer->user_data;
    std::string imgDir = HAIER_IMG_DIR;
    if(framePlayer->currIndex <= framePlayer->endIndex){
        
        std::string index = std::to_string(framePlayer->currIndex);
        // index ,我的帧序列文件编号,需要补0,补充到5位,可以根据自己的需求修改
        int len = index.length();
        for(int i = 0; i < 5 - len; i++){
            index = "0" + index;
        }

        std::string path = imgDir+framePlayer->prefix + index + framePlayer->suffix;
        // printf("path:%s %d        %d        %d \n",path.c_str(),framePlayer->currIndex,framePlayer->indexGap);
        lv_img_set_src(framePlayer->img, path.c_str());
        lv_obj_invalidate(framePlayer->img);
        framePlayer->currIndex+=framePlayer->indexGap;
    }else{
        framePlayer->currIndex = framePlayer->startIndex;
    }
}
FramePlayer::~FramePlayer()
{
    lv_timer_del(timer);
}

使用

下面给出具体的使用方法:

 	FramePlayer * framePlayer;
    framePlayer = new FramePlayer(root);
    framePlayer->setPrefix("demo/ai_ball_178/");
    framePlayer->setSuffix(".png");
    framePlayer->setStartIndex(0);
    framePlayer->setEndIndex(102);
    framePlayer->setIndexGap(2);
    framePlayer->setSize(178, 178);
    framePlayer->setPos(190, 95);
    framePlayer->setPeriod(60);
    framePlayer->play();
Logo

旨在为数千万中国开发者提供一个无缝且高效的云端环境,以支持学习、使用和贡献开源项目。

更多推荐