#pragma once

#include "kmp_pi.h"
#include "mp3info.h"
#include "config.h"//mpg123.h の前にインクルードしないと正常動作しない
#include "mpg123.h"//
#include "kpi_decoder.h"
#include "kpi_impl.h"

class KbMpg123Decoder : public KbKpiUnknownImpl<IKpiDecoder>
{
private:
#ifdef REAL_IS_FLOAT
    typedef float mpg123_float;
#else
    typedef double mpg123_float;
#endif
    IKpiFile     *m_pFile;
    MP3Info       m_Mp3Info;
    mpg123_handle *m_mpg123;
    int           m_decode_status;
    BYTE          m_InputBuf[16384];//ファイルから読み込んだバッファ
    DWORD         m_dwInputBufLen;  //読み込んだバッファのサイズ
    DWORD         m_dwBlockAlign;
    BOOL          m_bEof;
    KPI_MEDIAINFO m_MediaInfo;
    //ギャップレス再生用
    DWORD         m_dwStartSample;  //先頭(サンプル単位)(デコード結果はここから使用)
    UINT64        m_qwEndSample;    //終端(サンプル単位)(デコード結果はここまで使用)
                                    //(LAME タグの enc_delay/enc_padding 付きの場合のみ有効）
    UINT64        m_qwDecodedSample;//デコード済みサンプル数
    DWORD         m_dwSkipRemain;    //スキップサンプル数残り
    //

    BYTE          m_OutputBuf[1152 * 2 * sizeof(mpg123_float)];//デコード結果を格納するバッファ
    DWORD         m_dwOutputRemain;         //m_OutputBuf のうち、未処理な部分のサイズ
                                            //最小値0、最大値sizeof(m_OutputBuf)
    DWORD         m_dwOutputBufSizeSample;  //m_OutputBuf の有効な部分のサイズ
public:
    static void GetDefaultDecoder(wchar_t* pszDecoder, int nSize);
    static bool IsSupportDecoder(const wchar_t* cszDecoder);
    DWORD  __fastcall Open(const KPI_MEDIAINFO *cpRequest,
                           IKpiFile *pFile,
                           IKpiFolder *pFolder,
                           IKpiConfig *pConfig);
    DWORD  WINAPI Select(DWORD dwNumber,
                         const KPI_MEDIAINFO **ppMediaInfo,
                         IKpiTagInfo *pTagInfo,
                         DWORD dwTagGetFlags);
    UINT64 WINAPI Seek(UINT64 qwPosSample, DWORD dwSeekFlag);
    DWORD  WINAPI Render(BYTE *Buffer, DWORD dwSizeSample);
    DWORD  WINAPI UpdateConfig(void *pvReserved){return 0;}
    KbMpg123Decoder(void);
    ~KbMpg123Decoder(void);
};

