Чтобы использовать MCI с mciSendCommand
, необходимо
- Откройте устройство и получите идентификатор устройства.
- Установите поиск.
- Play.
Или
- Откройте устройство и получите идентификатор устройства.
- Воспроизведение с указанной позиции напрямую.
Пример:
#include <windows.h>
#pragma comment(lib, "winmm.lib")
MCIDEVICEID MCIOpen(LPCTSTR strPath)
{
MCI_OPEN_PARMS mciOP;
DWORD opReturn;
mciOP.lpstrDeviceType = NULL;
mciOP.lpstrElementName = strPath; //Set the .wav file name to open
opReturn = mciSendCommand(NULL, MCI_OPEN, MCI_OPEN_ELEMENT, (DWORD)(LPVOID)&mciOP);
if (!opReturn)
return mciOP.wDeviceID;
return -1;
}
DWORD MCISeek(MCIDEVICEID wDeviceID,int sec)
{
MCI_SEEK_PARMS SeekParms;
SeekParms.dwTo = (sec) * 1000;
return mciSendCommand(wDeviceID, MCI_SEEK, MCI_TO, (DWORD)(LPVOID)&SeekParms);
}
DWORD MCIPlay(MCIDEVICEID wDeviceID)
{
MCI_PLAY_PARMS mciPP;
return mciSendCommand(wDeviceID, MCI_PLAY, MCI_NOTIFY| MCI_WAIT, (DWORD)&mciPP);
}
DWORD MCIPlayFrom(MCIDEVICEID wDeviceID,int sec)
{
MCI_PLAY_PARMS play;
play.dwFrom = sec*1000;//Play From sec*1000 ms
return mciSendCommand(wDeviceID, MCI_PLAY, MCI_NOTIFY | MCI_FROM| MCI_WAIT, (DWORD)&play);
}
int main()
{
//open device
MCIDEVICEID wDeviceID = MCIOpen("test.wav"); //Save DeviceID
DWORD opReturn;
if (wDeviceID != -1)
{
//MCI_SET_PARMS mciSet;
//mciSet.dwTimeFormat = MCI_FORMAT_MILLISECONDS;//set time format to milliseconds
//opReturn = mciSendCommand(wDeviceID, MCI_SET, MCI_SET_TIME_FORMAT, (DWORD)(LPVOID)&mciSet);
////set the position at 30s.
//opReturn = MCISeek(wDeviceID, 30);
////play
//opReturn = MCIPlay(wDeviceID);
opReturn = MCIPlayFrom(wDeviceID,30);
}
return opReturn;
}
Обратите внимание, что если вы хотите получить звук, при использовании MCI_PLAY
.
необходим флаг
MCI_WAIT
.
EDIT:
Вы не можете услышать звук, потому что у вас мало времени для начала воспроизведения. Он начнет воспроизведение и сразу же закроет его (это можно проверить, добавив Sleep()
после начала воспроизведения). См. связанную проблему . Если вы хотите воспроизвести без ожидания, вам нужно обработать MCI_NOTIFY
, установить дескриптор окна обратного вызова и обработать MM_MCINOTIFY
, когда воспроизведение закончится.
#include <windows.h>
#pragma comment(lib, "winmm.lib")
HWND hwnd;
MCIDEVICEID MCIOpen(LPCTSTR strPath)
{
MCI_OPEN_PARMS mciOP;
DWORD opReturn;
mciOP.lpstrDeviceType = NULL;
mciOP.lpstrElementName = strPath; //Set the .wav file name to open
opReturn = mciSendCommand(NULL, MCI_OPEN, MCI_OPEN_ELEMENT, (DWORD)(LPVOID)&mciOP);
if (!opReturn)
return mciOP.wDeviceID;
return -1;
}
DWORD MCISeek(MCIDEVICEID wDeviceID,int sec)
{
MCI_SEEK_PARMS SeekParms;
SeekParms.dwTo = (sec) * 1000;
return mciSendCommand(wDeviceID, MCI_SEEK, MCI_TO, (DWORD)(LPVOID)&SeekParms);
}
DWORD MCIPlay(MCIDEVICEID wDeviceID)
{
MCI_PLAY_PARMS mciPP;
mciPP.dwCallback = (DWORD_PTR)hwnd;
return mciSendCommand(wDeviceID, MCI_PLAY, MCI_NOTIFY, (DWORD)&mciPP);
}
DWORD MCIPlayFrom(MCIDEVICEID wDeviceID,int sec)
{
MCI_PLAY_PARMS play;
play.dwFrom = sec*1000;//Play From sec*1000 ms
return mciSendCommand(wDeviceID, MCI_PLAY, MCI_NOTIFY | MCI_FROM, (DWORD)&play);
}
LRESULT CALLBACK WndProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
{
switch (message)
{
case MM_MCINOTIFY:
{
if (MCI_NOTIFY_SUCCESSFUL == wParam) //MCI_NOTIFY_SUCCESSFUL means that the song has been played successfully.
{
//To Do
}
}
break;
default:
return DefWindowProc(hWnd, message, wParam, lParam);
}
return 0;
}
int main()
{
static const char* class_name = "DUMMY_CLASS";
WNDCLASSEX wx = {};
wx.cbSize = sizeof(WNDCLASSEX);
wx.lpfnWndProc = WndProc; // function which will handle messages
wx.hInstance = GetModuleHandleA(NULL);
wx.lpszClassName = class_name;
if (RegisterClassEx(&wx)) {
hwnd = CreateWindowEx(0, class_name, "dummy_name", 0, 0, 0, 0, 0, HWND_MESSAGE, NULL, NULL, NULL);
}
//open device
MCIDEVICEID wDeviceID = MCIOpen("test.wav"); //Save DeviceID
DWORD opReturn;
if (wDeviceID != -1)
{
//MCI_SET_PARMS mciSet;
//mciSet.dwTimeFormat = MCI_FORMAT_MILLISECONDS;//set time format to milliseconds
//opReturn = mciSendCommand(wDeviceID, MCI_SET, MCI_SET_TIME_FORMAT, (DWORD)(LPVOID)&mciSet);
////set the position at 30s.
//opReturn = MCISeek(wDeviceID, 30);
////play
//opReturn = MCIPlay(wDeviceID);
opReturn = MCIPlayFrom(wDeviceID,30);
}
HACCEL hAccelTable = LoadAccelerators(wx.hInstance, class_name);
MSG msg;
while (GetMessage(&msg, nullptr, 0, 0))
{
if (!TranslateAccelerator(msg.hwnd, hAccelTable, &msg))
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
}
return 0;
}