Source code of Windows XP (NT5)
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

441 lines
12 KiB

  1. /*****************************************************************************
  2. *
  3. * diqmode.c
  4. *
  5. * "Mode" property sheet page.
  6. *
  7. *****************************************************************************/
  8. #include "diquick.h"
  9. /*****************************************************************************
  10. *
  11. * Common_AcqSetDataFormat
  12. *
  13. * Common worker function that sets the data format.
  14. *
  15. *****************************************************************************/
  16. STDMETHODIMP
  17. Common_AcqSetDataFormat(PDEVDLGINFO pddi)
  18. {
  19. return IDirectInputDevice8_SetDataFormat(pddi->pdid, pddi->pvtbl->pdf);
  20. }
  21. /*****************************************************************************
  22. *
  23. * Common_AcqDestroy
  24. *
  25. * Common worker function that doesn't do anything.
  26. *
  27. *****************************************************************************/
  28. STDMETHODIMP_(void)
  29. Common_AcqDestroy(PDEVDLGINFO pddi)
  30. {
  31. }
  32. /*****************************************************************************
  33. *
  34. * Mode_SyncCheckButtons
  35. *
  36. * Sync the dialog buttons with the IDirectInputXxx object.
  37. *
  38. *****************************************************************************/
  39. void INTERNAL
  40. Mode_SyncCheckButtons(PDEVDLGINFO pddi, HWND hdlg)
  41. {
  42. UINT idc;
  43. DWORD dw;
  44. switch (pddi->discl) {
  45. default:
  46. case DISCL_BACKGROUND | DISCL_NONEXCLUSIVE:
  47. idc = IDC_DEV_PASSIVE; break;
  48. case DISCL_FOREGROUND | DISCL_NONEXCLUSIVE:
  49. idc = IDC_DEV_PASSIVE_FOREGROUND; break;
  50. case DISCL_BACKGROUND | DISCL_EXCLUSIVE:
  51. idc = IDC_DEV_ACTIVE_BACKGROUND; break;
  52. case DISCL_FOREGROUND | DISCL_EXCLUSIVE:
  53. idc = IDC_DEV_ACTIVE; break;
  54. }
  55. CheckRadioButton(hdlg, IDC_DEV_PASSIVE, IDC_DEV_ACTIVE, idc);
  56. CheckRadioButton(hdlg, IDC_DEV_POLLED, IDC_DEV_EVENT,
  57. pddi->fPoll ? IDC_DEV_POLLED : IDC_DEV_EVENT);
  58. EnableWindow(GetDlgItem(hdlg, IDC_DEV_NOWINKEY), FALSE);
  59. if (pddi->pvtbl == &c_acqvtblDevMouse || pddi->pvtbl == &c_acqvtblDevMouse2 ) {
  60. idc = IDC_DEV_MOUSE;
  61. } else if (pddi->pvtbl == &c_acqvtblDevKbd) {
  62. idc = IDC_DEV_KEYBOARD;
  63. EnableWindow(GetDlgItem(hdlg, IDC_DEV_NOWINKEY), TRUE);
  64. } else if (pddi->pvtbl == &c_acqvtblDevJoy) {
  65. idc = IDC_DEV_JOYSTICK;
  66. } else if (pddi->pvtbl == &c_acqvtblDev) {
  67. idc = IDC_DEV_DEVICE;
  68. } else {
  69. idc = 0;
  70. }
  71. CheckRadioButton(hdlg, IDC_DEV_MOUSE, IDC_DEV_DEVICE, idc);
  72. if (SUCCEEDED(GetDwordProperty(pddi->pdid, DIPROP_AXISMODE, &dw))) {
  73. CheckRadioButton(hdlg, IDC_DEV_ABS, IDC_DEV_REL,
  74. dw == DIPROPAXISMODE_ABS ? IDC_DEV_ABS
  75. : IDC_DEV_REL);
  76. }
  77. if (SUCCEEDED(GetDwordProperty(pddi->pdid, DIPROP_CALIBRATIONMODE, &dw))) {
  78. } else {
  79. dw = 0;
  80. }
  81. CheckDlgButton(hdlg, IDC_DEV_CAL, dw);
  82. }
  83. /*****************************************************************************
  84. *
  85. * Mode_OnDataFormat
  86. *
  87. * Change the device data format.
  88. *
  89. *****************************************************************************/
  90. BOOL INTERNAL
  91. Mode_OnDataFormat(PDEVDLGINFO pddi, HWND hdlg, UINT id)
  92. {
  93. DIDEVCAPS didc;
  94. HRESULT hres;
  95. UINT idDev;
  96. /*
  97. * Kill the old data format before setting the new one.
  98. */
  99. if (pddi->pvtbl) {
  100. pddi->pvtbl->Destroy(pddi);
  101. }
  102. if( id == 0 ) { //from On_InitDialog
  103. didc.dwSize = cbX(DIDEVCAPS_DX3);
  104. hres = IDirectInputDevice8_GetCapabilities(pddi->pdid, &didc);
  105. if (SUCCEEDED(hres))
  106. idDev = GET_DIDEVICE_TYPE(didc.dwDevType);
  107. } else
  108. idDev = id+0x100; // Hack, add 0x100 to make sure ranges do not overlap
  109. switch (idDev) {
  110. case DI8DEVTYPE_MOUSE:
  111. case IDC_DEV_MOUSE+0x100:
  112. #if DIRECTINPUT_VERSION >= 0x700
  113. pddi->pvtbl = &c_acqvtblDevMouse2;
  114. #else
  115. pddi->pvtbl = &c_acqvtblDevMouse;
  116. #endif
  117. break;
  118. case DI8DEVTYPE_KEYBOARD:
  119. case IDC_DEV_KEYBOARD+0x100:
  120. pddi->pvtbl = &c_acqvtblDevKbd;
  121. break;
  122. case DI8DEVTYPE_JOYSTICK:
  123. case DI8DEVTYPE_GAMEPAD:
  124. case DI8DEVTYPE_DRIVING:
  125. case DI8DEVTYPE_FLIGHT:
  126. case DI8DEVTYPE_1STPERSON:
  127. case DI8DEVTYPE_DEVICECTRL:
  128. case DI8DEVTYPE_SCREENPOINTER:
  129. case DI8DEVTYPE_REMOTE:
  130. case DI8DEVTYPE_SUPPLEMENTAL:
  131. case IDC_DEV_JOYSTICK+0x100:
  132. pddi->pvtbl = &c_acqvtblDevJoy;
  133. break;
  134. case DI8DEVTYPE_DEVICE:
  135. case IDC_DEV_DEVICE+0x100:
  136. pddi->pvtbl = &c_acqvtblDev;
  137. break;
  138. }
  139. if (pddi->pvtbl) {
  140. HRESULT hres;
  141. hres = pddi->pvtbl->SetDataFormat(pddi);
  142. if (FAILED(hres)) {
  143. MessageBoxV(GetParent(hdlg), IDS_ERR_DATAFORMAT);
  144. }
  145. }
  146. /* Always sync buttons, because the data format may change axis modes */
  147. Mode_SyncCheckButtons(pddi, hdlg);
  148. return 1;
  149. }
  150. /*****************************************************************************
  151. *
  152. * Mode_OnInitDialog
  153. *
  154. * Set up all the random switches.
  155. *
  156. * Notice that GetCapabilities is in the same location in all the
  157. * DirectInputXxx interfaces.
  158. *
  159. *****************************************************************************/
  160. #pragma BEGIN_CONST_DATA
  161. /*
  162. * Acceleration info: Accelerate in steps of 32, then 128.
  163. */
  164. UDACCEL c_uda[] = {
  165. { 0, 32 },
  166. { 1, 128 },
  167. };
  168. #pragma END_CONST_DATA
  169. BOOL INTERNAL
  170. Mode_OnInitDialog(HWND hdlg, LPARAM lp)
  171. {
  172. PDEVDLGINFO pddi = (PV)(((LPPROPSHEETPAGE)lp)->lParam);
  173. SetDialogPtr(hdlg, pddi);
  174. CheckRadioButton(hdlg, IDC_DEV_ABS, IDC_DEV_REL, IDC_DEV_ABS);
  175. /*
  176. * Note that we do not check any device format.
  177. * This lets us make sure that things work when nothing is selected.
  178. */
  179. Mode_SyncCheckButtons(pddi, hdlg);
  180. /*
  181. * Configure the buffer size edit and its updown control.
  182. */
  183. SetDlgItemInt(hdlg, IDC_DEV_BUFSIZE, 0, 0);
  184. SendDlgItemMessage(hdlg, IDC_DEV_BUFSIZEUD, UDM_SETACCEL,
  185. cA(c_uda), (LPARAM)&c_uda);
  186. SendDlgItemMessage(hdlg, IDC_DEV_BUFSIZEUD, UDM_SETRANGE,
  187. 0, MAKELONG(1025, 0)); /* 1025 is illegal */
  188. Mode_OnDataFormat( pddi, hdlg, 0 );
  189. return 1;
  190. }
  191. /*****************************************************************************
  192. *
  193. * Mode_OnCooperativity
  194. *
  195. *****************************************************************************/
  196. BOOL INTERNAL
  197. Mode_OnCooperativity(PDEVDLGINFO pddi, HWND hdlg, int id)
  198. {
  199. HRESULT hres;
  200. DWORD discl = 0;
  201. switch (id) {
  202. case IDC_DEV_ACTIVE_BACKGROUND:
  203. discl = DISCL_BACKGROUND | DISCL_EXCLUSIVE; break;
  204. case IDC_DEV_ACTIVE:
  205. discl = DISCL_FOREGROUND | DISCL_EXCLUSIVE; break;
  206. case IDC_DEV_PASSIVE_FOREGROUND:
  207. discl = DISCL_FOREGROUND | DISCL_NONEXCLUSIVE; break;
  208. case IDC_DEV_PASSIVE:
  209. discl = DISCL_BACKGROUND | DISCL_NONEXCLUSIVE; break;
  210. case IDC_DEV_NOWINKEY:
  211. if( IsDlgButtonChecked(hdlg, IDC_DEV_NOWINKEY) ) {
  212. discl = pddi->disclLastTry | DISCL_NOWINKEY;
  213. } else {
  214. discl = pddi->disclLastTry & ~DISCL_NOWINKEY;
  215. }
  216. }
  217. if( id != IDC_DEV_NOWINKEY ) {
  218. if( IsDlgButtonChecked(hdlg, IDC_DEV_NOWINKEY) ) {
  219. discl = discl | DISCL_NOWINKEY;
  220. } else {
  221. discl = discl & ~DISCL_NOWINKEY;
  222. }
  223. }
  224. if (discl != pddi->disclLastTry && discl != pddi->discl) {
  225. pddi->disclLastTry = discl;
  226. hres = IDirectInputDevice8_SetCooperativeLevel(pddi->pdid,
  227. GetParent(hdlg), discl);
  228. if (SUCCEEDED(hres)) {
  229. pddi->discl = discl;
  230. } else {
  231. CheckDlgButton( hdlg, IDC_DEV_NOWINKEY, BST_UNCHECKED );
  232. Mode_SyncCheckButtons(pddi, hdlg);
  233. MessageBoxV(GetParent(hdlg), IDS_ERR_COOPERATIVITY);
  234. }
  235. }
  236. return 1;
  237. }
  238. /*****************************************************************************
  239. *
  240. * Mode_OnDataMode
  241. *
  242. *****************************************************************************/
  243. BOOL INTERNAL
  244. Mode_OnDataMode(PDEVDLGINFO pddi, HWND hdlg, int id)
  245. {
  246. pddi->fPoll = (id == IDC_DEV_POLLED);
  247. return 1;
  248. }
  249. /*****************************************************************************
  250. *
  251. * Mode_OnAxisMode
  252. *
  253. *****************************************************************************/
  254. BOOL INTERNAL
  255. Mode_OnAxisMode(PDEVDLGINFO pddi, HWND hdlg, int id)
  256. {
  257. if (pddi && pddi->pdid) {
  258. DWORD dwMode;
  259. HRESULT hres;
  260. if (id == IDC_DEV_ABS) {
  261. dwMode = DIPROPAXISMODE_ABS;
  262. } else {
  263. dwMode = DIPROPAXISMODE_REL;
  264. }
  265. hres = SetDwordProperty(pddi->pdid, DIPROP_AXISMODE, dwMode);
  266. if (SUCCEEDED(hres)) {
  267. } else {
  268. MessageBoxV(GetParent(hdlg), IDS_ERR_AXISMODE);
  269. }
  270. }
  271. return 1;
  272. }
  273. /*****************************************************************************
  274. *
  275. * Mode_OnCalMode
  276. *
  277. *****************************************************************************/
  278. BOOL INTERNAL
  279. Mode_OnCalMode(PDEVDLGINFO pddi, HWND hdlg)
  280. {
  281. if (pddi && pddi->pdid) {
  282. DWORD dwMode;
  283. HRESULT hres;
  284. dwMode = IsDlgButtonChecked(hdlg, IDC_DEV_CAL);
  285. hres = SetDwordProperty(pddi->pdid, DIPROP_CALIBRATIONMODE, dwMode);
  286. if (SUCCEEDED(hres)) {
  287. } else {
  288. MessageBoxV(GetParent(hdlg), IDS_ERR_CALMODE);
  289. }
  290. }
  291. return 1;
  292. }
  293. /*****************************************************************************
  294. *
  295. * Mode_SyncBufferSize
  296. *
  297. *****************************************************************************/
  298. BOOL INTERNAL
  299. Mode_SyncBufferSize(PDEVDLGINFO pddi, HWND hdlg)
  300. {
  301. if (pddi && pddi->pdid) {
  302. UINT ui = GetDlgItemInt(hdlg, IDC_DEV_BUFSIZE, 0, 0);
  303. HRESULT hres;
  304. hres = SetDwordProperty(pddi->pdid, DIPROP_BUFFERSIZE, ui);
  305. if (SUCCEEDED(hres)) {
  306. } else {
  307. MessageBoxV(GetParent(hdlg), IDS_ERR_BUFFERSIZE);
  308. }
  309. }
  310. return 1;
  311. }
  312. /*****************************************************************************
  313. *
  314. * Mode_OnCommand
  315. *
  316. *****************************************************************************/
  317. BOOL INTERNAL
  318. Mode_OnCommand(HWND hdlg, int id, UINT cmd)
  319. {
  320. PDEVDLGINFO pddi = GetDialogPtr(hdlg);
  321. if (cmd == BN_CLICKED) {
  322. switch (id) {
  323. case IDC_DEV_PASSIVE:
  324. case IDC_DEV_PASSIVE_FOREGROUND:
  325. case IDC_DEV_ACTIVE_BACKGROUND:
  326. case IDC_DEV_ACTIVE:
  327. case IDC_DEV_NOWINKEY:
  328. return Mode_OnCooperativity(pddi, hdlg, id);
  329. case IDC_DEV_POLLED:
  330. case IDC_DEV_EVENT: return Mode_OnDataMode(pddi, hdlg, id);
  331. case IDC_DEV_ABS:
  332. case IDC_DEV_REL: return Mode_OnAxisMode(pddi, hdlg, id);
  333. case IDC_DEV_CAL: return Mode_OnCalMode(pddi, hdlg);
  334. case IDC_DEV_MOUSE:
  335. case IDC_DEV_KEYBOARD:
  336. case IDC_DEV_JOYSTICK:
  337. case IDC_DEV_DEVICE: return Mode_OnDataFormat(pddi, hdlg, id);
  338. }
  339. } else if (cmd == EN_UPDATE) {
  340. if (id == IDC_DEV_BUFSIZE) {
  341. return Mode_SyncBufferSize(pddi, hdlg);
  342. }
  343. }
  344. return 0;
  345. }
  346. /*****************************************************************************
  347. *
  348. * Mode_DlgProc
  349. *
  350. *****************************************************************************/
  351. INT_PTR CALLBACK
  352. Mode_DlgProc(HWND hdlg, UINT wm, WPARAM wp, LPARAM lp)
  353. {
  354. switch (wm) {
  355. case WM_INITDIALOG: return Mode_OnInitDialog(hdlg, lp);
  356. case WM_COMMAND:
  357. return Mode_OnCommand(hdlg,
  358. (int)GET_WM_COMMAND_ID(wp, lp),
  359. (UINT)GET_WM_COMMAND_CMD(wp, lp));
  360. }
  361. return 0;
  362. }