• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>

            Codejie's C++ Space

            Using C++

            使用DirectSound播放MP3文件

                將對MP3的支持代碼加入到DSound程序中,以供wxDeMPQ使用,隨便調(diào)整了一下代碼,使基類作更多的事情。下面修改后的代碼,源碼在這里

                DSoundObject.h
             1 #ifndef __DSOUNDOBJECT_H__
             2 #define __DSOUNDOBJECT_H__
             3 
             4 #include <windows.h>
             5 #include <dsound.h>
             6 
             7 #include <string>
             8 
             9 extern HANDLE _eventNotify[3];
            10 
            11 class CDSoundObject
            12 {
            13 public:
            14     enum SoundType { ST_WAVE, ST_MP3 };
            15     static const DWORD SIZE_DS_BUFFER    =    32 * 1024;
            16 public:
            17     CDSoundObject(SoundType type);
            18     virtual ~CDSoundObject();
            19 
            20     virtual int Init(HWND hwnd);
            21     virtual int LoadFile(const std::string& file) = 0;
            22 
            23     virtual int Play();
            24     virtual int Pause();
            25     virtual int Stop();
            26     virtual bool IsPlaying() const;
            27     virtual double Duration() = 0;
            28 protected:
            29     virtual int CreateDSound();
            30     virtual void ReleaseDSound();
            31     virtual int CreateDSoundBuffer();
            32     virtual void ReleaseDSoundBuffer();
            33 
            34     virtual int InitDSData() = 0;
            35     virtual int LoadDSData(DWORD start, DWORD count) = 0;
            36     virtual int PlayOver();
            37 protected:
            38     HWND _hWnd;
            39     SoundType _eType;
            40     IDirectSound * _pDS;
            41     IDirectSoundBuffer * _pDSBuffer;
            42     IDirectSoundNotify8* _pDSNotify;
            43 protected:
            44     int CreateNotifyThread();
            45     void ReleaseNotifyThread();
            46     static DWORD NotifyHandleProc(LPVOID param);
            47 protected:
            48     DWORD _dwNotifyThreadID;
            49     HANDLE _hNotifyThread;
            50 
            51     DSBPOSITIONNOTIFY _notifyPos[2];
            52 protected:
            53     DWORD _dwPlayPos; 
            54 };
            55 
            56 #endif
                DSoundObject.cpp
              1 #include "DSoundObject.h"
              2 
              3 HANDLE _eventNotify[3];
              4 
              5 CDSoundObject::CDSoundObject(CDSoundObject::SoundType type)
              6 : _eType(type)
              7 , _pDS(NULL), _pDSBuffer(NULL), _pDSNotify(NULL)
              8 , _dwNotifyThreadID(0), _hNotifyThread(NULL)
              9 , _dwPlayPos(0)
             10 {
             11 }
             12 
             13 CDSoundObject::~CDSoundObject()
             14 {
             15     ReleaseNotifyThread();
             16     ReleaseDSoundBuffer();
             17     ReleaseDSound();
             18 }
             19 
             20 
             21 int CDSoundObject::Init(HWND hwnd)
             22 {
             23     _hWnd = hwnd;
             24 
             25     return CreateDSound();
             26 }
             27 
             28 int CDSoundObject::CreateDSound()
             29 {
             30     HRESULT hr = DirectSoundCreate(NULL, &_pDS, NULL);
             31     if(hr != DS_OK)
             32         return -1;
             33     _pDS->SetCooperativeLevel(_hWnd, DSSCL_NORMAL);
             34     return 0;
             35 }
             36 
             37 
             38 void CDSoundObject::ReleaseDSound()
             39 {
             40     if(_pDS != NULL)
             41         _pDS->Release(), _pDS = NULL;
             42 }
             43 
             44 int CDSoundObject::CreateDSoundBuffer()
             45 {
             46     ReleaseDSoundBuffer();
             47 
             48     return 0;
             49 }
             50 
             51 void CDSoundObject::ReleaseDSoundBuffer()
             52 {
             53     if(_pDSBuffer != NULL)
             54     {
             55         _pDSBuffer->Stop();
             56         _pDSBuffer->Release();
             57         _pDSBuffer = NULL;
             58     }
             59 }
             60 
             61 int CDSoundObject::CreateNotifyThread()
             62 {
             63     ReleaseNotifyThread();
             64 
             65     //event
             66     _eventNotify[0= CreateEvent(NULL, FALSE, FALSE, NULL);
             67     _eventNotify[1= CreateEvent(NULL, FALSE, FALSE, NULL);
             68     _eventNotify[2= CreateEvent(NULL, FALSE, FALSE, NULL);
             69 
             70 
             71     _hNotifyThread = CreateThread(NULL, 0, (LPTHREAD_START_ROUTINE)NotifyHandleProc, (LPVOID)this0&_dwNotifyThreadID);
             72     if(_hNotifyThread == NULL)
             73         return -1;
             74 
             75     HRESULT hr = _pDSBuffer->QueryInterface(IID_IDirectSoundNotify8, (void**)&_pDSNotify);
             76     if(hr != DS_OK)
             77         return -1;
             78 
             79     _notifyPos[0].dwOffset = (SIZE_DS_BUFFER / 2- 1;
             80     _notifyPos[0].hEventNotify = _eventNotify[0];
             81     _notifyPos[1].dwOffset = SIZE_DS_BUFFER - 1;
             82     _notifyPos[1].hEventNotify = _eventNotify[1];
             83 
             84     hr = _pDSNotify->SetNotificationPositions(2, _notifyPos);
             85     if(hr != DS_OK)
             86         return -1;
             87 
             88     return 0;
             89 }
             90 
             91 void CDSoundObject::ReleaseNotifyThread()
             92 {
             93     if(_hNotifyThread != NULL)
             94     {
             95         //TerminateThread(_hNotifyThread, 0);
             96         SetEvent(_eventNotify[2]);
             97         CloseHandle(_hNotifyThread);
             98         _hNotifyThread = NULL;
             99     }
            100     for(int i = 0; i < 2++ i)
            101     {
            102         if(_eventNotify[i] != NULL)
            103         {
            104             CloseHandle(_eventNotify[i]);
            105             _eventNotify[i] = NULL;
            106         }
            107     }
            108 
            109     if(_pDSNotify != NULL)
            110     {
            111         _pDSNotify->Release();
            112         _pDSNotify = NULL;
            113     }
            114 }
            115 
            116 DWORD CDSoundObject::NotifyHandleProc(LPVOID param)
            117 {
            118     CDSoundObject* obj = (CDSoundObject*)(param);
            119     if(obj == NULL)
            120         return -1;
            121 
            122     while(true)
            123     {
            124         DWORD ret = MsgWaitForMultipleObjects(3, _eventNotify, FALSE, INFINITE, QS_ALLEVENTS);
            125         if(ret == WAIT_FAILED)
            126             return -1;
            127         
            128         DWORD notify = ret - WAIT_OBJECT_0;
            129         if(notify == 0)
            130         {
            131             if(obj->LoadDSData(0, SIZE_DS_BUFFER / 2!= 0)
            132                 break;
            133         }
            134         else if(notify == 1)
            135         {
            136             if(obj->LoadDSData(SIZE_DS_BUFFER / 2 , SIZE_DS_BUFFER / 2!= 0)
            137                 break;
            138         }
            139         else if(notify == 2)
            140         {
            141             break;
            142         }
            143         else
            144         {
            145             continue;
            146         }
            147     }
            148 
            149     obj->PlayOver();
            150 
            151     return 0;
            152 }
            153 
            154 int CDSoundObject::Play()
            155 {
            156     if(_dwPlayPos == 0)
            157     {
            158         InitDSData();
            159     }
            160 
            161     _pDSBuffer->SetCurrentPosition(_dwPlayPos);
            162     _pDSBuffer->SetVolume(-2000);//DSBVOLUME_MAX);
            163     _pDSBuffer->Play(00, DSBPLAY_LOOPING);
            164 
            165     return 0;
            166 }
            167 
            168 int CDSoundObject::Pause()
            169 {
            170     if(_pDSBuffer == NULL)
            171         return -1;
            172     HRESULT hr = _pDSBuffer->GetCurrentPosition(&_dwPlayPos, NULL);
            173     if(hr != DS_OK)
            174         return -1;
            175     _pDSBuffer->Stop();
            176 
            177     return 0;
            178 }
            179 
            180 int CDSoundObject::Stop()
            181 {
            182     if(_pDSBuffer == NULL)
            183         return -1;
            184     _pDSBuffer->Stop();
            185     _dwPlayPos = 0;
            186 
            187     return 0;
            188 }
            189 
            190 bool CDSoundObject::IsPlaying() const
            191 {
            192     if(_pDSBuffer == NULL)
            193         return false;
            194 
            195     DWORD status = 0;
            196     HRESULT hr = _pDSBuffer->GetStatus(&status);
            197     if(hr != DS_OK)
            198         return false;
            199     return ((status & DSBSTATUS_PLAYING) == DSBSTATUS_PLAYING ? true : false);
            200 }
            201 
            202 int CDSoundObject::PlayOver()
            203 {
            204     return Stop();
            205 }
            206 
            207 
                DSMP3Object.h
             1 #ifndef __DSMP3OBJECT_H__
             2 #define __DSMP3OBJECT_H__
             3 
             4 #include <fstream>
             5 #include <string>
             6 
             7 #include "mpg123.h"
             8 
             9 #include "DSoundObject.h"
            10 
            11 class CDSMP3Object : public CDSoundObject
            12 {
            13 public:
            14     CDSMP3Object();
            15     virtual ~CDSMP3Object();
            16     
            17     virtual int LoadFile(const std::string& file);
            18     virtual double Duration();
            19 protected:
            20     virtual void Release();
            21     virtual int CreateDSoundBuffer();
            22 
            23     virtual int InitDSData();
            24     virtual int LoadDSData(DWORD start, DWORD count);
            25 private:
            26     mpg123_handle* _handle;
            27     unsigned char _buffer[SIZE_DS_BUFFER / 2];
            28     WAVEFORMATEX _fmtWave;
            29 };
            30 
            31 #endif
            32 
                DSMP3Object.cpp
              1 #include "DSMP3Object.h"
              2 
              3 CDSMP3Object::CDSMP3Object()
              4 : CDSoundObject(CDSoundObject::ST_MP3)
              5 , _handle(NULL)
              6 {
              7 }
              8 
              9 CDSMP3Object::~CDSMP3Object()
             10 {
             11     Release();
             12 }
             13 
             14 void CDSMP3Object::Release()
             15 {
             16     if(_handle != NULL)
             17     {
             18         mpg123_close(_handle);
             19         mpg123_delete(_handle);
             20         _handle = NULL;
             21         mpg123_exit();
             22     }
             23 }
             24 
             25 int CDSMP3Object::LoadFile(const std::string &file)
             26 {
             27     Release();
             28 
             29     if(mpg123_init() != MPG123_OK)
             30         return -1;
             31     int ret = -1;
             32     _handle = mpg123_new(NULL, &ret);
             33     if(_handle == NULL || ret != MPG123_OK)
             34         return -1;
             35 
             36     if(mpg123_open(_handle, file.c_str()) != MPG123_OK)
             37         return -1;
             38 
             39     if(CreateDSoundBuffer() != 0)
             40         return -1;
             41 
             42     return 0;
             43 }
             44 
             45 int CDSMP3Object::CreateDSoundBuffer()
             46 {
             47     CDSoundObject::CreateDSoundBuffer();
             48 
             49     long rate = 0;
             50     int channel = 0;
             51     int encoding = 0;
             52 
             53     if(mpg123_getformat(_handle, &rate, &channel, &encoding) != MPG123_OK)
             54         return -1;
             55     if((encoding & MPG123_ENC_16) == MPG123_ENC_16)
             56         encoding = 16;
             57     else if((encoding & MPG123_ENC_32) == MPG123_ENC_32)
             58         encoding = 32;
             59     else
             60         encoding = 8;
             61 
             62     memset(&_fmtWave, 0sizeof(WAVEFORMATEX));
             63     _fmtWave.wFormatTag = WAVE_FORMAT_PCM;
             64     _fmtWave.nChannels = channel;
             65     _fmtWave.nSamplesPerSec = rate;
             66     _fmtWave.wBitsPerSample = encoding;
             67     _fmtWave.nBlockAlign = encoding / 8 * channel;
             68     _fmtWave.nAvgBytesPerSec = rate * (encoding / 8* channel;
             69     
             70     DSBUFFERDESC desc;
             71     memset(&desc, 0sizeof(DSBUFFERDESC));
             72     desc.dwSize = sizeof(DSBUFFERDESC);
             73     desc.dwFlags = DSBCAPS_GLOBALFOCUS | DSBCAPS_CTRLVOLUME | DSBCAPS_CTRLPOSITIONNOTIFY | DSBCAPS_LOCSOFTWARE;
             74     desc.dwBufferBytes = CDSoundObject::SIZE_DS_BUFFER;
             75     desc.lpwfxFormat = &_fmtWave;
             76 
             77     if(_pDSBuffer != NULL)
             78         _pDSBuffer->Release();
             79 
             80     HRESULT hr = _pDS->CreateSoundBuffer(&desc, &_pDSBuffer, NULL);
             81     if(hr != DS_OK)
             82         return -1;
             83     
             84     return 0;
             85 }
             86 
             87 int CDSMP3Object::InitDSData()
             88 {
             89     //if(mpg123_seek(_handle, 0, SEEK_SET) < 0)
             90     //    return -1;
             91     off_t s = mpg123_seek(_handle, 0, SEEK_SET);
             92     if(s < 0)
             93         return -1;
             94 
             95     if(LoadDSData(0, CDSoundObject::SIZE_DS_BUFFER) != 0)
             96         return -1;
             97 
             98     if(CreateNotifyThread() != 0)
             99         return -1;
            100 
            101 //    _dwPlayPos = 0;
            102 
            103     return 0;
            104 }
            105 
            106 int CDSMP3Object::LoadDSData(DWORD start, DWORD count)
            107 {
            108     LPVOID aptr1 = NULL, aptr2 = NULL;
            109     DWORD abyte1 = NULL, abyte2 = NULL;
            110 
            111     HRESULT hr = _pDSBuffer->Lock(start, count, &aptr1, &abyte1, &aptr2, &abyte2, 0);
            112     if(hr != DS_OK)
            113         return -1;
            114 
            115     size_t outsize = 0;
            116     if(mpg123_read(_handle, _buffer, SIZE_DS_BUFFER / 2&outsize) != MPG123_OK)
            117         return -1;
            118 
            119     memcpy(aptr1, _buffer, outsize);
            120     if(aptr2 != 0)
            121     {
            122         if(mpg123_read(_handle, _buffer, SIZE_DS_BUFFER / 2&outsize) != MPG123_OK)
            123             return -1;
            124         memcpy(aptr2, _buffer, outsize);
            125     }
            126 
            127     _pDSBuffer->Unlock(aptr1, abyte1, aptr2, abyte2);
            128 
            129     return 0;
            130 }
            131 
            132 double CDSMP3Object::Duration()
            133 {
            134     off_t len = mpg123_length(_handle);
            135     return (len / _fmtWave.nSamplesPerSec);
            136 }



            posted on 2009-03-26 10:57 codejie 閱讀(6026) 評論(8)  編輯 收藏 引用 所屬分類: C++

            評論

            # re: 使用DirectSound播放MP3文件 2009-12-07 19:51 chl

            你好,看了你的DS播放MP3的代碼,我也是在寫這個(gè)相關(guān)代碼,第一次接觸聲音部分,看了你的代碼很有收獲,想問你,mpg123_read就可以把MP3轉(zhuǎn)化為WAV的了嗎?還有就是你有mpg123的源碼嗎?可以發(fā)給我嗎?我的QQ:84818557,郵箱84818557@qq.com,看到消息給我回復(fù)好嗎,謝謝。  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件[未登錄] 2009-12-07 21:40 codejie

            @chl
            我想你需要的都在http://www.mpg123.de/api/  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件 2009-12-08 21:13 chl

            我已經(jīng)解決了,還是很 感謝你,以后多交流,我的聲音系統(tǒng)也完成了。  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件 2009-12-09 09:30 codejie

            @chl
            GX  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件 2010-01-24 13:58 kun

            能把 vs下 編譯libmpg的sln給我?(kunooo@qq.com)  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件[未登錄] 2010-01-24 14:48 codejie

            @kun
            mpg庫到http://www.mpg123.de/下載就可以了。  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件 2011-07-02 20:28 huangdi

            好像不能播放。只能播放開頭一點(diǎn)點(diǎn)  回復(fù)  更多評論   

            # re: 使用DirectSound播放MP3文件 2011-07-04 10:39 codejie

            @huangdi
            啊,我都忘記這個(gè)了。。看了半天,如果是這樣,那應(yīng)該是‘循環(huán)’加載數(shù)據(jù)時(shí)沒有算準(zhǔn)‘位置’。辛苦你多試試了。  回復(fù)  更多評論   

            公告

            Using C++

            導(dǎo)航

            統(tǒng)計(jì)

            留言簿(73)

            隨筆分類(513)

            積分與排名

            最新評論

            閱讀排行榜

            評論排行榜

            久久亚洲中文字幕精品一区| 久久九九兔免费精品6| 好属妞这里只有精品久久| 国产精品免费福利久久| 91精品国产高清久久久久久国产嫩草 | 九九热久久免费视频| 日日狠狠久久偷偷色综合0| 久久久精品国产免大香伊| 亚洲精品tv久久久久| 久久精品国产亚洲AV电影| 久久精品亚洲精品国产欧美| 亚洲AV无码久久精品成人 | 欧美激情精品久久久久久久九九九 | 亚洲国产精品成人久久蜜臀| 久久久综合香蕉尹人综合网| 国产真实乱对白精彩久久| 久久精品不卡| 亚洲人成无码www久久久| 欧美国产成人久久精品| 久久中文字幕人妻丝袜| 亚洲AV无码成人网站久久精品大| 日韩人妻无码一区二区三区久久 | 精品国产乱码久久久久久人妻| 狠狠色丁香久久婷婷综合蜜芽五月| 国产精品久久婷婷六月丁香| 99精品国产99久久久久久97 | 狠狠色狠狠色综合久久| 亚洲色婷婷综合久久| 久久er99热精品一区二区| 色综合久久88色综合天天| 亚洲国产精品成人久久| 狠狠狠色丁香婷婷综合久久俺| 一本一道久久精品综合 | 久久精品国产福利国产琪琪| 亚洲欧美成人久久综合中文网 | 91超碰碰碰碰久久久久久综合| 久久婷婷五月综合97色直播| 亚洲精品乱码久久久久久| 99久久夜色精品国产网站| 精品精品国产自在久久高清| 久久精品国产亚洲av瑜伽|