52 lines
1.4 KiB
C++
52 lines
1.4 KiB
C++
#pragma once
|
|
|
|
#include <cstdint>
|
|
#include <functional>
|
|
#include <string>
|
|
#include <vector>
|
|
|
|
// Raw decoded frame: packed RGB24 pixels, top-to-bottom, no padding.
|
|
struct FrameData {
|
|
std::vector<uint8_t> pixels; // width * height * 3 bytes (RGB)
|
|
int width = 0;
|
|
int height = 0;
|
|
int64_t pts = 0; // presentation timestamp (stream time-base units)
|
|
};
|
|
|
|
// Callback invoked for every decoded frame.
|
|
// Return true to continue, false to stop early.
|
|
using FrameCallback = std::function<bool(const FrameData&)>;
|
|
|
|
/**
|
|
* Opens a video file with libavformat/libavcodec, seeks to the first video
|
|
* stream, and decodes every frame in display order, converting each to RGB24
|
|
* via libswscale before handing it to the caller.
|
|
*/
|
|
class FrameExtractor {
|
|
public:
|
|
explicit FrameExtractor(std::string path);
|
|
~FrameExtractor();
|
|
|
|
// Disallow copy
|
|
FrameExtractor(const FrameExtractor&) = delete;
|
|
FrameExtractor& operator=(const FrameExtractor&) = delete;
|
|
|
|
// Open the file and locate the video stream. Returns false on error.
|
|
bool open();
|
|
|
|
// Decode every frame and invoke cb for each one.
|
|
void forEachFrame(FrameCallback cb);
|
|
|
|
// Metadata accessors (valid after open())
|
|
int width() const;
|
|
int height() const;
|
|
double durationSeconds() const;
|
|
double framerate() const;
|
|
|
|
private:
|
|
struct Impl;
|
|
Impl* d = nullptr;
|
|
|
|
std::string m_path;
|
|
};
|