#pragma once

#include "codec_abstract_codec.h"
#include <vector>
#include <memory>
#include <mutex>
#include <chrono>

namespace av {
namespace codec {

// 视频解码器参数
struct VideoDecoderParams : public CodecParams {
    std::string codecName;      // 解码器名称 (如 "h264", "hevc", "vp9")
    int width = 0;              // 视频宽度（可选，用于验证）
    int height = 0;             // 视频高度（可选，用于验证）
    AVPixelFormat pixelFormat = AV_PIX_FMT_YUV420P; // 输出像素格式
    bool hardwareAccel = true;  // 是否启用硬件加速
    int threadCount = 0;        // 解码线程数（0为自动）
    bool lowLatency = false;    // 低延迟模式
    
    VideoDecoderParams() {
        type = MediaType::VIDEO;
    }
};

// 视频解码器类
class VideoDecoder : public AbstractDecoder {
public:
    VideoDecoder();
    ~VideoDecoder() override;
    
    // 基础接口实现
    ErrorCode open(const CodecParams& params) override;
    void close() override;
    ErrorCode flush() override;
    ErrorCode reset() override;
    
    // 初始化方法
    ErrorCode initialize(const CodecParams& params);
    
    // 从流参数设置解码器
    ErrorCode setStreamParameters(const AVCodecParameters* codecpar);
    
    // 解码接口
    ErrorCode decode(const AVPacketPtr& packet, std::vector<AVFramePtr>& frames) override;
    ErrorCode finishDecode(std::vector<AVFramePtr>& frames) override;
    
    // 状态查询
    bool isHardwareDecoder() const { return isHardwareDecoder_; }
    std::string getDecoderName() const;
    
    // 统计信息
    struct DecoderStats {
        uint64_t decodedFrames = 0;
        uint64_t droppedFrames = 0;
        uint64_t errorCount = 0;
        double avgDecodeTime = 0.0;
        uint64_t totalBytes = 0;
    };
    
    DecoderStats getStats() const;
    void resetStats();
    
    // 静态工具方法
    static std::vector<std::string> getSupportedDecoders();
    static bool isHardwareDecoder(const std::string& codecName);
    static std::string getRecommendedDecoder(const std::string& codecName = "");
    
    // 解码器工厂
    class VideoDecoderFactory {
    public:
        static std::unique_ptr<VideoDecoder> create(const std::string& codecName = "");
        static std::unique_ptr<VideoDecoder> createBest(bool preferHardware = true);
    };
    
protected:
    bool validateParams(const CodecParams& params) override;
    
private:
    // 内部实现方法
    ErrorCode initDecoder();
    ErrorCode setupDecoderParams();
    ErrorCode setupHardwareAcceleration();
    ErrorCode setupHardwareFrameContext();
    
    // 流参数
    const AVCodecParameters* streamCodecpar_ = nullptr;
    
    ErrorCode decodeFrame(const AVPacketPtr& packet, std::vector<AVFramePtr>& frames);
    ErrorCode receiveFrames(std::vector<AVFramePtr>& frames);
    
    AVFramePtr convertFrame(const AVFramePtr& frame);
    AVFramePtr transferFromHardware(AVFramePtr hwFrame);
    
    // 硬件加速相关
    AVHWDeviceType getHardwareDeviceType() const;
    AVPixelFormat getHardwarePixelFormat() const;
    
    // 统计相关
    void updateStats(bool success, double decodeTime, size_t dataSize);
    
    // 静态方法实现
    static void findUsableDecoders();
    
private:
    VideoDecoderParams videoParams_;
    
    // FFmpeg 对象
    const AVCodec* codec_ = nullptr;
    AVCodecContextPtr codecCtx_;
    AVBufferRef* hwDeviceCtx_ = nullptr;
    AVFramePtr hwFrame_;
    
    // 硬件加速相关
    bool isHardwareDecoder_ = false;
    

    
    // 线程安全
    mutable std::mutex decodeMutex_;
    
    // 统计信息
    mutable std::mutex statsMutex_;
    DecoderStats stats_;
    std::chrono::high_resolution_clock::time_point lastStatsUpdate_;
    
    // 静态成员
    static std::vector<std::string> supportedDecoders_;
    static std::once_flag decodersInitFlag_;
    
    // 支持的解码器列表
    static constexpr const char* HARDWARE_DECODERS[] = {
        "h264_cuvid",      // NVIDIA CUDA
        "hevc_cuvid",      // NVIDIA CUDA HEVC
        "h264_qsv",        // Intel Quick Sync Video
        "hevc_qsv",        // Intel Quick Sync Video HEVC
        "h264_d3d11va",    // Direct3D 11 Video Acceleration
        "hevc_d3d11va",    // Direct3D 11 Video Acceleration HEVC
        "h264_videotoolbox", // Apple VideoToolbox
        "hevc_videotoolbox", // Apple VideoToolbox HEVC
        "vp9_cuvid",       // NVIDIA CUDA VP9
        "av1_cuvid",       // NVIDIA CUDA AV1
        nullptr
    };
    
    static constexpr const char* SOFTWARE_DECODERS[] = {
        "h264",            // H.264/AVC
        "hevc",            // H.265/HEVC
        "vp8",             // VP8
        "vp9",             // VP9
        "av1",             // AV1
        "mpeg2video",      // MPEG-2
        "mpeg4",           // MPEG-4
        "mjpeg",           // Motion JPEG
        nullptr
    };
};

} // namespace codec
} // namespace av