mirror of
https://github.com/niellun/FastCarPlay.git
synced 2026-06-07 09:38:25 +02:00
Optimise queues and rendering
This commit is contained in:
+64
-20
@@ -1,5 +1,5 @@
|
||||
#ifndef SRC_VIDEO_BUFFER
|
||||
#define SRC_VIDEO_BUFFER
|
||||
#ifndef SRC_STRUCT_VIDEO_BUFFER
|
||||
#define SRC_STRUCT_VIDEO_BUFFER
|
||||
|
||||
extern "C"
|
||||
{
|
||||
@@ -7,31 +7,75 @@ extern "C"
|
||||
}
|
||||
|
||||
#include <atomic>
|
||||
|
||||
#include "helper/error.h"
|
||||
#include <stdexcept>
|
||||
|
||||
#define BUFFER_VIDEO_FRAMES 3
|
||||
|
||||
class VideoBuffer
|
||||
{
|
||||
public:
|
||||
VideoBuffer();
|
||||
~VideoBuffer();
|
||||
|
||||
Error allocate(uint16_t width, uint16_t height);
|
||||
uint16_t width() const { return _width; };
|
||||
uint16_t height() const { return _height; };
|
||||
void reset();
|
||||
bool getLatest(AVFrame **frame, uint32_t *id);
|
||||
void consumeLatest();
|
||||
const AVFrame *writeFrame(uint32_t id);
|
||||
void commitFrame();
|
||||
VideoBuffer()
|
||||
{
|
||||
_writing.store(0);
|
||||
_reading.store(-1);
|
||||
_latest.store(-1);
|
||||
for (uint8_t i = 0; i < BUFFER_VIDEO_FRAMES; ++i)
|
||||
{
|
||||
_ids[i] = 0;
|
||||
_frames[i] = av_frame_alloc();
|
||||
if (!_frames[i])
|
||||
{
|
||||
throw std::runtime_error("Failed to allocate AVFrame");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
~VideoBuffer()
|
||||
{
|
||||
for (uint8_t i = 0; i < BUFFER_VIDEO_FRAMES; ++i)
|
||||
{
|
||||
if (_frames[i])
|
||||
{
|
||||
av_frame_free(&_frames[i]);
|
||||
_frames[i] = nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
bool latest(AVFrame **frame, uint32_t *id)
|
||||
{
|
||||
_reading.store(_latest.load());
|
||||
int index = _reading.load();
|
||||
if (index < 0)
|
||||
return false;
|
||||
*frame = _frames[index];
|
||||
*id = _ids[index];
|
||||
return true;
|
||||
}
|
||||
|
||||
void consume()
|
||||
{
|
||||
_reading.store(-1);
|
||||
}
|
||||
|
||||
AVFrame *write(uint32_t id)
|
||||
{
|
||||
int index = _writing.load();
|
||||
while (index == _reading.load() || index == _latest.load())
|
||||
{
|
||||
index = (index + 1) % BUFFER_VIDEO_FRAMES;
|
||||
}
|
||||
_writing.store(index);
|
||||
_ids[index] = id;
|
||||
return _frames[index];
|
||||
}
|
||||
|
||||
void commit()
|
||||
{
|
||||
_latest.store(_writing.load());
|
||||
}
|
||||
|
||||
private:
|
||||
void deallocate();
|
||||
|
||||
uint16_t _width;
|
||||
uint16_t _height;
|
||||
std::atomic<int8_t> _latest;
|
||||
std::atomic<int8_t> _reading;
|
||||
std::atomic<int8_t> _writing;
|
||||
@@ -39,4 +83,4 @@ private:
|
||||
uint32_t _ids[BUFFER_VIDEO_FRAMES];
|
||||
};
|
||||
|
||||
#endif /* SRC_VIDEO_BUFFER */
|
||||
#endif /* SRC_STRUCT_VIDEO_BUFFER */
|
||||
|
||||
Reference in New Issue
Block a user