91 lines
2.4 KiB
C++
91 lines
2.4 KiB
C++
#ifndef PROJECT_PLAYER_H
|
|
#define PROJECT_PLAYER_H
|
|
|
|
#include "ffcpp/MediaFile.h"
|
|
#include "ffcpp/Scaler.h"
|
|
#include "TSQueue.h"
|
|
#include "Resampler.h"
|
|
#include "readerwriterqueue.h"
|
|
#include <memory>
|
|
#include <thread>
|
|
#include <condition_variable>
|
|
#include <mutex>
|
|
#include <cstdint>
|
|
#include <cstdio>
|
|
|
|
namespace ffcpp {
|
|
|
|
struct IVideoSink {
|
|
virtual AVPixelFormat getPixelFormat() const noexcept = 0;
|
|
virtual void drawFrame(void* pixelsData, int pitch) = 0;
|
|
virtual void drawPlanarYUVFrame(const void *yPlane, const void *uPlane, const void *vPlane, int yPitch,
|
|
int uPitch, int vPitch) = 0;
|
|
};
|
|
|
|
struct IAudioSource {
|
|
virtual void fillSampleBuffer(uint8_t *data, int length) = 0;
|
|
};
|
|
|
|
struct IAudioSink {
|
|
virtual void setAudioSource(IAudioSource* audioSrc) = 0;
|
|
virtual AVSampleFormat getSampleFormat() = 0;
|
|
virtual int getChannelsCount() = 0;
|
|
virtual int getSampleRate() = 0;
|
|
};
|
|
|
|
enum class PlayerState {
|
|
Shutdown,
|
|
Stopped,
|
|
Playing,
|
|
Paused
|
|
};
|
|
|
|
class Player: private IAudioSource {
|
|
private:
|
|
static constexpr size_t AUDIO_BUFFER_LENGTH = 16*1024;
|
|
|
|
private:
|
|
typedef moodycamel::ReaderWriterQueue<FramePtr> FrameQueue;
|
|
|
|
private:
|
|
std::shared_ptr<IVideoSink> _vSink;
|
|
std::shared_ptr<IAudioSink> _aSink;
|
|
std::unique_ptr<MediaFile> _curMedia;
|
|
StreamPtr _aStream;
|
|
StreamPtr _vStream;
|
|
ScalerPtr _scaler;
|
|
ResamplerPtr _resampler;
|
|
PlayerState _state;
|
|
|
|
std::unique_ptr<uint8_t[]> _aSamplesBuffer;
|
|
int _samplesInBuffer;
|
|
FILE* _asFile;
|
|
|
|
std::mutex _mutex;
|
|
std::condition_variable _stateCond;
|
|
FrameQueue _videoFrames;
|
|
FrameQueue _audioFrames;
|
|
std::thread _decodeThread;
|
|
std::thread _vPlayThread;
|
|
|
|
public:
|
|
Player(std::shared_ptr<IVideoSink> vSink, std::shared_ptr<IAudioSink> aSink);
|
|
~Player();
|
|
|
|
void setMedia(std::string path);
|
|
void setVideoSize(size_t width, size_t height);
|
|
void play();
|
|
|
|
private:
|
|
void decode();
|
|
void displayFrames();
|
|
void processFrame(FramePtr frame, AVMediaType type, FrameQueue* queue);
|
|
|
|
private:
|
|
void fillSampleBuffer(uint8_t *data, int length) override;
|
|
};
|
|
|
|
}
|
|
|
|
#endif //PROJECT_PLAYER_H
|