Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenvolume.c
Go to the documentation of this file.
00001 /* $Id: main.c 12852 2005-01-06 13:58:04Z mf $ 00002 * 00003 * PROJECT: ReactOS Multimedia Control Panel 00004 * FILE: dll/cpl/mmsys/mmsys.c 00005 * PURPOSE: ReactOS Multimedia Control Panel 00006 * PROGRAMMER: Thomas Weidenmueller <w3seek@reactos.com> 00007 * Johannes Anderwald <janderwald@reactos.com> 00008 * Dmitry Chapyshev <dmitry@reactos.org> 00009 */ 00010 00011 #include "mmsys.h" 00012 00013 #define VOLUME_DIVIDER 0xFFF 00014 00015 typedef struct _IMGINFO 00016 { 00017 HBITMAP hBitmap; 00018 INT cxSource; 00019 INT cySource; 00020 } IMGINFO, *PIMGINFO; 00021 00022 00023 typedef struct _GLOBAL_DATA 00024 { 00025 HMIXER hMixer; 00026 HICON hIconMuted; 00027 HICON hIconUnMuted; 00028 00029 LONG muteVal; 00030 DWORD muteControlID; 00031 00032 DWORD volumeControlID; 00033 DWORD volumeMinimum; 00034 DWORD volumeMaximum; 00035 DWORD volumeValue; 00036 00037 } GLOBAL_DATA, *PGLOBAL_DATA; 00038 00039 00040 static VOID 00041 InitImageInfo(PIMGINFO ImgInfo) 00042 { 00043 BITMAP bitmap; 00044 00045 ZeroMemory(ImgInfo, sizeof(*ImgInfo)); 00046 00047 ImgInfo->hBitmap = LoadImage(hApplet, 00048 MAKEINTRESOURCE(IDB_SPEAKIMG), 00049 IMAGE_BITMAP, 00050 0, 00051 0, 00052 LR_DEFAULTCOLOR); 00053 00054 if (ImgInfo->hBitmap != NULL) 00055 { 00056 GetObject(ImgInfo->hBitmap, sizeof(BITMAP), &bitmap); 00057 00058 ImgInfo->cxSource = bitmap.bmWidth; 00059 ImgInfo->cySource = bitmap.bmHeight; 00060 } 00061 } 00062 00063 00064 VOID 00065 GetMuteControl(PGLOBAL_DATA pGlobalData) 00066 { 00067 MIXERLINE mxln; 00068 MIXERCONTROL mxc; 00069 MIXERLINECONTROLS mxlctrl; 00070 00071 if (pGlobalData->hMixer == NULL) 00072 return; 00073 00074 mxln.cbStruct = sizeof(MIXERLINE); 00075 mxln.dwComponentType = MIXERLINE_COMPONENTTYPE_DST_SPEAKERS; 00076 00077 if (mixerGetLineInfo((HMIXEROBJ)pGlobalData->hMixer, &mxln, MIXER_OBJECTF_HMIXER | MIXER_GETLINEINFOF_COMPONENTTYPE) 00078 != MMSYSERR_NOERROR) return; 00079 00080 mxlctrl.cbStruct = sizeof(MIXERLINECONTROLS); 00081 mxlctrl.dwLineID = mxln.dwLineID; 00082 mxlctrl.dwControlType = MIXERCONTROL_CONTROLTYPE_MUTE; 00083 mxlctrl.cControls = 1; 00084 mxlctrl.cbmxctrl = sizeof(MIXERCONTROL); 00085 mxlctrl.pamxctrl = &mxc; 00086 00087 if (mixerGetLineControls((HMIXEROBJ)pGlobalData->hMixer, &mxlctrl, MIXER_OBJECTF_HMIXER | MIXER_GETLINECONTROLSF_ONEBYTYPE) 00088 != MMSYSERR_NOERROR) return; 00089 00090 pGlobalData->muteControlID = mxc.dwControlID; 00091 } 00092 00093 00094 VOID 00095 GetMuteState(PGLOBAL_DATA pGlobalData) 00096 { 00097 MIXERCONTROLDETAILS_BOOLEAN mxcdMute; 00098 MIXERCONTROLDETAILS mxcd; 00099 00100 if (pGlobalData->hMixer == NULL) 00101 return; 00102 00103 mxcd.cbStruct = sizeof(MIXERCONTROLDETAILS); 00104 mxcd.dwControlID = pGlobalData->muteControlID; 00105 mxcd.cChannels = 1; 00106 mxcd.cMultipleItems = 0; 00107 mxcd.cbDetails = sizeof(MIXERCONTROLDETAILS_BOOLEAN); 00108 mxcd.paDetails = &mxcdMute; 00109 00110 if (mixerGetControlDetails((HMIXEROBJ)pGlobalData->hMixer, &mxcd, MIXER_OBJECTF_HMIXER | MIXER_GETCONTROLDETAILSF_VALUE) 00111 != MMSYSERR_NOERROR) 00112 return; 00113 00114 pGlobalData->muteVal = mxcdMute.fValue; 00115 } 00116 00117 00118 VOID 00119 SwitchMuteState(PGLOBAL_DATA pGlobalData) 00120 { 00121 MIXERCONTROLDETAILS_BOOLEAN mxcdMute; 00122 MIXERCONTROLDETAILS mxcd; 00123 00124 mxcd.cbStruct = sizeof(MIXERCONTROLDETAILS); 00125 mxcd.dwControlID = pGlobalData->muteControlID; 00126 mxcd.cChannels = 1; 00127 mxcd.cMultipleItems = 0; 00128 mxcd.cbDetails = sizeof(MIXERCONTROLDETAILS_BOOLEAN); 00129 mxcd.paDetails = &mxcdMute; 00130 00131 mxcdMute.fValue = !pGlobalData->muteVal; 00132 if (mixerSetControlDetails((HMIXEROBJ)pGlobalData->hMixer, &mxcd, MIXER_OBJECTF_HMIXER | MIXER_SETCONTROLDETAILSF_VALUE) 00133 != MMSYSERR_NOERROR) 00134 return; 00135 00136 pGlobalData->muteVal = mxcdMute.fValue; 00137 } 00138 00139 00140 VOID 00141 GetVolumeControl(PGLOBAL_DATA pGlobalData) 00142 { 00143 MIXERLINE mxln; 00144 MIXERCONTROL mxc; 00145 MIXERLINECONTROLS mxlc; 00146 00147 if (pGlobalData->hMixer == NULL) 00148 return; 00149 00150 mxln.cbStruct = sizeof(MIXERLINE); 00151 mxln.dwComponentType = MIXERLINE_COMPONENTTYPE_DST_SPEAKERS; 00152 if (mixerGetLineInfo((HMIXEROBJ)pGlobalData->hMixer, &mxln, MIXER_OBJECTF_HMIXER | MIXER_GETLINEINFOF_COMPONENTTYPE) 00153 != MMSYSERR_NOERROR) 00154 return; 00155 00156 mxlc.cbStruct = sizeof(MIXERLINECONTROLS); 00157 mxlc.dwLineID = mxln.dwLineID; 00158 mxlc.dwControlType = MIXERCONTROL_CONTROLTYPE_VOLUME; 00159 mxlc.cControls = 1; 00160 mxlc.cbmxctrl = sizeof(MIXERCONTROL); 00161 mxlc.pamxctrl = &mxc; 00162 if (mixerGetLineControls((HMIXEROBJ)pGlobalData->hMixer, &mxlc, MIXER_OBJECTF_HMIXER | MIXER_GETLINECONTROLSF_ONEBYTYPE) 00163 != MMSYSERR_NOERROR) 00164 return; 00165 00166 pGlobalData->volumeMinimum = mxc.Bounds.dwMinimum; 00167 pGlobalData->volumeMaximum = mxc.Bounds.dwMaximum; 00168 pGlobalData->volumeControlID = mxc.dwControlID; 00169 } 00170 00171 00172 VOID 00173 GetVolumeValue(PGLOBAL_DATA pGlobalData) 00174 { 00175 MIXERCONTROLDETAILS_UNSIGNED mxcdVolume; 00176 MIXERCONTROLDETAILS mxcd; 00177 00178 if (pGlobalData->hMixer == NULL) 00179 return; 00180 00181 mxcd.cbStruct = sizeof(MIXERCONTROLDETAILS); 00182 mxcd.dwControlID = pGlobalData->volumeControlID; 00183 mxcd.cChannels = 1; 00184 mxcd.cMultipleItems = 0; 00185 mxcd.cbDetails = sizeof(MIXERCONTROLDETAILS_UNSIGNED); 00186 mxcd.paDetails = &mxcdVolume; 00187 00188 if (mixerGetControlDetails((HMIXEROBJ)pGlobalData->hMixer, &mxcd, MIXER_OBJECTF_HMIXER | MIXER_GETCONTROLDETAILSF_VALUE) 00189 != MMSYSERR_NOERROR) 00190 return; 00191 00192 pGlobalData->volumeValue = mxcdVolume.dwValue; 00193 } 00194 00195 00196 VOID 00197 SetVolumeValue(PGLOBAL_DATA pGlobalData){ 00198 MIXERCONTROLDETAILS_UNSIGNED mxcdVolume; 00199 MIXERCONTROLDETAILS mxcd; 00200 00201 if (pGlobalData->hMixer == NULL) 00202 return; 00203 00204 mxcdVolume.dwValue = pGlobalData->volumeValue; 00205 mxcd.cbStruct = sizeof(MIXERCONTROLDETAILS); 00206 mxcd.dwControlID = pGlobalData->volumeControlID; 00207 mxcd.cChannels = 1; 00208 mxcd.cMultipleItems = 0; 00209 mxcd.cbDetails = sizeof(MIXERCONTROLDETAILS_UNSIGNED); 00210 mxcd.paDetails = &mxcdVolume; 00211 00212 if (mixerSetControlDetails((HMIXEROBJ)pGlobalData->hMixer, &mxcd, MIXER_OBJECTF_HMIXER | MIXER_SETCONTROLDETAILSF_VALUE) 00213 != MMSYSERR_NOERROR) 00214 return; 00215 00216 pGlobalData->volumeValue = mxcdVolume.dwValue; 00217 } 00218 00219 00220 VOID 00221 InitVolumeControls(HWND hwndDlg, PGLOBAL_DATA pGlobalData) 00222 { 00223 UINT NumMixers; 00224 MIXERCAPS mxc; 00225 00226 NumMixers = mixerGetNumDevs(); 00227 if (!NumMixers) 00228 { 00229 EnableWindow(GetDlgItem(hwndDlg, IDC_VOLUME_TRACKBAR), FALSE); 00230 EnableWindow(GetDlgItem(hwndDlg, IDC_MUTE_CHECKBOX), FALSE); 00231 EnableWindow(GetDlgItem(hwndDlg, IDC_ICON_IN_TASKBAR), FALSE); 00232 EnableWindow(GetDlgItem(hwndDlg, IDC_ADVANCED_BTN), FALSE); 00233 EnableWindow(GetDlgItem(hwndDlg, IDC_SPEAKER_SET_BTN), FALSE); 00234 EnableWindow(GetDlgItem(hwndDlg, IDC_SPEAKER_VOL_BTN), FALSE); 00235 EnableWindow(GetDlgItem(hwndDlg, IDC_ADVANCED2_BTN), FALSE); 00236 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconMuted); 00237 return; 00238 } 00239 00240 if (mixerOpen(&pGlobalData->hMixer, 0, PtrToUlong(hwndDlg), 0, MIXER_OBJECTF_MIXER | CALLBACK_WINDOW) != MMSYSERR_NOERROR) 00241 { 00242 MessageBox(hwndDlg, _T("Cannot open mixer"), NULL, MB_OK); 00243 return; 00244 } 00245 00246 ZeroMemory(&mxc, sizeof(MIXERCAPS)); 00247 if (mixerGetDevCaps(PtrToUint(pGlobalData->hMixer), &mxc, sizeof(MIXERCAPS)) != MMSYSERR_NOERROR) 00248 { 00249 MessageBox(hwndDlg, _T("mixerGetDevCaps failed"), NULL, MB_OK); 00250 return; 00251 } 00252 00253 GetMuteControl(pGlobalData); 00254 GetMuteState(pGlobalData); 00255 if (pGlobalData->muteVal) 00256 { 00257 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0); 00258 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconMuted); 00259 } 00260 else 00261 { 00262 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_UNCHECKED, (LPARAM)0); 00263 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconUnMuted); 00264 } 00265 00266 GetVolumeControl(pGlobalData); 00267 GetVolumeValue(pGlobalData); 00268 00269 SendDlgItemMessage(hwndDlg, IDC_DEVICE_NAME, WM_SETTEXT, 0, (LPARAM)mxc.szPname); 00270 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETRANGE, (WPARAM)TRUE, 00271 (LPARAM)MAKELONG(pGlobalData->volumeMinimum, pGlobalData->volumeMaximum/VOLUME_DIVIDER)); 00272 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETPAGESIZE, (WPARAM)FALSE, (LPARAM)1); 00273 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETSEL, (WPARAM)FALSE, 00274 (LPARAM)MAKELONG(pGlobalData->volumeMinimum, pGlobalData->volumeValue/VOLUME_DIVIDER)); 00275 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETPOS, (WPARAM)TRUE, (LPARAM)pGlobalData->volumeValue/VOLUME_DIVIDER); 00276 } 00277 00278 00279 VOID 00280 LaunchSoundControl(HWND hwndDlg) 00281 { 00282 if ((INT_PTR)ShellExecuteW(NULL, L"open", L"sndvol32.exe", NULL, NULL, SW_SHOWNORMAL) > 32) 00283 return; 00284 MessageBox(hwndDlg, _T("Cannot run sndvol32.exe"), NULL, MB_OK); 00285 } 00286 00287 /* Volume property page dialog callback */ 00288 //static INT_PTR CALLBACK 00289 INT_PTR CALLBACK 00290 VolumeDlgProc(HWND hwndDlg, 00291 UINT uMsg, 00292 WPARAM wParam, 00293 LPARAM lParam) 00294 { 00295 static IMGINFO ImgInfo; 00296 PGLOBAL_DATA pGlobalData; 00297 UNREFERENCED_PARAMETER(lParam); 00298 UNREFERENCED_PARAMETER(wParam); 00299 00300 pGlobalData = (PGLOBAL_DATA)GetWindowLongPtr(hwndDlg, DWLP_USER); 00301 00302 00303 00304 switch(uMsg) 00305 { 00306 case MM_MIXM_LINE_CHANGE: 00307 { 00308 GetMuteState(pGlobalData); 00309 if (pGlobalData->muteVal) 00310 { 00311 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0); 00312 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconMuted); 00313 } 00314 else 00315 { 00316 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_UNCHECKED, (LPARAM)0); 00317 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconUnMuted); 00318 } 00319 break; 00320 } 00321 case MM_MIXM_CONTROL_CHANGE: 00322 { 00323 GetVolumeValue(pGlobalData); 00324 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETSEL, (WPARAM)FALSE, (LPARAM)MAKELONG(pGlobalData->volumeMinimum, pGlobalData->volumeValue/VOLUME_DIVIDER)); 00325 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETPOS, (WPARAM)TRUE, (LPARAM)pGlobalData->volumeValue/VOLUME_DIVIDER); 00326 break; 00327 } 00328 case WM_INITDIALOG: 00329 { 00330 pGlobalData = (GLOBAL_DATA*) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(GLOBAL_DATA)); 00331 SetWindowLongPtr(hwndDlg, DWLP_USER, (LONG_PTR)pGlobalData); 00332 00333 pGlobalData->hIconUnMuted = LoadImage(hApplet, MAKEINTRESOURCE(IDI_CPLICON), IMAGE_ICON, 32, 32, LR_DEFAULTCOLOR); 00334 pGlobalData->hIconMuted = LoadImage(hApplet, MAKEINTRESOURCE(IDI_MUTED_ICON), IMAGE_ICON, 32, 32, LR_DEFAULTCOLOR); 00335 00336 InitImageInfo(&ImgInfo); 00337 InitVolumeControls(hwndDlg, pGlobalData); 00338 break; 00339 } 00340 00341 case WM_DRAWITEM: 00342 { 00343 LPDRAWITEMSTRUCT lpDrawItem; 00344 lpDrawItem = (LPDRAWITEMSTRUCT) lParam; 00345 if(lpDrawItem->CtlID == IDC_SPEAKIMG) 00346 { 00347 HDC hdcMem; 00348 LONG left; 00349 00350 /* Position image in centre of dialog */ 00351 left = (lpDrawItem->rcItem.right - ImgInfo.cxSource) / 2; 00352 00353 hdcMem = CreateCompatibleDC(lpDrawItem->hDC); 00354 if (hdcMem != NULL) 00355 { 00356 SelectObject(hdcMem, ImgInfo.hBitmap); 00357 BitBlt(lpDrawItem->hDC, 00358 left, 00359 lpDrawItem->rcItem.top, 00360 lpDrawItem->rcItem.right - lpDrawItem->rcItem.left, 00361 lpDrawItem->rcItem.bottom - lpDrawItem->rcItem.top, 00362 hdcMem, 00363 0, 00364 0, 00365 SRCCOPY); 00366 DeleteDC(hdcMem); 00367 } 00368 } 00369 break; 00370 } 00371 00372 case WM_COMMAND: 00373 { 00374 switch (LOWORD(wParam)) 00375 { 00376 case IDC_MUTE_CHECKBOX: 00377 SwitchMuteState(pGlobalData); 00378 if (pGlobalData->muteVal) 00379 { 00380 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_CHECKED, (LPARAM)0); 00381 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconMuted); 00382 } 00383 else 00384 { 00385 SendDlgItemMessage(hwndDlg, IDC_MUTE_CHECKBOX, BM_SETCHECK, (WPARAM)BST_UNCHECKED, (LPARAM)0); 00386 SendDlgItemMessage(hwndDlg, IDC_MUTE_ICON, STM_SETIMAGE, IMAGE_ICON, (LPARAM)pGlobalData->hIconUnMuted); 00387 } 00388 break; 00389 case IDC_ADVANCED_BTN: 00390 LaunchSoundControl(hwndDlg); 00391 break; 00392 } 00393 break; 00394 } 00395 00396 case WM_HSCROLL: 00397 { 00398 HWND hVolumeTrackbar = GetDlgItem(hwndDlg, IDC_VOLUME_TRACKBAR); 00399 if (hVolumeTrackbar == (HWND)lParam) 00400 { 00401 pGlobalData->volumeValue = (DWORD)SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_GETPOS, 0, 0)*VOLUME_DIVIDER; 00402 SetVolumeValue(pGlobalData); 00403 SendDlgItemMessage(hwndDlg, IDC_VOLUME_TRACKBAR, TBM_SETSEL, (WPARAM)TRUE, 00404 (LPARAM)MAKELONG(pGlobalData->volumeMinimum, pGlobalData->volumeValue/VOLUME_DIVIDER)); 00405 } 00406 break; 00407 } 00408 00409 case WM_DESTROY: 00410 mixerClose(pGlobalData->hMixer); 00411 DestroyIcon(pGlobalData->hIconMuted); 00412 DestroyIcon(pGlobalData->hIconUnMuted); 00413 HeapFree(GetProcessHeap(), 0, pGlobalData); 00414 break; 00415 } 00416 00417 return FALSE; 00418 } Generated on Sat May 26 2012 04:18:07 for ReactOS by
1.7.6.1
|