]> icculus.org git repositories - btb/d2x.git/blob - arch/win32/d3dframe/userdlg.cpp
added UDP support for win32
[btb/d2x.git] / arch / win32 / d3dframe / userdlg.cpp
1 //-----------------------------------------------------------------------------
2 // File: UserDlg.cpp
3 //
4 // Desc: Support functions for the user select driver dialog.
5
6 //       Note: Since this code is destined for a static link library, the
7 //       dialog dox is constructed manually. Otherwise, we would use a resource
8 //       and save many lines of code. Manually constructing dialog boxes is not
9 //       trivial and there are many issues (unicode, dword alignment, etc.)
10 //       involved.
11 //
12 //
13 // Copyright (c) 1997-1998 Microsoft Corporation. All rights reserved.
14 //-----------------------------------------------------------------------------
15
16 #include <tchar.h>
17 #include "D3DEnum.h"
18 #include <stdio.h>
19 #include "d3dutil.h"
20
21
22
23 //-----------------------------------------------------------------------------
24 // Constants and function prototypes for the user select driver dialog
25 //-----------------------------------------------------------------------------
26 #define IDC_STATIC       0xffff
27 #define IDC_DRIVER_COMBO   1000
28 #define IDC_DEVICE_COMBO   1001
29 #define IDC_MODE_COMBO     1002
30
31
32
33
34 //-----------------------------------------------------------------------------
35 // External variables (declared in the D3DEnum.cpp file)
36 //-----------------------------------------------------------------------------
37 extern D3DEnum_DriverInfo* g_pCurrentDriver;     // The selected DD driver
38
39
40
41
42 //-----------------------------------------------------------------------------
43 // Name:  CopyToWideChar
44 //-----------------------------------------------------------------------------
45 static VOID CopyToWideChar( WCHAR** pstrOut, LPTSTR strIn )
46 {
47     DWORD  dwLen  = lstrlen( strIn );
48     WCHAR* strOut = *pstrOut;
49
50 #ifdef UNICODE // Copy Unicode to Unicode
51     _wcsncpy( strOut, strIn, dwLen );
52     strOut[dwLen] = L'\0';
53 #else         // Copy Ansi to Unicode
54     dwLen = MultiByteToWideChar( CP_ACP, 0, strIn, dwLen, strOut, dwLen );
55     strOut[dwLen++] = L'\0'; // Add the null terminator
56 #endif
57     *pstrOut += dwLen;
58 }
59
60
61
62
63 //-----------------------------------------------------------------------------
64 // Name: AddDialogControl()
65 // Desc: Internal function to help build the user select dialog
66 //-----------------------------------------------------------------------------
67 static VOID AddDialogControl( WORD** pp, DWORD dwStyle, SHORT x, SHORT y,
68                               SHORT cx, SHORT cy, WORD id, 
69                               LPTSTR strClassName, LPTSTR strTitle )
70 {
71     // DWORD align the current ptr
72     DLGITEMTEMPLATE* p = (DLGITEMTEMPLATE*)(((((ULONG)(*pp))+3)>>2)<<2);
73
74     p->style           = dwStyle | WS_CHILD | WS_VISIBLE;
75     p->dwExtendedStyle = 0L;
76     p->x               = x;
77     p->y               = y;
78     p->cx              = cx;
79     p->cy              = cy;
80     p->id              = id;
81
82     *pp = (WORD*)(++p); // Advance ptr
83
84     CopyToWideChar( (WCHAR**)pp, strClassName ); // Set Class name
85     CopyToWideChar( (WCHAR**)pp, strTitle );     // Set Title
86
87     (*pp)++;          // Skip Extra Stuff
88 }
89
90
91
92
93 //-----------------------------------------------------------------------------
94 // Name: _BuildUserSelectDialog()
95 // Desc: Internal function to build the user select dialog
96 //-----------------------------------------------------------------------------
97 DLGTEMPLATE* _BuildDriverSelectTemplate()
98 {
99     // Allocate ample memory for building the template
100     DLGTEMPLATE* pDlgTemplate = new DLGTEMPLATE[50];
101     if( NULL == pDlgTemplate )
102         return NULL;
103     ZeroMemory( pDlgTemplate, 50*sizeof(DLGTEMPLATE) );
104     
105     // Fill in the DLGTEMPLATE info
106     DLGTEMPLATE* pdt     = pDlgTemplate;
107     pdt->style           = DS_MODALFRAME | DS_NOIDLEMSG | DS_SETFOREGROUND |
108                            DS_3DLOOK | DS_CENTER | WS_POPUP | WS_VISIBLE |
109                            WS_CAPTION | WS_SYSMENU | DS_SETFONT;
110     pdt->dwExtendedStyle = 0L;
111     pdt->cdit            = 8;
112     pdt->x               = 0;
113     pdt->y               = 0;
114     pdt->cx              = 179;
115     pdt->cy              = 84;
116
117     // Add menu array, class array, dlg title, font size and font name
118     WORD* pw = (WORD*)(++pdt);
119     *pw++ = L'\0';                               // Set Menu array to nothing
120     *pw++ = L'\0';                               // Set Class array to nothing
121     CopyToWideChar( (WCHAR**)&pw, TEXT( "Select New Direct3D Driver" ) ); // Dlg title
122     *pw++ = 8;                                   // Font Size
123     CopyToWideChar( (WCHAR**)&pw, TEXT("Arial") );         // Font Name
124  
125     // Add the okay button
126     AddDialogControl( &pw, BS_PUSHBUTTON | WS_TABSTOP, 65, 65, 51, 14, 
127                       IDOK, TEXT("BUTTON"), TEXT("OK") );
128
129     // Add the cancel button
130     AddDialogControl( &pw, BS_PUSHBUTTON | WS_TABSTOP, 123, 65, 51, 14, 
131                       IDCANCEL, TEXT("BUTTON"), TEXT("Cancel") );
132
133     // Add the driver select combobox
134     AddDialogControl( &pw, CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP, 
135                       36, 5, 138, 45, 
136                       IDC_DRIVER_COMBO, TEXT("COMBOBOX"), TEXT("") );
137
138     // Add the device select combobox
139     AddDialogControl( &pw, CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP, 
140                       36, 24, 138, 45,
141                       IDC_DEVICE_COMBO, TEXT("COMBOBOX"), TEXT("") );
142
143     // Add the mode select combobox
144     AddDialogControl( &pw, CBS_DROPDOWNLIST | WS_VSCROLL | WS_TABSTOP,
145                       36, 44, 138, 45, 
146                       IDC_MODE_COMBO, TEXT("COMBOBOX"), TEXT("") );
147
148     // Add the "Driver:" text
149     AddDialogControl( &pw, SS_LEFT, 5, 5, 22, 13, 
150                       IDC_STATIC, TEXT("STATIC"), TEXT("Driver:") );
151
152     // Add the "Device:" text
153     AddDialogControl( &pw, SS_LEFT, 5, 24, 25, 13,
154                       IDC_STATIC, TEXT("STATIC"), TEXT("Device:") );
155
156     // Add the "Mode:" text
157     AddDialogControl( &pw, SS_LEFT, 5, 44, 22, 13, 
158                       IDC_STATIC, TEXT("STATIC"), TEXT("Mode:") );
159
160     return pDlgTemplate;
161 }
162
163
164
165
166 //-----------------------------------------------------------------------------
167 // Name: UpdateComboBoxesContent()
168 // Desc: Builds the list of drivers, devices and modes for the combo boxes
169 //       in the driver select dialog box.
170 //-----------------------------------------------------------------------------
171 static VOID UpdateComboBoxesContent( HWND hDlg, 
172                                                                  D3DEnum_DriverInfo** ppCurrentDriver, 
173                                      D3DEnum_DeviceInfo** ppCurrentDevice, 
174                                      D3DEnum_ModeInfo** ppCurrentMode,
175                                                                          BOOL bWindowed )
176 {
177     // Check the parameters
178     if( (NULL==ppCurrentDriver) || (NULL==ppCurrentDevice) || 
179         (NULL==ppCurrentMode) )
180         return;
181
182     // If the specified driver is NULL, use the first one in the list
183     if( NULL == *ppCurrentDriver) 
184         (*ppCurrentDriver) = D3DEnum_GetFirstDriver();
185
186     // If the specified device is NULL, use the first one in the list
187     if( NULL == *ppCurrentDevice) 
188         (*ppCurrentDevice) = (*ppCurrentDriver)->pFirstDevice;
189     
190     // Reset the content in each of the combo boxes
191     SendDlgItemMessage( hDlg, IDC_DRIVER_COMBO, CB_RESETCONTENT, 0, 0 );
192     SendDlgItemMessage( hDlg, IDC_DEVICE_COMBO, CB_RESETCONTENT, 0, 0 );
193     SendDlgItemMessage( hDlg, IDC_MODE_COMBO,   CB_RESETCONTENT, 0, 0 );
194
195     // Build the list of drivers for the combo box
196     for( D3DEnum_DriverInfo* pDriver = D3DEnum_GetFirstDriver(); pDriver; 
197          pDriver = pDriver->pNext )
198     {
199         // Add driver desc to the combo box
200         DWORD dwItem = SendDlgItemMessage( hDlg, IDC_DRIVER_COMBO, 
201                            CB_ADDSTRING, 0, (LPARAM)pDriver->strDesc );
202
203         // Associate DriverInfo ptr with the item in the combo box
204         SendDlgItemMessage( hDlg, IDC_DRIVER_COMBO, CB_SETITEMDATA, 
205                             (WPARAM)dwItem, (LPARAM)pDriver );
206
207         // If this is the current driver, set is as the current selection
208         if( pDriver == (*ppCurrentDriver) )
209             SendDlgItemMessage( hDlg, IDC_DRIVER_COMBO, CB_SETCURSEL,
210                                 (WPARAM)dwItem, 0L );
211     }
212
213     // Build the list of devices for the combo box
214     for( D3DEnum_DeviceInfo* pDevice = (*ppCurrentDriver)->pFirstDevice; pDevice;
215          pDevice = pDevice->pNext )
216     {
217         // Add device name to the combo box
218         DWORD dwItem = SendDlgItemMessage( hDlg, IDC_DEVICE_COMBO, 
219                            CB_ADDSTRING, 0, (LPARAM)pDevice->strName );
220
221         // Associate DeviceInfo ptr with the item in the combo box
222         SendDlgItemMessage( hDlg, IDC_DEVICE_COMBO, CB_SETITEMDATA,
223                             (WPARAM)dwItem, (LPARAM)pDevice );
224
225         // If this is the current device, set this as the current selection
226         if( pDevice == (*ppCurrentDevice) )
227             SendDlgItemMessage( hDlg, IDC_DEVICE_COMBO, CB_SETCURSEL, 
228                                 (WPARAM)dwItem, 0L );
229     }
230
231         if( (*ppCurrentDriver)->ddDriverCaps.dwCaps2 & DDCAPS2_CANRENDERWINDOWED 
232         && ( NULL == (*ppCurrentDriver)->pGUID )
233                 && (*ppCurrentDevice)->bCompatbileWithDesktop )
234         {
235                 // Add windowed mode to the combo box of available modes
236         DWORD dwItem = SendDlgItemMessage( hDlg, IDC_MODE_COMBO, 
237                            CB_ADDSTRING, 0, (LPARAM)TEXT("Windowed mode") );
238         
239                 // Associate ModeInfo ptr with the item in the combo box
240         SendDlgItemMessage( hDlg, IDC_MODE_COMBO, CB_SETITEMDATA, 
241                             (WPARAM)dwItem, (LPARAM)NULL );
242
243         // If the current device is windowed, set this as current
244         if( bWindowed )
245             SendDlgItemMessage( hDlg, IDC_MODE_COMBO, CB_SETCURSEL, 
246                                 (WPARAM)dwItem, 0L );
247         }
248
249     // Build the list of modes for the combo box
250     for( D3DEnum_ModeInfo* pMode = (*ppCurrentDevice)->pFirstMode; pMode; 
251          pMode = pMode->pNext )
252     {
253         // Add mode desc to the combo box
254         DWORD dwItem = SendDlgItemMessage( hDlg, IDC_MODE_COMBO, 
255                                            CB_ADDSTRING, 0,
256                                            (LPARAM)pMode->strDesc );
257
258         // Associate ModeInfo ptr with the item in the combo box
259         SendDlgItemMessage( hDlg, IDC_MODE_COMBO, CB_SETITEMDATA, 
260                             (WPARAM)dwItem, (LPARAM)pMode );
261
262         // If this is the current mode, set is as the current selection
263         if( !bWindowed && ( pMode == (*ppCurrentMode) ) )
264                                 SendDlgItemMessage( hDlg, IDC_MODE_COMBO, CB_SETCURSEL, 
265                                                                         (WPARAM)dwItem, 0L );
266     }   
267 }
268
269
270
271
272 //-----------------------------------------------------------------------------
273 // Name: _DriverSelectProc()
274 // Desc: Windows message handling function for the driver select dialog
275 //-----------------------------------------------------------------------------
276 BOOL CALLBACK _DriverSelectProc( HWND hDlg, UINT uiMsg, WPARAM wParam, 
277                                  LPARAM lParam )
278 {
279     static D3DEnum_DriverInfo *pOldDriver,  *pNewDriver;
280     static D3DEnum_DeviceInfo *pOldDevice,  *pNewDevice;
281     static D3DEnum_ModeInfo   *pOldMode,    *pNewMode;
282     static BOOL                bOldWindowed, bNewWindowed;
283
284     // Handle the initialization message
285     if( WM_INITDIALOG == uiMsg )
286     {
287         // Setup temp storage pointers for dialog
288         pNewDriver   = pOldDriver   = g_pCurrentDriver;
289         pNewDevice   = pOldDevice   = pOldDriver->pCurrentDevice;
290         pNewMode     = pOldMode     = pOldDevice->pCurrentMode;
291                 bNewWindowed = bOldWindowed = pOldDevice->bWindowed;
292
293         UpdateComboBoxesContent( hDlg, &pOldDriver, &pOldDevice, 
294                                  &pOldMode, bOldWindowed );
295         return TRUE;
296     }
297     
298     if( WM_COMMAND == uiMsg )
299     {
300         // Handle the case when the user hits the OK button
301         if( IDOK == LOWORD(wParam) )
302         {
303             // Check if any of the options were changed
304             if( ( pOldDriver != pNewDriver ) || ( pOldDevice != pNewDevice ) ||
305                 ( pOldMode != pNewMode ) || ( bOldWindowed != bNewWindowed ) )
306             {
307                                 // Set actual ptrs from the temp ptrs used for the dialog
308                 g_pCurrentDriver = pNewDriver;
309                 g_pCurrentDriver->pCurrentDevice = pNewDevice;
310                 g_pCurrentDriver->pCurrentDevice->pCurrentMode = pNewMode;
311                 g_pCurrentDriver->pCurrentDevice->bWindowed    = bNewWindowed;
312  
313                 EndDialog( hDlg, IDOK );
314                 return TRUE;
315             }
316             else
317             {
318                 EndDialog( hDlg, IDCANCEL );
319                 return TRUE;
320             }
321         }
322
323         // Handle the case when the user hits the Cancel button
324         else if( IDCANCEL == LOWORD(wParam) )
325         {
326             EndDialog( hDlg, IDCANCEL );
327             return TRUE;
328         }
329
330         // Handle the case when the user chooses an item in the combo boxes.
331         else if( CBN_SELENDOK == HIWORD(wParam) )
332         {
333             DWORD dwIndex    = SendMessage( (HWND)lParam, CB_GETCURSEL, 
334                                             0, 0 );
335             LONG  pNewObject = SendMessage( (HWND)lParam, CB_GETITEMDATA,
336                                             dwIndex, 0 );
337             
338             if( (CB_ERR==dwIndex) )
339                 return TRUE;
340
341             // Handle the case where one of these may have changed. The
342             // combo boxes will need to be updated to reflect the changes.
343             switch( LOWORD( wParam ) )
344             {
345                 case IDC_DRIVER_COMBO:
346                     if( pNewObject && pNewObject != (LONG)pNewDriver )
347                     {
348                         pNewDriver   = (D3DEnum_DriverInfo*)pNewObject;
349                         pNewDevice   = pNewDriver->pCurrentDevice;;
350                         pNewMode     = pNewDevice->pCurrentMode;
351                                                 bNewWindowed = pNewDevice->bWindowed;
352                     }
353                     break;
354                 case IDC_DEVICE_COMBO:
355                     if( pNewObject && pNewObject != (LONG)pNewDevice )
356                                         {
357                         pNewDevice   = (D3DEnum_DeviceInfo*)pNewObject;
358                         pNewMode     = pNewDevice->pCurrentMode;
359                                                 bNewWindowed = pNewDevice->bWindowed;
360                                         }
361                     break;
362                 case IDC_MODE_COMBO:
363                                         if( pNewObject )
364                                         {
365                                                 pNewMode = (D3DEnum_ModeInfo*)pNewObject;
366                                                 bNewWindowed = FALSE;
367                                         }
368                                         else
369                                                 bNewWindowed = TRUE;
370                     break;
371             }
372
373             UpdateComboBoxesContent( hDlg, &pNewDriver, &pNewDevice,
374                                      &pNewMode, bNewWindowed );
375
376             return TRUE;
377         }
378     }
379     return FALSE;
380 }
381
382
383