1 #include "LDViewPreferences.h"
2 #include <CUI/CUIDialog.h>
3 #pragma warning(push)
4 #pragma warning(disable:4091)
5 #include <shlobj.h>
6 #include <shlwapi.h>
7 #pragma warning(pop)
8 #include <LDLib/LDrawModelViewer.h>
9 #include <LDLib/LDPreferences.h>
10 #include <LDLoader/LDLPalette.h>
11 #include <TCFoundation/TCMacros.h>
12 #include <TCFoundation/TCWebClient.h>
13 #include "LDVExtensionsSetup.h"
14 #include "Resource.h"
15 #include <LDLib/LDUserDefaultsKeys.h>
16 #include "ModelWindow.h"
17 #include "LDViewWindow.h"
18 #include <CUI/CUIScaler.h>
19
20 #include <TCFoundation/TCUserDefaults.h>
21 #include <TCFoundation/mystring.h>
22 #include <TCFoundation/TCStringArray.h>
23 #include <TCFoundation/TCAlertManager.h>
24 #include <Commctrl.h>
25 #include <stdio.h>
26 //#include <tmschema.h>
27 #include <TRE/TREGLExtensions.h>
28 #include <HtmlHelp.h>
29
30 #if defined(_MSC_VER) && _MSC_VER >= 1400 && defined(_DEBUG)
31 #define new DEBUG_CLIENTBLOCK
32 #endif // _DEBUG
33
34 //#define WILLY_DEBUG
35
36 #ifdef WILLY_DEBUG
WillyMessage(const char * message)37 void WillyMessage(const char *message)
38 {
39 FILE *debugFile = ucfopen("C:\\LDView-Debug.txt", "a");
40 if (debugFile)
41 {
42 fprintf(debugFile, "%s\n", message);
43 fclose(debugFile);
44 }
45 }
46 #else // WILLY_DEBUG
WillyMessage(const char *)47 void WillyMessage(const char *)
48 {
49 }
50 #endif //WILLY_DEBUG
51
52 #ifndef IDC_HARDWARE_STEREO
53 #define IDC_HARDWARE_STEREO 1030
54 #endif
55
56 #if (_WIN32_WINNT < 0x0500)
57 #define ODS_NOFOCUSRECT 0x0200
58 #endif // (_WIN32_WINNT < 0x0500)
59
60 #define DEFAULT_PREF_SET ls(_UC("DefaultPrefSet"))
61
62 ucstring LDViewPreferences::ldviewPath;
63
LDViewPreferences(HINSTANCE hInstance,LDrawModelViewer * modelViewer)64 LDViewPreferences::LDViewPreferences(HINSTANCE hInstance,
65 LDrawModelViewer* modelViewer)
66 :CUIPropertySheet(ls(_UC("LDViewPreferences")), hInstance),
67 modelViewer(modelViewer ? ((LDrawModelViewer*)modelViewer->retain()) :
68 NULL),
69 ldPrefs(new LDPreferences(modelViewer)),
70 generalPageNumber(0),
71 geometryPageNumber(1),
72 effectsPageNumber(2),
73 primitivesPageNumber(3),
74 updatesPageNumber(4),
75 prefSetsPageNumber(5),
76 hGeneralPage(NULL),
77 hBackgroundColorBitmap(NULL),
78 hBackgroundColorButton(NULL),
79 hDefaultColorBitmap(NULL),
80 hDefaultColorButton(NULL),
81 hMouseOverButton(NULL),
82 origButtonWindowProc(NULL),
83 hButtonColorDC(NULL),
84 hGeometryPage(NULL),
85 hEffectsPage(NULL),
86 hPrimitivesPage(NULL),
87 hUpdatesPage(NULL),
88 hPrefSetsPage(NULL),
89 setActiveWarned(false),
90 checkAbandon(true),
91 hButtonTheme(NULL)
92 // hTabTheme(NULL)
93 {
94 WillyMessage("\n\n\n");
95 CUIThemes::init();
96 loadSettings();
97 applySettings();
98 TCAlertManager::registerHandler(TCUserDefaults::alertClass(), this,
99 (TCAlertCallback)&LDViewPreferences::userDefaultChangedAlertCallback);
100 TCAlertManager::registerHandler(
101 LDPreferences::lightVectorChangedAlertClass(), this,
102 (TCAlertCallback)&LDViewPreferences::lightVectorChangedCallback);
103 lightDirIndexToId[0] = IDR_LIGHT_ANGLE_UL;
104 lightDirIndexToId[1] = IDR_LIGHT_ANGLE_UM;
105 lightDirIndexToId[2] = IDR_LIGHT_ANGLE_UR;
106 lightDirIndexToId[3] = IDR_LIGHT_ANGLE_ML;
107 lightDirIndexToId[4] = IDR_LIGHT_ANGLE_MM;
108 lightDirIndexToId[5] = IDR_LIGHT_ANGLE_MR;
109 lightDirIndexToId[6] = IDR_LIGHT_ANGLE_LL;
110 lightDirIndexToId[7] = IDR_LIGHT_ANGLE_LM;
111 lightDirIndexToId[8] = IDR_LIGHT_ANGLE_LR;
112 for (IntIntMap::const_iterator it = lightDirIndexToId.begin()
113 ; it != lightDirIndexToId.end(); it++)
114 {
115 lightDirIdToIndex[it->second] = it->first;
116 }
117 }
118
~LDViewPreferences(void)119 LDViewPreferences::~LDViewPreferences(void)
120 {
121 }
122
dealloc(void)123 void LDViewPreferences::dealloc(void)
124 {
125 TCAlertManager::unregisterHandler(this);
126 TCObject::release(modelViewer);
127 TCObject::release(ldPrefs);
128 if (hButtonTheme)
129 {
130 CUIThemes::closeThemeData(hButtonTheme);
131 hButtonTheme = NULL;
132 }
133 /*
134 if (hTabTheme)
135 {
136 CUIThemes::closeThemeData(hTabTheme);
137 hTabTheme = NULL;
138 }
139 */
140 CUIPropertySheet::dealloc();
141 }
142
lightVectorChangedCallback(TCAlert *)143 void LDViewPreferences::lightVectorChangedCallback(TCAlert * /*alert*/)
144 {
145 checkLightVector();
146 }
147
userDefaultChangedAlertCallback(TCAlert * alert)148 void LDViewPreferences::userDefaultChangedAlertCallback(TCAlert *alert)
149 {
150 const char *key = alert->getMessage();
151
152 if (key)
153 {
154 if (strcmp(key, CHECK_PART_TRACKER_KEY) == 0)
155 {
156 if (hUpdatesPage)
157 {
158 setCheck(hUpdatesPage, IDC_CHECK_PART_TRACKER,
159 ldPrefs->getCheckPartTracker());
160 }
161 }
162 }
163 }
164
applySettings(void)165 void LDViewPreferences::applySettings(void)
166 {
167 ldPrefs->applySettings();
168 }
169
loadSettings(void)170 void LDViewPreferences::loadSettings(void)
171 {
172 ldPrefs->loadSettings();
173 }
174
getColor(const char * key,COLORREF defaultColor)175 COLORREF LDViewPreferences::getColor(const char *key, COLORREF defaultColor)
176 {
177 return (COLORREF)htonl(TCUserDefaults::longForKey(key,
178 (long)(htonl(defaultColor) >> 8)) << 8);
179 }
180
setColor(const char * key,COLORREF color)181 void LDViewPreferences::setColor(const char *key, COLORREF color)
182 {
183 TCUserDefaults::setLongForKey((long)(htonl(color) >> 8), key);
184 }
185
setUseSeams(bool value)186 void LDViewPreferences::setUseSeams(bool value)
187 {
188 if (value != ldPrefs->getUseSeams())
189 {
190 ldPrefs->setUseSeams(value, true, true);
191 if (hGeometryPage)
192 {
193 setCheck(hGeometryPage, IDC_SEAMS, value);
194 if (value)
195 {
196 enableSeams();
197 }
198 else
199 {
200 disableSeams();
201 }
202 }
203 }
204 }
205
setDrawWireframe(bool value)206 void LDViewPreferences::setDrawWireframe(bool value)
207 {
208 if (value != ldPrefs->getDrawWireframe())
209 {
210 ldPrefs->setDrawWireframe(value, true, true);
211 if (hGeometryPage)
212 {
213 setupGroupCheckButton(hGeometryPage, IDC_WIREFRAME, value);
214 if (value)
215 {
216 enableWireframe();
217 }
218 else
219 {
220 disableWireframe();
221 }
222 }
223 }
224 }
225
setUseWireframeFog(bool value)226 void LDViewPreferences::setUseWireframeFog(bool value)
227 {
228 if (value != ldPrefs->getUseWireframeFog())
229 {
230 ldPrefs->setUseWireframeFog(value, true, true);
231 if (hGeometryPage)
232 {
233 setCheck(hGeometryPage, IDC_WIREFRAME_FOG, value);
234 }
235 }
236 }
237
setRemoveHiddenLines(bool value)238 void LDViewPreferences::setRemoveHiddenLines(bool value)
239 {
240 if (value != ldPrefs->getRemoveHiddenLines())
241 {
242 ldPrefs->setRemoveHiddenLines(value, true, true);
243 if (hGeometryPage)
244 {
245 setCheck(hGeometryPage, IDC_REMOVE_HIDDEN_LINES, value);
246 }
247 }
248 }
249
setEdgesOnly(bool value)250 void LDViewPreferences::setEdgesOnly(bool value)
251 {
252 if (value != ldPrefs->getEdgesOnly())
253 {
254 ldPrefs->setEdgesOnly(value, true, true);
255 if (hGeometryPage)
256 {
257 setCheck(hGeometryPage, IDC_EDGES_ONLY, value);
258 }
259 }
260 }
261
getFullScreenRefresh(void)262 int LDViewPreferences::getFullScreenRefresh(void)
263 {
264 return ldPrefs->getFullScreenRefresh();
265 }
266
getSeamWidth(void)267 int LDViewPreferences::getSeamWidth(void)
268 {
269 return ldPrefs->getSeamWidth();
270 }
271
getQualityLighting(void)272 bool LDViewPreferences::getQualityLighting(void)
273 {
274 return ldPrefs->getQualityLighting();
275 }
276
getUsesFlatShading(void)277 bool LDViewPreferences::getUsesFlatShading(void)
278 {
279 return ldPrefs->getUseFlatShading();
280 }
281
getCutawayMode(void)282 LDVCutawayMode LDViewPreferences::getCutawayMode(void)
283 {
284 return ldPrefs->getCutawayMode();
285 }
286
getUsesSpecular(void)287 bool LDViewPreferences::getUsesSpecular(void)
288 {
289 return ldPrefs->getUseSpecular();
290 }
291
getOneLight(void)292 bool LDViewPreferences::getOneLight(void)
293 {
294 return ldPrefs->getOneLight();
295 }
296
getDrawLightDats(void)297 bool LDViewPreferences::getDrawLightDats(void)
298 {
299 return ldPrefs->getDrawLightDats();
300 }
301
getOptionalStandardLight(void)302 bool LDViewPreferences::getOptionalStandardLight(void)
303 {
304 return ldPrefs->getOptionalStandardLight();
305 }
306
getPerformSmoothing(void)307 bool LDViewPreferences::getPerformSmoothing(void)
308 {
309 return ldPrefs->getPerformSmoothing();
310 }
311
getShowsFPS(void)312 bool LDViewPreferences::getShowsFPS(void)
313 {
314 return ldPrefs->getShowFps();
315 }
316
getLineSmoothing(void)317 bool LDViewPreferences::getLineSmoothing(void)
318 {
319 return ldPrefs->getLineSmoothing();
320 }
321
getQualityStuds(void)322 bool LDViewPreferences::getQualityStuds(void)
323 {
324 return ldPrefs->getQualityStuds();
325 }
326
getAllowPrimitiveSubstitution(void)327 bool LDViewPreferences::getAllowPrimitiveSubstitution(void)
328 {
329 return ldPrefs->getAllowPrimitiveSubstitution();
330 }
331
getShowsHighlightLines(void)332 bool LDViewPreferences::getShowsHighlightLines(void)
333 {
334 return ldPrefs->getShowHighlightLines();
335 }
336
getEdgesOnly(void)337 bool LDViewPreferences::getEdgesOnly(void)
338 {
339 return ldPrefs->getEdgesOnly();
340 }
341
getDrawConditionalHighlights(void)342 bool LDViewPreferences::getDrawConditionalHighlights(void)
343 {
344 return ldPrefs->getDrawConditionalHighlights();
345 }
346
getShowAllConditionalLines(void)347 bool LDViewPreferences::getShowAllConditionalLines(void)
348 {
349 return ldPrefs->getShowAllConditionalLines();
350 }
351
getShowConditionalControlPoints(void)352 bool LDViewPreferences::getShowConditionalControlPoints(void)
353 {
354 return ldPrefs->getShowConditionalControlPoints();
355 }
356
getUseFlatShading(void)357 bool LDViewPreferences::getUseFlatShading(void)
358 {
359 return ldPrefs->getUseFlatShading();
360 }
361
getBoundingBoxesOnly(void)362 bool LDViewPreferences::getBoundingBoxesOnly(void)
363 {
364 return ldPrefs->getBoundingBoxesOnly();
365 }
366
getTransDefaultColor(void)367 bool LDViewPreferences::getTransDefaultColor(void)
368 {
369 return ldPrefs->getTransDefaultColor();
370 }
371
getUseSeams(void)372 bool LDViewPreferences::getUseSeams(void)
373 {
374 return ldPrefs->getUseSeams();
375 }
376
getDrawWireframe(void)377 bool LDViewPreferences::getDrawWireframe(void)
378 {
379 return ldPrefs->getDrawWireframe();
380 }
381
getBfc(void)382 bool LDViewPreferences::getBfc(void)
383 {
384 return ldPrefs->getBfc();
385 }
386
getShowAxes(void)387 bool LDViewPreferences::getShowAxes(void)
388 {
389 return ldPrefs->getShowAxes();
390 }
391
getRandomColors(void)392 bool LDViewPreferences::getRandomColors(void)
393 {
394 return ldPrefs->getRandomColors();
395 }
396
getRedBackFaces(void)397 bool LDViewPreferences::getRedBackFaces(void)
398 {
399 return ldPrefs->getRedBackFaces();
400 }
401
getGreenFrontFaces(void)402 bool LDViewPreferences::getGreenFrontFaces(void)
403 {
404 return ldPrefs->getGreenFrontFaces();
405 }
406
getBlueNeutralFaces(void)407 bool LDViewPreferences::getBlueNeutralFaces(void)
408 {
409 return ldPrefs->getBlueNeutralFaces();
410 }
411
getUseWireframeFog(void)412 bool LDViewPreferences::getUseWireframeFog(void)
413 {
414 return ldPrefs->getUseWireframeFog();
415 }
416
getRemoveHiddenLines(void)417 bool LDViewPreferences::getRemoveHiddenLines(void)
418 {
419 return ldPrefs->getRemoveHiddenLines();
420 }
421
getUsePolygonOffset(void)422 bool LDViewPreferences::getUsePolygonOffset(void)
423 {
424 return ldPrefs->getUsePolygonOffset();
425 }
426
getBlackHighlights(void)427 bool LDViewPreferences::getBlackHighlights(void)
428 {
429 return ldPrefs->getBlackHighlights();
430 }
431
getUseLighting(void)432 bool LDViewPreferences::getUseLighting(void)
433 {
434 return ldPrefs->getUseLighting();
435 }
436
getSubduedLighting(void)437 bool LDViewPreferences::getSubduedLighting(void)
438 {
439 return ldPrefs->getSubduedLighting();
440 }
441
getUseStipple(void)442 bool LDViewPreferences::getUseStipple(void)
443 {
444 return ldPrefs->getUseStipple();
445 }
446
getSortTransparent(void)447 bool LDViewPreferences::getSortTransparent(void)
448 {
449 return ldPrefs->getSortTransparent();
450 }
451
getTextureStuds(void)452 bool LDViewPreferences::getTextureStuds(void)
453 {
454 return ldPrefs->getTextureStuds();
455 }
456
getTexmaps(void)457 bool LDViewPreferences::getTexmaps(void)
458 {
459 return ldPrefs->getTexmaps();
460 }
461
getBackgroundColor(void)462 COLORREF LDViewPreferences::getBackgroundColor(void)
463 {
464 int r, g, b;
465
466 ldPrefs->getBackgroundColor(r, g, b);
467 return RGB((BYTE)r, (BYTE)g, (BYTE)b);
468 }
469
getDefaultColor(void)470 COLORREF LDViewPreferences::getDefaultColor(void)
471 {
472 int r, g, b;
473
474 ldPrefs->getDefaultColor(r, g, b);
475 return RGB((BYTE)r, (BYTE)g, (BYTE)b);
476 }
477
setDrawConditionalHighlights(bool value)478 void LDViewPreferences::setDrawConditionalHighlights(bool value)
479 {
480 if (value != ldPrefs->getDrawConditionalHighlights())
481 {
482 ldPrefs->setDrawConditionalHighlights(value, true, true);
483 if (hGeometryPage)
484 {
485 setCheck(hGeometryPage, IDC_CONDITIONAL_HIGHLIGHTS, value);
486 }
487 }
488 }
489
setShowAllConditionalLines(bool value)490 void LDViewPreferences::setShowAllConditionalLines(bool value)
491 {
492 if (value != ldPrefs->getShowAllConditionalLines())
493 {
494 ldPrefs->setShowAllConditionalLines(value, true, true);
495 if (hGeometryPage)
496 {
497 setCheck(hGeometryPage, IDC_ALL_CONDITIONAL, value);
498 }
499 }
500 }
501
setShowConditionalControlPoints(bool value)502 void LDViewPreferences::setShowConditionalControlPoints(bool value)
503 {
504 if (value != ldPrefs->getShowConditionalControlPoints())
505 {
506 ldPrefs->setShowConditionalControlPoints(value, true, true);
507 if (hGeometryPage)
508 {
509 setCheck(hGeometryPage, IDC_CONDITIONAL_CONTROLS, value);
510 }
511 }
512 }
513
setUseFlatShading(bool value)514 void LDViewPreferences::setUseFlatShading(bool value)
515 {
516 if (value != ldPrefs->getUseFlatShading())
517 {
518 ldPrefs->setUseFlatShading(value, true, true);
519 if (hEffectsPage)
520 {
521 setCheck(hEffectsPage, IDC_FLAT_SHADING, value);
522 }
523 }
524 }
525
setBoundingBoxesOnly(bool value)526 void LDViewPreferences::setBoundingBoxesOnly(bool value)
527 {
528 if (value != ldPrefs->getBoundingBoxesOnly())
529 {
530 ldPrefs->setBoundingBoxesOnly(value, true, true);
531 if (hGeometryPage)
532 {
533 setCheck(hGeometryPage, IDC_PART_BOUNDING_BOXES, value);
534 }
535 }
536 }
537
setTransDefaultColor(bool value)538 void LDViewPreferences::setTransDefaultColor(bool value)
539 {
540 if (value != ldPrefs->getTransDefaultColor())
541 {
542 ldPrefs->setTransDefaultColor(value, true, true);
543 if (hGeneralPage)
544 {
545 setCheck(hGeneralPage, IDC_TRANS_DEFAULT_COLOR, value);
546 }
547 }
548 }
549
setPerformSmoothing(bool value)550 void LDViewPreferences::setPerformSmoothing(bool value)
551 {
552 if (value != ldPrefs->getPerformSmoothing())
553 {
554 ldPrefs->setPerformSmoothing(value, true, true);
555 if (hEffectsPage)
556 {
557 setCheck(hEffectsPage, IDC_SMOOTH_CURVES, value);
558 }
559 }
560 }
561
setCutawayMode(LDVCutawayMode value)562 void LDViewPreferences::setCutawayMode(LDVCutawayMode value)
563 {
564 if (value != ldPrefs->getCutawayMode())
565 {
566 ldPrefs->setCutawayMode(value, true, true);
567 if (hEffectsPage)
568 {
569 setupCutaway();
570 }
571 }
572 }
573
setUsePolygonOffset(bool value)574 void LDViewPreferences::setUsePolygonOffset(bool value)
575 {
576 if (value != ldPrefs->getUsePolygonOffset())
577 {
578 ldPrefs->setUsePolygonOffset(value, true, true);
579 if (hGeometryPage)
580 {
581 setCheck(hGeometryPage, IDC_QUALITY_LINES, value);
582 }
583 }
584 }
585
setBlackHighlights(bool value)586 void LDViewPreferences::setBlackHighlights(bool value)
587 {
588 if (value != ldPrefs->getBlackHighlights())
589 {
590 ldPrefs->setBlackHighlights(value, true, true);
591 if (hGeometryPage)
592 {
593 setCheck(hGeometryPage, IDC_ALWAYS_BLACK, value);
594 }
595 }
596 }
597
setShowsHighlightLines(bool value)598 void LDViewPreferences::setShowsHighlightLines(bool value)
599 {
600 if (value != ldPrefs->getShowHighlightLines())
601 {
602 ldPrefs->setShowHighlightLines(value, true, true);
603 if (hGeometryPage)
604 {
605 setupGroupCheckButton(hGeometryPage, IDC_HIGHLIGHTS, value);
606 if (value)
607 {
608 enableEdges();
609 }
610 else
611 {
612 disableEdges();
613 }
614 }
615 }
616 }
617
setTextureStuds(bool value)618 void LDViewPreferences::setTextureStuds(bool value)
619 {
620 if (value != ldPrefs->getTextureStuds())
621 {
622 ldPrefs->setTextureStuds(value, true, true);
623 if (hPrimitivesPage)
624 {
625 setCheck(hPrimitivesPage, IDC_TEXTURE_STUDS, value);
626 }
627 }
628 }
629
setTexmaps(bool value)630 void LDViewPreferences::setTexmaps(bool value)
631 {
632 if (value != ldPrefs->getTexmaps())
633 {
634 ldPrefs->setTexmaps(value, true, true);
635 if (hPrimitivesPage)
636 {
637 setCheck(hPrimitivesPage, IDC_TEXMAPS, value);
638 }
639 }
640 }
641
setAllowPrimitiveSubstitution(bool value)642 void LDViewPreferences::setAllowPrimitiveSubstitution(bool value)
643 {
644 if (value != ldPrefs->getAllowPrimitiveSubstitution())
645 {
646 ldPrefs->setAllowPrimitiveSubstitution(value, true, true);
647 if (hPrimitivesPage)
648 {
649 setupGroupCheckButton(hPrimitivesPage, IDC_PRIMITIVE_SUBSTITUTION,
650 value);
651 if (value)
652 {
653 enablePrimitives();
654 }
655 else
656 {
657 disablePrimitives();
658 }
659 }
660 }
661 }
662
setRedBackFaces(bool value)663 void LDViewPreferences::setRedBackFaces(bool value)
664 {
665 if (value != ldPrefs->getRedBackFaces())
666 {
667 ldPrefs->setRedBackFaces(value, true, true);
668 if (hGeometryPage)
669 {
670 setCheck(hGeometryPage, IDC_RED_BACK_FACES, value);
671 }
672 }
673 }
674
setGreenFrontFaces(bool value)675 void LDViewPreferences::setGreenFrontFaces(bool value)
676 {
677 if (value != ldPrefs->getGreenFrontFaces())
678 {
679 ldPrefs->setGreenFrontFaces(value, true, true);
680 if (hGeometryPage)
681 {
682 setCheck(hGeometryPage, IDC_GREEN_FRONT_FACES, value);
683 }
684 }
685 }
686
setBlueNeutralFaces(bool value)687 void LDViewPreferences::setBlueNeutralFaces(bool value)
688 {
689 if (value != ldPrefs->getBlueNeutralFaces())
690 {
691 ldPrefs->setBlueNeutralFaces(value, true, true);
692 if (hGeometryPage)
693 {
694 setCheck(hGeometryPage, IDC_BLUE_NEUTRAL_FACES, value);
695 }
696 }
697 }
698
setBfc(bool value)699 void LDViewPreferences::setBfc(bool value)
700 {
701 if (value != ldPrefs->getBfc())
702 {
703 ldPrefs->setBfc(value, true, true);
704 if (hGeometryPage)
705 {
706 setupGroupCheckButton(hGeometryPage, IDC_BFC, value);
707 if (value)
708 {
709 enableBfc();
710 }
711 else
712 {
713 disableBfc();
714 }
715 }
716 }
717 }
718
setShowAxes(bool value)719 void LDViewPreferences::setShowAxes(bool value)
720 {
721 if (value != ldPrefs->getShowAxes())
722 {
723 ldPrefs->setShowAxes(value, true, true);
724 if (hGeneralPage)
725 {
726 setCheck(hGeneralPage, IDC_SHOW_AXES, value);
727 }
728 }
729 }
730
setRandomColors(bool value)731 void LDViewPreferences::setRandomColors(bool value)
732 {
733 if (value != ldPrefs->getRandomColors())
734 {
735 ldPrefs->setRandomColors(value, true, true);
736 if (hGeneralPage)
737 {
738 setCheck(hGeneralPage, IDC_RANDOM_COLORS, value);
739 }
740 }
741 }
742
743 // This is called from LDViewWindow.
setQualityLighting(bool value)744 void LDViewPreferences::setQualityLighting(bool value)
745 {
746 if (value != ldPrefs->getQualityLighting())
747 {
748 ldPrefs->setQualityLighting(value, true, true);
749 if (hEffectsPage)
750 {
751 setCheck(hEffectsPage, IDC_LIGHTING_QUALITY, value);
752 }
753 }
754 }
755
setSubduedLighting(bool value)756 void LDViewPreferences::setSubduedLighting(bool value)
757 {
758 if (value != ldPrefs->getSubduedLighting())
759 {
760 ldPrefs->setSubduedLighting(value, true, true);
761 if (hEffectsPage)
762 {
763 setCheck(hEffectsPage, IDC_LIGHTING_SUBDUED, value);
764 }
765 }
766 }
767
setQualityStuds(bool value)768 void LDViewPreferences::setQualityStuds(bool value)
769 {
770 if (value != ldPrefs->getQualityStuds())
771 {
772 ldPrefs->setQualityStuds(value, true, true);
773 if (hPrimitivesPage)
774 {
775 setCheck(hPrimitivesPage, IDC_STUD_QUALITY, !value);
776 }
777 }
778 }
779
setUsesFlatShading(bool value)780 void LDViewPreferences::setUsesFlatShading(bool value)
781 {
782 if (value != ldPrefs->getUseFlatShading())
783 {
784 ldPrefs->setUseFlatShading(value, true, true);
785 if (hEffectsPage)
786 {
787 setCheck(hEffectsPage, IDC_FLAT_SHADING, value);
788 }
789 }
790 }
791
setUsesSpecular(bool value)792 void LDViewPreferences::setUsesSpecular(bool value)
793 {
794 if (value != ldPrefs->getUseSpecular())
795 {
796 ldPrefs->setUseSpecular(value, true, true);
797 if (hEffectsPage)
798 {
799 setCheck(hEffectsPage, IDC_SPECULAR, value);
800 }
801 }
802 }
803
setOneLight(bool value)804 void LDViewPreferences::setOneLight(bool value)
805 {
806 if (value != ldPrefs->getOneLight())
807 {
808 ldPrefs->setOneLight(value, true, true);
809 if (hEffectsPage)
810 {
811 setCheck(hEffectsPage, IDC_ALTERNATE_LIGHTING, value);
812 }
813 }
814 }
815
setDrawLightDats(bool value)816 void LDViewPreferences::setDrawLightDats(bool value)
817 {
818 if (value != ldPrefs->getDrawLightDats())
819 {
820 ldPrefs->setDrawLightDats(value, true, true);
821 if (hEffectsPage)
822 {
823 setCheck(hEffectsPage, IDC_DRAW_LIGHT_DATS, value);
824 }
825 }
826 }
827
setOptionalStandardLight(bool value)828 void LDViewPreferences::setOptionalStandardLight(bool value)
829 {
830 if (value != ldPrefs->getOptionalStandardLight())
831 {
832 ldPrefs->setOptionalStandardLight(value, true, true);
833 if (hEffectsPage)
834 {
835 setCheck(hEffectsPage, IDC_OPTIONAL_STANDARD_LIGHT, value);
836 }
837 }
838 }
839
setUseLighting(bool value)840 void LDViewPreferences::setUseLighting(bool value)
841 {
842 if (value != ldPrefs->getUseLighting())
843 {
844 ldPrefs->setUseLighting(value, true, true);
845 if (hEffectsPage)
846 {
847 setupGroupCheckButton(hEffectsPage, IDC_LIGHTING, value);
848 if (value)
849 {
850 enableLighting();
851 }
852 else
853 {
854 disableLighting();
855 }
856 }
857 }
858 }
859
run(void)860 INT_PTR LDViewPreferences::run(void)
861 {
862 bool wasPaused = true;
863 INT_PTR retValue;
864
865 if (modelViewer)
866 {
867 wasPaused = modelViewer->getPaused() != 0;
868 if (!wasPaused)
869 {
870 modelViewer->pause();
871 }
872 }
873 addPage(IDD_GENERAL_PREFS);
874 addPage(IDD_GEOMETRY_PREFS);
875 addPage(IDD_EFFECTS_PREFS);
876 addPage(IDD_PRIMITIVES_PREFS);
877 addPage(IDD_UPDATES_PREFS);
878 addPage(IDD_PREFSETS_PREFS);
879 checkAbandon = true;
880 retValue = CUIPropertySheet::run();
881 if (!wasPaused)
882 {
883 modelViewer->unpause();
884 }
885 return retValue;
886 }
887
doDialogNotify(HWND hDlg,int controlId,LPNMHDR notification)888 BOOL LDViewPreferences::doDialogNotify(HWND hDlg, int controlId,
889 LPNMHDR notification)
890 {
891 // debugPrintf("LDViewPreferences::doDialogNotify: %d 0x%08X\n",
892 // notification->code, notification->code);
893 if (notification->code == NM_RELEASEDCAPTURE)
894 {
895 if (hDlg == hEffectsPage)
896 {
897 if (controlId == IDC_STEREO_SPACING ||
898 controlId == IDC_CUTAWAY_OPACITY ||
899 controlId == IDC_CUTAWAY_THICKNESS)
900 {
901 enableApply(hEffectsPage);
902 return FALSE;
903 }
904 }
905 else if (hDlg == hGeometryPage)
906 {
907 if (controlId == IDC_WIREFRAME_THICKNESS ||
908 controlId == IDC_EDGE_THICKNESS)
909 {
910 enableApply(hGeometryPage);
911 return FALSE;
912 }
913 }
914 else if (hDlg == hPrimitivesPage)
915 {
916 if (controlId == IDC_CURVE_QUALITY)
917 {
918 enableApply(hPrimitivesPage);
919 return FALSE;
920 }
921 else if (controlId == IDC_ANISO_LEVEL)
922 {
923 enableApply(hPrimitivesPage);
924 setAniso(trackBarGetPos(hAnisoLevelSlider));
925 return FALSE;
926 }
927 else if (controlId == IDC_TEXTURE_OFFSET)
928 {
929 enableApply(hPrimitivesPage);
930 return FALSE;
931 }
932 }
933 }
934 else if (notification->code == CBN_SELCHANGE)
935 {
936 debugPrintf("combo sel\n");
937 }
938 return CUIPropertySheet::doDialogNotify(hDlg, controlId, notification);
939 }
940
getLDViewPath(bool useQuotes)941 UCSTR LDViewPreferences::getLDViewPath(bool useQuotes)
942 {
943 UCCHAR origPath[MAX_PATH];
944 UCCHAR newPath[MAX_PATH];
945
946 if (ldviewPath.empty())
947 {
948 UCSTR commandLine = copyString(GetCommandLine());
949
950 PathRemoveArgs(commandLine);
951 PathUnquoteSpaces(commandLine);
952 PathRemoveFileSpec(commandLine);
953 GetCurrentDirectory(MAX_PATH, origPath);
954 if (SetCurrentDirectory(commandLine))
955 {
956 GetCurrentDirectory(MAX_PATH, newPath);
957 PathUnquoteSpaces(newPath);
958 ldviewPath = newPath;
959 SetCurrentDirectory(origPath);
960 }
961 else
962 {
963 ldviewPath = origPath;
964 }
965 delete commandLine;
966 }
967 ucstrcpy(newPath, ldviewPath.c_str());
968 if (useQuotes)
969 {
970 PathQuoteSpaces(newPath);
971 }
972 return copyString(newPath);
973 }
974
getLDViewPath(CUCSTR helpFilename,bool useQuotes)975 UCSTR LDViewPreferences::getLDViewPath(CUCSTR helpFilename, bool useQuotes)
976 {
977 UCSTR programPath = getLDViewPath();
978 UCCHAR tmpPath[MAX_PATH];
979
980 ucstrcpy(tmpPath, programPath);
981 delete[] programPath;
982 if (helpFilename)
983 {
984 PathAppend(tmpPath, helpFilename);
985 }
986 if (useQuotes)
987 {
988 PathQuoteSpaces(tmpPath);
989 }
990 return copyString(tmpPath);
991 }
992
getPageDialogID(HWND hDlg)993 DWORD LDViewPreferences::getPageDialogID(HWND hDlg)
994 {
995 if (hDlg == hGeneralPage)
996 {
997 return IDD_GENERAL_PREFS;
998 }
999 else if (hDlg == hGeometryPage)
1000 {
1001 return IDD_GEOMETRY_PREFS;
1002 }
1003 else if (hDlg == hEffectsPage)
1004 {
1005 return IDD_EFFECTS_PREFS;
1006 }
1007 else if (hDlg == hPrimitivesPage)
1008 {
1009 return IDD_PRIMITIVES_PREFS;
1010 }
1011 else if (hDlg == hUpdatesPage)
1012 {
1013 return IDD_UPDATES_PREFS;
1014 }
1015 else if (hDlg == hPrefSetsPage)
1016 {
1017 return IDD_PREFSETS_PREFS;
1018 }
1019 return 0;
1020 }
1021
doDialogHelp(HWND hDlg,LPHELPINFO helpInfo)1022 BOOL LDViewPreferences::doDialogHelp(HWND hDlg, LPHELPINFO helpInfo)
1023 {
1024 DWORD dialogId = getPageDialogID(hDlg);
1025
1026 if (dialogId)
1027 {
1028 return CUIDialog::DoHtmlHelp(hDlg, helpInfo);
1029 }
1030 return FALSE;
1031 }
1032
getPrefSet(int index)1033 ucstring LDViewPreferences::getPrefSet(int index)
1034 {
1035 ucstring prefSet;
1036 listBoxGetText(hPrefSetsList, index, prefSet);
1037 return prefSet;
1038 }
1039
getSelectedPrefSet(void)1040 ucstring LDViewPreferences::getSelectedPrefSet(void)
1041 {
1042 int selectedIndex = listBoxGetCurSel(hPrefSetsList);
1043
1044 if (selectedIndex != LB_ERR)
1045 {
1046 return getPrefSet(selectedIndex);
1047 }
1048 return ucstring();
1049 }
1050
abandonChanges(void)1051 void LDViewPreferences::abandonChanges(void)
1052 {
1053 int i;
1054 HWND hPage;
1055
1056 doReset();
1057 for (i = 0; i < prefSetsPageNumber; i++)
1058 {
1059 hPage = hwndArray->pointerAtIndex(i);
1060 if (hPage)
1061 {
1062 disableApply(hPage);
1063 hwndArray->replacePointer(NULL, i);
1064 }
1065 }
1066 hPage = hwndArray->pointerAtIndex(prefSetsPageNumber);
1067 if (hPage)
1068 {
1069 disableApply(hPage);
1070 }
1071 }
1072
runPrefSetApplyDialog(void)1073 INT_PTR LDViewPreferences::runPrefSetApplyDialog(void)
1074 {
1075 INT_PTR retValue = DialogBoxParam(getLanguageModule(),
1076 MAKEINTRESOURCE(IDD_PREFSET_APPLY), hWindow, staticDialogProc,
1077 (LPARAM)this);
1078
1079 if (retValue == IDC_APPLY)
1080 {
1081 PropSheet_Apply(hPropSheet);
1082 }
1083 else if (retValue == IDC_ABANDON)
1084 {
1085 abandonChanges();
1086 }
1087 return retValue;
1088 }
1089
doPrefSetSelected(bool force)1090 BOOL LDViewPreferences::doPrefSetSelected(bool force)
1091 {
1092 ucstring selectedPrefSet = getSelectedPrefSet();
1093 bool needToReselect = false;
1094
1095 if (checkAbandon && getApplyEnabled() && !force)
1096 {
1097 char *savedSession =
1098 TCUserDefaults::getSavedSessionNameFromKey(PREFERENCE_SET_KEY);
1099 ucstring ucSavedSession;
1100
1101 if (!savedSession || !savedSession[0])
1102 {
1103 ucSavedSession = DEFAULT_PREF_SET;
1104 }
1105 else
1106 {
1107 utf8toucstring(ucSavedSession, savedSession);
1108 }
1109 delete[] savedSession;
1110 if (selectedPrefSet == ucSavedSession)
1111 {
1112 return FALSE;
1113 }
1114 else
1115 {
1116 needToReselect = true;
1117 selectPrefSet(_UC(""), true);
1118 if (runPrefSetApplyDialog() == IDCANCEL)
1119 {
1120 checkAbandon = true;
1121 return TRUE;
1122 }
1123 }
1124 }
1125 if (!selectedPrefSet.empty())
1126 {
1127 BOOL enabled = TRUE;
1128
1129 if (needToReselect)
1130 {
1131 selectPrefSet(selectedPrefSet);
1132 }
1133 if (selectedPrefSet == DEFAULT_PREF_SET)
1134 {
1135 enabled = FALSE;
1136 }
1137 EnableWindow(hDeletePrefSetButton, enabled);
1138 }
1139 enableApply(hPrefSetsPage);
1140 checkAbandon = false;
1141 return FALSE;
1142 }
1143
doDialogThemeChanged(void)1144 BOOL LDViewPreferences::doDialogThemeChanged(void)
1145 {
1146 if (hButtonTheme)
1147 {
1148 CUIThemes::closeThemeData(hButtonTheme);
1149 hButtonTheme = NULL;
1150 }
1151 /*
1152 if (hTabTheme)
1153 {
1154 CUIThemes::closeThemeData(hTabTheme);
1155 hTabTheme = NULL;
1156 }
1157 */
1158 if (CUIThemes::isThemeLibLoaded())
1159 {
1160 if (hBackgroundColorButton)
1161 {
1162 setupBackgroundColorButton();
1163 }
1164 if (hDefaultColorButton)
1165 {
1166 setupDefaultColorButton();
1167 }
1168 if (hGeometryPage)
1169 {
1170 setupGroupCheckButton(hGeometryPage, IDC_WIREFRAME,
1171 ldPrefs->getDrawWireframe());
1172 }
1173 /*
1174 if (hLightDirStatic)
1175 {
1176 initThemesTab(hLightDirStatic);
1177 }
1178 */
1179 }
1180 return FALSE;
1181 }
1182
doDialogCommand(HWND hDlg,int controlId,int notifyCode,HWND controlHWnd)1183 BOOL LDViewPreferences::doDialogCommand(HWND hDlg, int controlId,
1184 int notifyCode, HWND controlHWnd)
1185 {
1186 UCCHAR className[1024];
1187
1188 GetClassName(controlHWnd, className, COUNT_OF(className));
1189 if (ucstrcmp(className, WC_COMBOBOX) == 0)
1190 {
1191 if (notifyCode == CBN_SELCHANGE)
1192 {
1193 return doComboSelChange(hDlg, controlId, controlHWnd);
1194 }
1195 }
1196 else if (notifyCode == BN_CLICKED)
1197 {
1198 return doClick(hDlg, controlId, controlHWnd);
1199 }
1200 else if (notifyCode == EN_CHANGE)
1201 {
1202 if (controlId == IDC_FS_RATE || controlId == IDC_FOV ||
1203 controlId == IDC_PROXY_SERVER || controlId == IDC_PROXY_PORT ||
1204 controlId == IDC_MISSING_DAYS || controlId == IDC_UPDATED_DAYS)
1205 {
1206 enableApply(hDlg);
1207 return 0;
1208 }
1209 }
1210 else if (notifyCode == LBN_SELCHANGE)
1211 {
1212 if (hDlg == hPrefSetsPage)
1213 {
1214 return doPrefSetSelected();
1215 }
1216 }
1217 return LDP_UNKNOWN_COMMAND;
1218 }
1219
setupBackgroundColorButton(void)1220 void LDViewPreferences::setupBackgroundColorButton(void)
1221 {
1222 setupColorButton(hGeneralPage, hBackgroundColorButton,
1223 IDC_BACKGROUND_COLOR, hBackgroundColorBitmap,
1224 getBackgroundColor());
1225 }
1226
setupDefaultColorButton(void)1227 void LDViewPreferences::setupDefaultColorButton(void)
1228 {
1229 setupColorButton(hGeneralPage, hDefaultColorButton,
1230 IDC_DEFAULT_COLOR, hDefaultColorBitmap,
1231 getDefaultColor());
1232 }
1233
staticIconButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1234 LRESULT CALLBACK LDViewPreferences::staticIconButtonProc(
1235 HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
1236 {
1237 LDViewPreferences *thisPtr =
1238 (LDViewPreferences *)GetWindowLongPtr(hWnd, GWLP_USERDATA);
1239
1240 return thisPtr->iconButtonProc(hWnd, message, wParam, lParam);
1241 }
1242
iconButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1243 LRESULT LDViewPreferences::iconButtonProc(
1244 HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
1245 {
1246 switch (message)
1247 {
1248 case WM_MOUSEMOVE:
1249 if (hMouseOverButton != hWnd)
1250 {
1251 if (hMouseOverButton)
1252 {
1253 InvalidateRect(hMouseOverButton, NULL, FALSE);
1254 }
1255 hMouseOverButton = hWnd;
1256 InvalidateRect(hWnd, NULL, FALSE);
1257 }
1258 break;
1259 }
1260 return CallWindowProc((WNDPROC)origButtonWindowProc, hWnd, message, wParam,
1261 lParam);
1262 }
1263
staticGroupCheckButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1264 LRESULT CALLBACK LDViewPreferences::staticGroupCheckButtonProc(HWND hWnd,
1265 UINT message,
1266 WPARAM wParam,
1267 LPARAM lParam)
1268 {
1269 LDViewPreferences *thisPtr =
1270 (LDViewPreferences *)GetWindowLongPtr(hWnd, GWLP_USERDATA);
1271
1272 return thisPtr->groupCheckButtonProc(hWnd, message, wParam, lParam);
1273 }
1274
groupCheckButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1275 LRESULT LDViewPreferences::groupCheckButtonProc(HWND hWnd, UINT message,
1276 WPARAM wParam, LPARAM lParam)
1277 {
1278 switch (message)
1279 {
1280 case WM_MOUSEMOVE:
1281 if (hMouseOverButton != hWnd)
1282 {
1283 if (hMouseOverButton)
1284 {
1285 InvalidateRect(hMouseOverButton, NULL, FALSE);
1286 }
1287 hMouseOverButton = hWnd;
1288 InvalidateRect(hWnd, NULL, FALSE);
1289 }
1290 break;
1291 }
1292 return CallWindowProc((WNDPROC)origButtonWindowProc, hWnd, message, wParam,
1293 lParam);
1294 }
1295
staticColorButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1296 LRESULT CALLBACK LDViewPreferences::staticColorButtonProc(HWND hWnd,
1297 UINT message,
1298 WPARAM wParam,
1299 LPARAM lParam)
1300 {
1301 LDViewPreferences *thisPtr =
1302 (LDViewPreferences *)GetWindowLongPtr(hWnd, GWLP_USERDATA);
1303
1304 return thisPtr->colorButtonProc(hWnd, message, wParam, lParam);
1305 }
1306
colorButtonProc(HWND hWnd,UINT message,WPARAM wParam,LPARAM lParam)1307 LRESULT LDViewPreferences::colorButtonProc(HWND hWnd, UINT message,
1308 WPARAM wParam, LPARAM lParam)
1309 {
1310 switch (message)
1311 {
1312 case WM_MOUSEMOVE:
1313 if (hMouseOverButton != hWnd)
1314 {
1315 if (hMouseOverButton)
1316 {
1317 InvalidateRect(hMouseOverButton, NULL, FALSE);
1318 }
1319 hMouseOverButton = hWnd;
1320 InvalidateRect(hWnd, NULL, FALSE);
1321 }
1322 break;
1323 }
1324 return CallWindowProc((WNDPROC)origButtonWindowProc, hWnd, message, wParam,
1325 lParam);
1326 }
1327
setupIconButton(HWND hButton)1328 void LDViewPreferences::setupIconButton(HWND hButton)
1329 {
1330 initThemesButton(hButton);
1331 if (hButtonTheme)
1332 {
1333 LONG_PTR oldWindowProc;
1334 DWORD dwStyle = GetWindowLong(hButton, GWL_STYLE);
1335 int buttonType = dwStyle & BS_TYPEMASK;
1336
1337 buttonTypes[hButton] = buttonType;
1338 if (buttonType != BS_OWNERDRAW)
1339 {
1340 dwStyle = (dwStyle & ~BS_TYPEMASK) | BS_OWNERDRAW;
1341 buttonSetStyle(hButton, dwStyle);
1342 }
1343 // subclass the button so we can know when the mouse has moved over it
1344 SetWindowLongPtr(hButton, GWLP_USERDATA, (LONG_PTR)this);
1345 oldWindowProc = SetWindowLongPtr(hButton, GWLP_WNDPROC,
1346 (LONG_PTR)staticIconButtonProc);
1347 if (!origButtonWindowProc)
1348 {
1349 origButtonWindowProc = oldWindowProc;
1350 }
1351 }
1352 else
1353 {
1354 if (origButtonWindowProc)
1355 {
1356 if (buttonTypes.find(hButton) != buttonTypes.end())
1357 {
1358 DWORD dwStyle = GetWindowLong(hButton, GWL_STYLE);
1359
1360 dwStyle = (dwStyle & ~BS_TYPEMASK) | buttonTypes[hButton];
1361 buttonSetStyle(hButton, dwStyle);
1362 // Put the window proc back if we've every overridden one. Maybe
1363 // the user disabled themes.
1364 SetWindowLongPtr(hButton, GWLP_WNDPROC,
1365 (LONG_PTR)origButtonWindowProc);
1366 }
1367 }
1368 }
1369 }
1370
setupColorButton(HWND hPage,HWND & hColorButton,int controlID,HBITMAP & hButtonBitmap,COLORREF color)1371 void LDViewPreferences::setupColorButton(HWND hPage, HWND &hColorButton,
1372 int controlID, HBITMAP &hButtonBitmap,
1373 COLORREF color)
1374 {
1375 int imageWidth;
1376 int imageHeight;
1377 HDC hPageDC;
1378 RECT clientRect;
1379
1380 initThemesButton(hColorButton);
1381 if (hButtonBitmap)
1382 {
1383 DeleteObject(hButtonBitmap);
1384 if (origButtonWindowProc)
1385 {
1386 SetWindowLongPtr(hColorButton, GWLP_WNDPROC,
1387 (LONG_PTR)origButtonWindowProc);
1388 }
1389 }
1390 hColorButton = GetDlgItem(hPage, controlID);
1391 GetClientRect(hColorButton, &clientRect);
1392 if (hButtonTheme)
1393 {
1394 RECT contentRect;
1395
1396 // subclass the Wizard button so we can know when the mouse has moved
1397 // over it
1398 SetWindowLongPtr(hColorButton, GWLP_USERDATA, (LONG_PTR)this);
1399 if (origButtonWindowProc)
1400 {
1401 SetWindowLongPtr(hColorButton, GWLP_WNDPROC,
1402 (LONG_PTR)staticColorButtonProc);
1403 }
1404 else
1405 {
1406 origButtonWindowProc = SetWindowLongPtr(hColorButton, GWLP_WNDPROC,
1407 (LONG_PTR)staticColorButtonProc);
1408 }
1409 CUIThemes::getThemeBackgroundContentRect(hButtonTheme, NULL,
1410 BP_PUSHBUTTON, PBS_HOT, &clientRect, &contentRect);
1411 LONG margin = scalePoints(6);
1412 imageWidth = contentRect.right - contentRect.left - margin;
1413 imageHeight = contentRect.bottom - contentRect.top - margin;
1414 }
1415 else
1416 {
1417 LONG margin = scalePoints(10);
1418 imageWidth = clientRect.right - clientRect.left - margin;
1419 imageHeight = clientRect.bottom - clientRect.top - margin;
1420 }
1421 hPageDC = GetDC(hPage);
1422 if (!hButtonColorDC)
1423 {
1424 hButtonColorDC = CreateCompatibleDC(hPageDC);
1425 }
1426 hButtonBitmap = CreateCompatibleBitmap(hPageDC, imageWidth, imageHeight);
1427 ReleaseDC(hPage, hPageDC);
1428 SetBitmapDimensionEx(hButtonBitmap, imageWidth, imageHeight, NULL);
1429 redrawColorBitmap(hColorButton, hButtonBitmap, color);
1430 CUIDialog::buttonSetBitmap(hPage, controlID, hButtonBitmap);
1431 }
1432
enableSeams(void)1433 void LDViewPreferences::enableSeams(void)
1434 {
1435 UCCHAR seamWidthString[128];
1436
1437 EnableWindow(hSeamSpin, TRUE);
1438 setCheck(hGeometryPage, IDC_SEAMS, true);
1439 sucprintf(seamWidthString, COUNT_OF(seamWidthString), _UC("%0.2f"),
1440 ldPrefs->getSeamWidth() / 100.0f);
1441 CUIDialog::windowSetText(hGeometryPage, IDC_SEAM_WIDTH_FIELD, seamWidthString);
1442 }
1443
disableSeams(void)1444 void LDViewPreferences::disableSeams(void)
1445 {
1446 EnableWindow(hSeamSpin, FALSE);
1447 setCheck(hGeometryPage, IDC_SEAMS, false);
1448 CUIDialog::windowSetText(hGeometryPage, IDC_SEAM_WIDTH_FIELD, _UC(""));
1449 }
1450
enableTextureFiltering(void)1451 void LDViewPreferences::enableTextureFiltering(void)
1452 {
1453 int activeTextureFilter;
1454
1455 EnableWindow(hTextureNearestButton, TRUE);
1456 EnableWindow(hTextureBilinearButton, TRUE);
1457 EnableWindow(hTextureTrilinearButton, TRUE);
1458 EnableWindow(hAnisoLevelLabel, TRUE);
1459 if (TREGLExtensions::haveAnisoExtension())
1460 {
1461 EnableWindow(hTextureAnisoButton, TRUE);
1462 }
1463 else
1464 {
1465 EnableWindow(hTextureAnisoButton, FALSE);
1466 }
1467 setCheck(hPrimitivesPage, IDC_TEXTURE_NEAREST, false);
1468 setCheck(hPrimitivesPage, IDC_TEXTURE_BILINEAR, false);
1469 setCheck(hPrimitivesPage, IDC_TEXTURE_TRILINEAR, false);
1470 setCheck(hPrimitivesPage, IDC_TEXTURE_ANISO, false);
1471 switch (ldPrefs->getTextureFilterType())
1472 {
1473 case GL_NEAREST_MIPMAP_NEAREST:
1474 activeTextureFilter = IDC_TEXTURE_NEAREST;
1475 break;
1476 case GL_LINEAR_MIPMAP_NEAREST:
1477 activeTextureFilter = IDC_TEXTURE_BILINEAR;
1478 break;
1479 case GL_LINEAR_MIPMAP_LINEAR:
1480 activeTextureFilter = IDC_TEXTURE_TRILINEAR;
1481 break;
1482 default:
1483 ldPrefs->setTextureFilterType(GL_LINEAR_MIPMAP_LINEAR);
1484 activeTextureFilter = IDC_TEXTURE_TRILINEAR;
1485 break;
1486 }
1487 if (activeTextureFilter == IDC_TEXTURE_TRILINEAR &&
1488 ldPrefs->getAnisoLevel() > 1.0)
1489 {
1490 EnableWindow(hAnisoLevelSlider, TRUE);
1491 activeTextureFilter = IDC_TEXTURE_ANISO;
1492 }
1493 else
1494 {
1495 EnableWindow(hAnisoLevelSlider, FALSE);
1496 }
1497 setCheck(hPrimitivesPage, activeTextureFilter, true);
1498 }
1499
disableTextureFiltering(void)1500 void LDViewPreferences::disableTextureFiltering(void)
1501 {
1502 EnableWindow(hTextureNearestButton, FALSE);
1503 EnableWindow(hTextureBilinearButton, FALSE);
1504 EnableWindow(hTextureTrilinearButton, FALSE);
1505 EnableWindow(hTextureAnisoButton, FALSE);
1506 EnableWindow(hAnisoLevelSlider, FALSE);
1507 EnableWindow(hAnisoLevelLabel, FALSE);
1508 setCheck(hPrimitivesPage, IDC_TEXTURE_NEAREST, false);
1509 setCheck(hPrimitivesPage, IDC_TEXTURE_BILINEAR, false);
1510 setCheck(hPrimitivesPage, IDC_TEXTURE_TRILINEAR, false);
1511 setCheck(hPrimitivesPage, IDC_TEXTURE_ANISO, false);
1512 }
1513
enableTexmaps(void)1514 void LDViewPreferences::enableTexmaps(void)
1515 {
1516 EnableWindow(hTextureOffsetLabel, TRUE);
1517 EnableWindow(hTextureOffsetSlider, TRUE);
1518 }
1519
disableTexmaps(void)1520 void LDViewPreferences::disableTexmaps(void)
1521 {
1522 EnableWindow(hTextureOffsetLabel, FALSE);
1523 EnableWindow(hTextureOffsetSlider, FALSE);
1524 }
1525
enablePrimitives(void)1526 void LDViewPreferences::enablePrimitives(void)
1527 {
1528 EnableWindow(hTextureStudsButton, TRUE);
1529 EnableWindow(hCurveQualityLabel, TRUE);
1530 EnableWindow(hCurveQualitySlider, TRUE);
1531 setCheck(hPrimitivesPage, IDC_TEXTURE_STUDS,ldPrefs->getTextureStuds());
1532 updateTextureFilteringEnabled();
1533 updateTexmapsEnabled();
1534 }
1535
disablePrimitives(void)1536 void LDViewPreferences::disablePrimitives(void)
1537 {
1538 EnableWindow(hTextureStudsButton, FALSE);
1539 EnableWindow(hCurveQualityLabel, FALSE);
1540 EnableWindow(hCurveQualitySlider, FALSE);
1541 setCheck(hPrimitivesPage, IDC_TEXTURE_STUDS, false);
1542 updateTextureFilteringEnabled();
1543 updateTexmapsEnabled();
1544 }
1545
setupSeamWidth(void)1546 void LDViewPreferences::setupSeamWidth(void)
1547 {
1548 UDACCEL accels[] = {{0, 1}, {1, 10}, {2, 20}};
1549
1550 hSeamSpin = GetDlgItem(hGeometryPage, IDC_SEAM_SPIN);
1551 SendDlgItemMessage(hGeometryPage, IDC_SEAM_SPIN, UDM_SETRANGE, 0,
1552 MAKELONG((short)500, (short)0));
1553 SendDlgItemMessage(hGeometryPage, IDC_SEAM_SPIN, UDM_SETPOS, 0,
1554 ldPrefs->getSeamWidth());
1555 SendDlgItemMessage(hGeometryPage, IDC_SEAM_SPIN, UDM_SETACCEL,
1556 COUNT_OF(accels), (LPARAM)accels);
1557 if (ldPrefs->getUseSeams())
1558 {
1559 enableSeams();
1560 }
1561 else
1562 {
1563 disableSeams();
1564 }
1565 }
1566
setupFullScreenRefresh(void)1567 void LDViewPreferences::setupFullScreenRefresh(void)
1568 {
1569 int fullScreenRefresh = ldPrefs->getFullScreenRefresh();
1570
1571 hFullScreenRateField = GetDlgItem(hGeneralPage, IDC_FS_RATE);
1572 SendDlgItemMessage(hGeneralPage, IDC_FS_RATE, EM_SETLIMITTEXT, 3, 0);
1573 if (fullScreenRefresh)
1574 {
1575 UCCHAR buf[128];
1576
1577 sucprintf(buf, COUNT_OF(buf), _UC("%d"), fullScreenRefresh);
1578 buf[3] = 0;
1579 CUIDialog::windowSetText(hGeneralPage, IDC_FS_RATE, buf);
1580 setCheck(hGeneralPage, IDC_FS_REFRESH, true);
1581 EnableWindow(hFullScreenRateField, TRUE);
1582 }
1583 else
1584 {
1585 CUIDialog::windowSetText(hGeneralPage, IDC_FS_RATE, _UC(""));
1586 setCheck(hGeneralPage, IDC_FS_REFRESH, false);
1587 EnableWindow(hFullScreenRateField, FALSE);
1588 }
1589 }
1590
redrawColorBitmap(HWND hColorButton,HBITMAP hButtonBitmap,COLORREF color)1591 void LDViewPreferences::redrawColorBitmap(HWND hColorButton,
1592 HBITMAP hButtonBitmap, COLORREF color)
1593 {
1594 HBRUSH hBrush = CreateSolidBrush(color);
1595 RECT bitmapRect;
1596 SIZE bitmapSize;
1597 HBITMAP hOldBitmap;
1598 HBRUSH hOldBrush;
1599
1600 GetBitmapDimensionEx(hButtonBitmap, &bitmapSize);
1601 bitmapRect.left = 0;
1602 bitmapRect.top = 0;
1603 bitmapRect.right = bitmapSize.cx;
1604 bitmapRect.bottom = bitmapSize.cy;
1605 hOldBrush = (HBRUSH)SelectObject(hButtonColorDC, hBrush);
1606 hOldBitmap = (HBITMAP)SelectObject(hButtonColorDC, hButtonBitmap);
1607 FillRect(hButtonColorDC, &bitmapRect, hBrush);
1608 if (CUIThemes::isThemeLibLoaded() && hButtonTheme)
1609 {
1610 CUIThemes::drawThemeEdge(hButtonTheme, hButtonColorDC, BP_PUSHBUTTON,
1611 PBS_PRESSED, &bitmapRect, EDGE_SUNKEN, BF_SOFT | BF_RECT, NULL);
1612 }
1613 else
1614 {
1615 DrawEdge(hButtonColorDC, &bitmapRect, EDGE_SUNKEN,
1616 BF_BOTTOMLEFT | BF_TOPRIGHT);
1617 }
1618 SelectObject(hButtonColorDC, hOldBrush);
1619 SelectObject(hButtonColorDC, hOldBitmap);
1620 DeleteObject(hBrush);
1621 InvalidateRect(hColorButton, NULL, 1);
1622 }
1623
applyPrefSetsChanges(void)1624 void LDViewPreferences::applyPrefSetsChanges(void)
1625 {
1626 if (hPrefSetsPage)
1627 {
1628 TCStringArray *oldPrefSetNames = TCUserDefaults::getAllSessionNames();
1629 int i;
1630 int count = oldPrefSetNames->getCount();
1631 ucstring ucPrefSetName;
1632 const char *sessionName = TCUserDefaults::getSessionName();
1633 bool changed = false;
1634
1635 for (i = 0; i < count; i++)
1636 {
1637 char *oldPrefSetName = oldPrefSetNames->stringAtIndex(i);
1638 ucstring ucOldPrefSetName;
1639 utf8toucstring(ucOldPrefSetName, oldPrefSetName);
1640 int index = listBoxFindStringExact(hPrefSetsList, ucOldPrefSetName);
1641
1642 if (index == LB_ERR)
1643 {
1644 TCUserDefaults::removeSession(oldPrefSetName);
1645 }
1646 }
1647 count = listBoxGetCount(hPrefSetsList);
1648 for (i = 1; i < count; i++)
1649 {
1650 ucPrefSetName = getPrefSet(i);
1651 std::string prefSetName;
1652 ucstringtoutf8(prefSetName, ucPrefSetName);
1653 if (oldPrefSetNames->indexOfString(prefSetName.c_str()) < 0)
1654 {
1655 TCUserDefaults::setSessionName(prefSetName.c_str(),
1656 PREFERENCE_SET_KEY);
1657 }
1658 }
1659 oldPrefSetNames->release();
1660 ucPrefSetName = getSelectedPrefSet();
1661 if (ucPrefSetName == DEFAULT_PREF_SET)
1662 {
1663 if (sessionName && sessionName[0])
1664 {
1665 TCUserDefaults::setSessionName(NULL, PREFERENCE_SET_KEY);
1666 changed = true;
1667 }
1668 }
1669 else
1670 {
1671 ucstring ucSessionName;
1672 utf8toucstring(ucSessionName, sessionName);
1673 if (ucPrefSetName != ucSessionName)
1674 {
1675 std::string prefSetName;
1676 ucstringtoutf8(prefSetName, ucPrefSetName);
1677 TCUserDefaults::setSessionName(prefSetName.c_str(),
1678 PREFERENCE_SET_KEY);
1679 changed = true;
1680 }
1681 }
1682 if (changed)
1683 {
1684 loadSettings();
1685 applySettings();
1686 if (hGeneralPage)
1687 {
1688 setupPage(generalPageNumber);
1689 }
1690 if (hGeometryPage)
1691 {
1692 setupPage(geometryPageNumber);
1693 }
1694 if (hEffectsPage)
1695 {
1696 setupPage(effectsPageNumber);
1697 }
1698 if (hPrimitivesPage)
1699 {
1700 setupPage(primitivesPageNumber);
1701 }
1702 if (hUpdatesPage)
1703 {
1704 setupPage(updatesPageNumber);
1705 }
1706 }
1707 }
1708 }
1709
applyGeneralChanges(void)1710 void LDViewPreferences::applyGeneralChanges(void)
1711 {
1712 if (hGeneralPage)
1713 {
1714 int iTemp = 0;
1715 float fTemp;
1716
1717 ldPrefs->setLineSmoothing(getCheck(hGeneralPage, IDC_LINE_AA));
1718 ldPrefs->setTransDefaultColor(getCheck(hGeneralPage,
1719 IDC_TRANS_DEFAULT_COLOR));
1720 ldPrefs->setProcessLdConfig(getCheck(hGeneralPage,
1721 IDC_PROCESS_LDCONFIG));
1722 ldPrefs->setRandomColors(getCheck(hGeneralPage, IDC_RANDOM_COLORS));
1723 ldPrefs->setShowFps(getCheck(hGeneralPage, IDC_FRAME_RATE));
1724 ldPrefs->setShowAxes(getCheck(hGeneralPage, IDC_SHOW_AXES));
1725 ldPrefs->setShowErrors(getCheck(hGeneralPage, IDC_SHOW_ERRORS));
1726 ldPrefs->setMemoryUsage(CUIDialog::comboGetCurSel(hGeneralPage,
1727 IDC_MEMORY_COMBO));
1728 if (getCheck(hGeneralPage, IDC_FS_REFRESH))
1729 {
1730 if (CUIDialog::windowGetValue(hGeneralPage, IDC_FS_RATE, iTemp))
1731 {
1732 if (!iTemp)
1733 {
1734 iTemp = -1;
1735 }
1736 }
1737 else
1738 {
1739 iTemp = -1;
1740 }
1741 }
1742 if (iTemp >= 0)
1743 {
1744 ldPrefs->setFullScreenRefresh(iTemp);
1745 }
1746 if (CUIDialog::windowGetValue(hGeneralPage, IDC_FOV, fTemp))
1747 {
1748 if (fTemp >= getMinFov() && fTemp <= getMaxFov())
1749 {
1750 ldPrefs->setFov(fTemp);
1751 }
1752 else
1753 {
1754 setupFov(true);
1755 }
1756 }
1757 else
1758 {
1759 setupFov(true);
1760 }
1761 ldPrefs->setSnapshotsDirMode(snapshotDirMode);
1762 if (snapshotDirMode == LDPreferences::DDMSpecificDir)
1763 {
1764 windowGetText(hSnapshotDirField, snapshotDir);
1765 if (snapshotDir.length() > 0)
1766 {
1767 std::string utf8Dir;
1768 ucstringtoutf8(utf8Dir, snapshotDir);
1769 ldPrefs->setSnapshotsDir(utf8Dir.c_str());
1770 }
1771 else
1772 {
1773 ldPrefs->setSnapshotsDirMode(LDPreferences::DDMLastDir);
1774 }
1775 }
1776 ldPrefs->setPartsListsDirMode(partsListDirMode);
1777 if (partsListDirMode == LDPreferences::DDMSpecificDir)
1778 {
1779 windowGetText(hPartsListDirField, partsListDir);
1780 if (partsListDir.length() > 0)
1781 {
1782 std::string utf8Dir;
1783 ucstringtoutf8(utf8Dir, partsListDir);
1784 ldPrefs->setPartsListsDir(utf8Dir.c_str());
1785 }
1786 else
1787 {
1788 ldPrefs->setPartsListsDirMode(LDPreferences::DDMLastDir);
1789 }
1790 }
1791 ldPrefs->setSaveDirMode(LDPreferences::SOExport, exportDirMode);
1792 if (exportDirMode == LDPreferences::DDMSpecificDir)
1793 {
1794 windowGetText(hExportDirField, exportDir);
1795 if (exportDir.length() > 0)
1796 {
1797 std::string utf8Dir;
1798 ucstringtoutf8(utf8Dir, exportDir);
1799 ldPrefs->setSaveDir(LDPreferences::SOExport, utf8Dir.c_str());
1800 }
1801 else
1802 {
1803 ldPrefs->setSaveDirMode(LDPreferences::SOExport,
1804 LDPreferences::DDMLastDir);
1805 }
1806 }
1807 ldPrefs->applyGeneralSettings();
1808 }
1809 ldPrefs->commitGeneralSettings();
1810 }
1811
applyGeometryChanges(void)1812 void LDViewPreferences::applyGeometryChanges(void)
1813 {
1814 if (hGeometryPage)
1815 {
1816 ldPrefs->setUseSeams(getCheck(hGeometryPage, IDC_SEAMS));
1817 ldPrefs->setBoundingBoxesOnly(getCheck(hGeometryPage,
1818 IDC_PART_BOUNDING_BOXES));
1819 ldPrefs->setDrawWireframe(getCachedCheck(hGeometryPage, IDC_WIREFRAME));
1820 ldPrefs->setUseWireframeFog(getCheck(hGeometryPage, IDC_WIREFRAME_FOG));
1821 ldPrefs->setRemoveHiddenLines(getCheck(hGeometryPage,
1822 IDC_REMOVE_HIDDEN_LINES));
1823 ldPrefs->setWireframeThickness(CUIDialog::trackBarGetPos(hGeometryPage,
1824 IDC_WIREFRAME_THICKNESS));
1825 ldPrefs->setBfc(getCachedCheck(hGeometryPage, IDC_BFC));
1826 ldPrefs->setRedBackFaces(getCheck(hGeometryPage, IDC_RED_BACK_FACES));
1827 ldPrefs->setGreenFrontFaces(getCheck(hGeometryPage,
1828 IDC_GREEN_FRONT_FACES));
1829 ldPrefs->setBlueNeutralFaces(getCheck(hGeometryPage,
1830 IDC_BLUE_NEUTRAL_FACES));
1831 ldPrefs->setShowHighlightLines(getCachedCheck(hGeometryPage,
1832 IDC_HIGHLIGHTS));
1833 if (ldPrefs->getShowHighlightLines())
1834 {
1835 ldPrefs->setEdgesOnly(getCheck(hGeometryPage, IDC_EDGES_ONLY));
1836 ldPrefs->setDrawConditionalHighlights(getCheck(hGeometryPage,
1837 IDC_CONDITIONAL_HIGHLIGHTS));
1838 if (ldPrefs->getDrawConditionalHighlights())
1839 {
1840 ldPrefs->setShowAllConditionalLines(getCheck(hGeometryPage,
1841 IDC_ALL_CONDITIONAL));
1842 ldPrefs->setShowConditionalControlPoints(getCheck(hGeometryPage,
1843 IDC_CONDITIONAL_CONTROLS));
1844 }
1845 ldPrefs->setUsePolygonOffset(getCheck(hGeometryPage,
1846 IDC_QUALITY_LINES));
1847 ldPrefs->setBlackHighlights(getCheck(hGeometryPage,
1848 IDC_ALWAYS_BLACK));
1849 }
1850 ldPrefs->setEdgeThickness(CUIDialog::trackBarGetPos(hGeometryPage,
1851 IDC_EDGE_THICKNESS));
1852 ldPrefs->applyGeometrySettings();
1853 }
1854 ldPrefs->commitGeometrySettings();
1855 }
1856
getSelectedLightDirection(void)1857 LDPreferences::LightDirection LDViewPreferences::getSelectedLightDirection(void)
1858 {
1859 LDPreferences::LightDirection lightDirection =
1860 LDPreferences::CustomDirection;
1861 for (IntIntMap::const_iterator it = lightDirIndexToId.begin()
1862 ; it != lightDirIndexToId.end(); it++)
1863 {
1864 if (getCachedCheck(hEffectsPage, it->second))
1865 {
1866 lightDirection =
1867 (LDPreferences::LightDirection)(it->first + 1);
1868 break;
1869 }
1870 }
1871 return lightDirection;
1872 }
1873
applyEffectsChanges(void)1874 void LDViewPreferences::applyEffectsChanges(void)
1875 {
1876 if (hEffectsPage)
1877 {
1878 ldPrefs->setUseLighting(getCachedCheck(hEffectsPage, IDC_LIGHTING));
1879 if (ldPrefs->getUseLighting())
1880 {
1881 LDPreferences::LightDirection lightDirection =
1882 getSelectedLightDirection();
1883 ldPrefs->setQualityLighting(getCheck(hEffectsPage,
1884 IDC_LIGHTING_QUALITY));
1885 ldPrefs->setSubduedLighting(getCheck(hEffectsPage,
1886 IDC_LIGHTING_SUBDUED));
1887 ldPrefs->setUseSpecular(getCheck(hEffectsPage, IDC_SPECULAR));
1888 ldPrefs->setOneLight(getCheck(hEffectsPage,
1889 IDC_ALTERNATE_LIGHTING));
1890 if (lightDirection != LDPreferences::CustomDirection)
1891 {
1892 ldPrefs->setLightDirection(lightDirection);
1893 }
1894 if (getCheck(hEffectsPage, IDC_DRAW_LIGHT_DATS))
1895 {
1896 ldPrefs->setDrawLightDats(true);
1897 ldPrefs->setOptionalStandardLight(getCheck(hEffectsPage,
1898 IDC_OPTIONAL_STANDARD_LIGHT));
1899 }
1900 else
1901 {
1902 ldPrefs->setDrawLightDats(false);
1903 }
1904 }
1905 // NOTE: the following setting doesn't require lighting to be enabled.
1906 ldPrefs->setNoLightGeom(getCheck(hEffectsPage, IDC_HIDE_LIGHT_DAT));
1907 ldPrefs->setStereoEyeSpacing(CUIDialog::trackBarGetPos(hEffectsPage,
1908 IDC_STEREO_SPACING));
1909 ldPrefs->setCutawayAlpha(CUIDialog::trackBarGetPos(hEffectsPage,
1910 IDC_CUTAWAY_OPACITY));
1911 ldPrefs->setCutawayThickness(CUIDialog::trackBarGetPos(hEffectsPage,
1912 IDC_CUTAWAY_THICKNESS));
1913 ldPrefs->setUseStipple(getCheck(hEffectsPage, IDC_STIPPLE));
1914 ldPrefs->setSortTransparent(getCheck(hEffectsPage, IDC_SORT));
1915 ldPrefs->setUseFlatShading(getCheck(hEffectsPage, IDC_FLAT_SHADING));
1916 ldPrefs->setPerformSmoothing(getCheck(hEffectsPage, IDC_SMOOTH_CURVES));
1917 ldPrefs->applyEffectsSettings();
1918 }
1919 ldPrefs->commitEffectsSettings();
1920 }
1921
applyPrimitivesChanges(void)1922 void LDViewPreferences::applyPrimitivesChanges(void)
1923 {
1924 if (hPrimitivesPage)
1925 {
1926 ldPrefs->setAllowPrimitiveSubstitution(getCachedCheck(hPrimitivesPage,
1927 IDC_PRIMITIVE_SUBSTITUTION));
1928 if (ldPrefs->getAllowPrimitiveSubstitution())
1929 {
1930 ldPrefs->setTextureStuds(getCheck(hPrimitivesPage,
1931 IDC_TEXTURE_STUDS));
1932 ldPrefs->setCurveQuality(CUIDialog::trackBarGetPos(hPrimitivesPage,
1933 IDC_CURVE_QUALITY));
1934 }
1935 ldPrefs->setTexmaps(getCheck(hPrimitivesPage, IDC_TEXMAPS));
1936 if (getTexmaps())
1937 {
1938 ldPrefs->setTextureOffsetFactor(textureOffsetFromSliderValue(
1939 trackBarGetPos(hTextureOffsetSlider)));
1940 }
1941 ldPrefs->setQualityStuds(!getCheck(hPrimitivesPage, IDC_STUD_QUALITY));
1942 ldPrefs->setHiResPrimitives(getCheck(hPrimitivesPage, IDC_HI_RES));
1943 ldPrefs->applyPrimitivesSettings();
1944 }
1945 ldPrefs->commitPrimitivesSettings();
1946 }
1947
applyUpdatesChanges(void)1948 void LDViewPreferences::applyUpdatesChanges(void)
1949 {
1950 if (hUpdatesPage)
1951 {
1952 ucstring tempString;
1953 int tempNum;
1954
1955 ldPrefs->setCheckPartTracker(getCheck(hUpdatesPage,
1956 IDC_CHECK_PART_TRACKER));
1957 if (ldPrefs->getCheckPartTracker())
1958 {
1959 UCCHAR buf[128];
1960
1961 if (windowGetValue(hMissingParts, tempNum))
1962 {
1963 if (tempNum > 0)
1964 {
1965 ldPrefs->setMissingPartWait(tempNum);
1966 }
1967 }
1968 sucprintf(buf, COUNT_OF(buf), _UC("%0d"), ldPrefs->getMissingPartWait());
1969 windowSetText(hMissingParts, buf);
1970 if (windowGetValue(hUpdatedParts, tempNum))
1971 {
1972 if (tempNum > 0)
1973 {
1974 ldPrefs->setUpdatedPartWait(tempNum);
1975 }
1976 }
1977 sucprintf(buf, COUNT_OF(buf), _UC("%0d"), ldPrefs->getUpdatedPartWait());
1978 windowSetText(hUpdatedParts, buf);
1979 }
1980 windowGetText(hProxyServer, tempString);
1981 if (!tempString.empty())
1982 {
1983 std::string utf8Temp;
1984 ucstringtoutf8(utf8Temp, tempString);
1985 ldPrefs->setProxyServer(utf8Temp.c_str());
1986 }
1987 if (windowGetValue(hProxyPort, tempNum))
1988 {
1989 ldPrefs->setProxyPort(tempNum);
1990 }
1991 ldPrefs->applyUpdatesSettings();
1992 }
1993 ldPrefs->commitUpdatesSettings();
1994 }
1995
applyChanges(void)1996 void LDViewPreferences::applyChanges(void)
1997 {
1998 applyGeneralChanges();
1999 applyGeometryChanges();
2000 applyEffectsChanges();
2001 applyPrimitivesChanges();
2002 applyUpdatesChanges();
2003 applyPrefSetsChanges(); // Note that if there are any pref sets changes,
2004 // there can't be any other changes.
2005 }
2006
saveDefaultView(void)2007 void LDViewPreferences::saveDefaultView(void)
2008 {
2009 ldPrefs->saveDefaultView();
2010 }
2011
resetDefaultView(void)2012 void LDViewPreferences::resetDefaultView(void)
2013 {
2014 ldPrefs->resetDefaultView();
2015 }
2016
getRGB(int color,int & r,int & g,int & b)2017 void LDViewPreferences::getRGB(int color, int &r, int &g, int &b)
2018 {
2019 r = color & 0xFF;
2020 g = (color >> 8) & 0xFF;
2021 b = (color >> 16) & 0xFF;
2022 }
2023
chooseBackgroundColor(void)2024 void LDViewPreferences::chooseBackgroundColor(void)
2025 {
2026 COLORREF backgroundColor = getBackgroundColor();
2027 int r, g, b;
2028
2029 chooseColor(hBackgroundColorButton, hBackgroundColorBitmap,
2030 backgroundColor);
2031 r = GetRValue(backgroundColor);
2032 g = GetGValue(backgroundColor);
2033 b = GetBValue(backgroundColor);
2034 ldPrefs->setBackgroundColor(r, g, b);
2035 }
2036
chooseDefaultColor(void)2037 void LDViewPreferences::chooseDefaultColor(void)
2038 {
2039 COLORREF defaultColor = getDefaultColor();
2040 int r, g, b;
2041
2042 chooseColor(hDefaultColorButton, hDefaultColorBitmap, defaultColor);
2043 r = GetRValue(defaultColor);
2044 g = GetGValue(defaultColor);
2045 b = GetBValue(defaultColor);
2046 ldPrefs->setDefaultColor(r, g, b);
2047 }
2048
chooseColor(HWND hColorButton,HBITMAP hColorBitmap,COLORREF & color)2049 void LDViewPreferences::chooseColor(HWND hColorButton, HBITMAP hColorBitmap,
2050 COLORREF &color)
2051 {
2052 CHOOSECOLOR chooseColor;
2053 int i;
2054 COLORREF customColors[16];
2055 int r, g, b;
2056
2057 for (i = 0; i < 16; i++)
2058 {
2059 ldPrefs->getCustomColor(i, r, g, b);
2060 customColors[i] = RGB(r, g, b);
2061 }
2062 memset(&chooseColor, 0, sizeof CHOOSECOLOR);
2063 chooseColor.lStructSize = sizeof CHOOSECOLOR;
2064 chooseColor.hwndOwner = hPropSheet;
2065 chooseColor.rgbResult = color;
2066 chooseColor.lpCustColors = customColors;
2067 chooseColor.Flags = CC_ANYCOLOR | CC_RGBINIT;
2068 EnableWindow(hPropSheet, FALSE);
2069 if (ChooseColor(&chooseColor))
2070 {
2071 color = chooseColor.rgbResult;
2072 redrawColorBitmap(hColorButton, hColorBitmap, color);
2073 }
2074 for (i = 0; i < 16; i++)
2075 {
2076 r = GetRValue(customColors[i]);
2077 g = GetGValue(customColors[i]);
2078 b = GetBValue(customColors[i]);
2079 ldPrefs->setCustomColor(i, r, g, b);
2080 }
2081 EnableWindow(hPropSheet, TRUE);
2082 }
2083
browseForDir(CUCSTR prompt,HWND hTextField,ucstring & dir)2084 void LDViewPreferences::browseForDir(
2085 CUCSTR prompt,
2086 HWND hTextField,
2087 ucstring &dir)
2088 {
2089 ucstring newDir = LDViewWindow::browseForDir(prompt, dir.c_str());
2090
2091 if (!newDir.empty())
2092 {
2093 dir = newDir;
2094 SetWindowText(hTextField, dir.c_str());
2095 enableApply(GetParent(hTextField));
2096 }
2097 }
2098
doGeneralClick(int controlId,HWND)2099 void LDViewPreferences::doGeneralClick(int controlId, HWND /*controlHWnd*/)
2100 {
2101 switch (controlId)
2102 {
2103 case IDC_FS_REFRESH:
2104 doFSRefresh();
2105 break;
2106 case IDC_BACKGROUND_COLOR:
2107 chooseBackgroundColor();
2108 break;
2109 case IDC_DEFAULT_COLOR:
2110 chooseDefaultColor();
2111 break;
2112 case IDC_GENERAL_RESET:
2113 ldPrefs->loadDefaultGeneralSettings(false);
2114 setupGeneralPage();
2115 break;
2116 case IDC_BROWSE_SNAPSHOTS_DIR:
2117 browseForDir(ls(_UC("BrowseForSnapshotDir")), hSnapshotDirField,
2118 snapshotDir);
2119 break;
2120 case IDC_BROWSE_PARTS_LIST_DIR:
2121 browseForDir(ls(_UC("BrowseForPartsListDir")), hPartsListDirField,
2122 partsListDir);
2123 break;
2124 case IDC_BROWSE_EXPORT_DIR:
2125 browseForDir(ls(_UC("BrowseForExportListDir")), hExportDirField,
2126 exportDir);
2127 break;
2128 }
2129 enableApply(hGeneralPage);
2130 }
2131
doGeometryClick(int controlId,HWND)2132 void LDViewPreferences::doGeometryClick(int controlId, HWND /*controlHWnd*/)
2133 {
2134 switch (controlId)
2135 {
2136 case IDC_HIGHLIGHTS:
2137 doHighlights();
2138 break;
2139 case IDC_CONDITIONAL_HIGHLIGHTS:
2140 doConditionals();
2141 break;
2142 case IDC_WIREFRAME:
2143 doWireframe();
2144 break;
2145 case IDC_BFC:
2146 doBfc();
2147 break;
2148 case IDC_SEAMS:
2149 doSeams();
2150 break;
2151 case IDC_GEOMETRY_RESET:
2152 ldPrefs->loadDefaultGeometrySettings(false);
2153 setupGeometryPage();
2154 break;
2155 }
2156 enableApply(hGeometryPage);
2157 }
2158
doEffectsClick(int controlId,HWND)2159 void LDViewPreferences::doEffectsClick(int controlId, HWND /*controlHWnd*/)
2160 {
2161 switch (controlId)
2162 {
2163 case IDC_LIGHTING:
2164 doLighting();
2165 break;
2166 case IDC_DRAW_LIGHT_DATS:
2167 doDrawLightDats();
2168 break;
2169 case IDC_STIPPLE:
2170 doStipple();
2171 break;
2172 case IDC_SORT:
2173 doSort();
2174 break;
2175 case IDC_FLAT_SHADING:
2176 doFlatShading();
2177 break;
2178 case IDC_SMOOTH_CURVES:
2179 doSmoothCurves();
2180 break;
2181 case IDC_STEREO:
2182 doStereo();
2183 break;
2184 case IDC_HARDWARE_STEREO:
2185 ldPrefs->setStereoMode(LDVStereoHardware);
2186 break;
2187 case IDC_CROSS_EYED_STEREO:
2188 ldPrefs->setStereoMode(LDVStereoCrossEyed);
2189 break;
2190 case IDC_PARALLEL_STEREO:
2191 ldPrefs->setStereoMode(LDVStereoParallel);
2192 break;
2193 case IDC_CUTAWAY:
2194 doCutaway();
2195 break;
2196 case IDC_CUTAWAY_COLOR:
2197 ldPrefs->setCutawayMode(LDVCutawayWireframe);
2198 setupOpacitySlider();
2199 break;
2200 case IDC_CUTAWAY_MONOCHROME:
2201 ldPrefs->setCutawayMode(LDVCutawayStencil);
2202 setupOpacitySlider();
2203 break;
2204 case IDC_EFFECTS_RESET:
2205 ldPrefs->loadDefaultEffectsSettings(false);
2206 setupEffectsPage();
2207 break;
2208 }
2209 if (lightDirIdToIndex.find(controlId) != lightDirIdToIndex.end())
2210 {
2211 if (!getCachedCheck(hEffectsPage, controlId))
2212 {
2213 for (IntIntMap::const_iterator it = lightDirIndexToId.begin()
2214 ; it != lightDirIndexToId.end(); it++)
2215 {
2216 if (getCachedCheck(hEffectsPage, it->second))
2217 {
2218 getCachedCheck(hEffectsPage, it->second, true);
2219 InvalidateRect(lightAngleButtons[it->first], NULL, TRUE);
2220 }
2221 }
2222 getCachedCheck(hEffectsPage, controlId, true);
2223 }
2224 }
2225 enableApply(hEffectsPage);
2226 }
2227
doDeletePrefSet(void)2228 void LDViewPreferences::doDeletePrefSet(void)
2229 {
2230 ucstring selectedPrefSet = getSelectedPrefSet();
2231
2232 if (!selectedPrefSet.empty())
2233 {
2234 int selectedIndex = listBoxFindStringExact(hPrefSetsList, selectedPrefSet);
2235
2236 if (checkAbandon && getApplyEnabled())
2237 {
2238 if (messageBoxUC(hWindow,
2239 ls(_UC("PrefSetAbandonConfirm")),
2240 ls(_UC("AbandonChanges")),
2241 MB_YESNO | MB_ICONQUESTION) == IDYES)
2242 {
2243 abandonChanges();
2244 }
2245 else
2246 {
2247 return;
2248 }
2249 }
2250 checkAbandon = false;
2251 listBoxDeleteString(hPrefSetsList, selectedIndex);
2252 while (selectedIndex >= listBoxGetCount(hPrefSetsList) &&
2253 selectedIndex > 0)
2254 {
2255 --selectedIndex;
2256 }
2257 selectedPrefSet = getPrefSet(selectedIndex);
2258 selectPrefSet(selectedPrefSet, true);
2259 }
2260 }
2261
doNewPrefSet(void)2262 void LDViewPreferences::doNewPrefSet(void)
2263 {
2264 newPrefSetName.clear();
2265 if (DialogBoxParam(getLanguageModule(), MAKEINTRESOURCE(IDD_NEW_PREF_SET),
2266 hPropSheet, staticDialogProc, (LPARAM)this) == IDOK)
2267 {
2268 if (!newPrefSetName.empty())
2269 {
2270 listBoxAddString(hPrefSetsList, newPrefSetName);
2271 selectPrefSet(newPrefSetName);
2272 }
2273 }
2274 }
2275
getHotKey(int index)2276 ucstring LDViewPreferences::getHotKey(int index)
2277 {
2278 char key[128];
2279
2280 sprintf(key, "%s/Key%d", HOT_KEYS_KEY, index);
2281 UCSTR hotKeyTemp = TCUserDefaults::stringForKeyUC(key, NULL, false);
2282 ucstring hotKey = hotKeyTemp;
2283 delete[] hotKeyTemp;
2284 return hotKey;
2285 }
2286
getHotKey(const ucstring & currentPrefSetName)2287 int LDViewPreferences::getHotKey(const ucstring& currentPrefSetName)
2288 {
2289 int i;
2290 int retValue = -1;
2291
2292 for (i = 0; i < 10 && retValue == -1; i++)
2293 {
2294 ucstring prefSetName = getHotKey(i);
2295
2296 if (!prefSetName.empty())
2297 {
2298 if (currentPrefSetName == prefSetName)
2299 {
2300 retValue = i;
2301 }
2302 }
2303 }
2304 return retValue;
2305 }
2306
getCurrentHotKey(void)2307 int LDViewPreferences::getCurrentHotKey(void)
2308 {
2309 ucstring currentPrefSetName = getSelectedPrefSet();
2310 int retValue = -1;
2311
2312 if (!currentPrefSetName.empty())
2313 {
2314 retValue = getHotKey(currentPrefSetName);
2315 }
2316 return retValue;
2317 }
2318
performHotKey(int lhotKeyIndex)2319 bool LDViewPreferences::performHotKey(int lhotKeyIndex)
2320 {
2321 ucstring hotKeyPrefSetName = getHotKey(lhotKeyIndex);
2322 bool retValue = false;
2323
2324 if (!hotKeyPrefSetName.empty() && !hPropSheet)
2325 {
2326 const char *currentSessionName = TCUserDefaults::getSessionName();
2327 bool hotKeyIsDefault = hotKeyPrefSetName == DEFAULT_PREF_SET;
2328
2329 if (currentSessionName)
2330 {
2331 ucstring ucCurrentSessionName;
2332 utf8toucstring(ucCurrentSessionName, currentSessionName);
2333 if (ucCurrentSessionName == hotKeyPrefSetName)
2334 {
2335 retValue = true;
2336 }
2337 }
2338 else if (hotKeyIsDefault)
2339 {
2340 retValue = true;
2341 }
2342 if (!retValue)
2343 {
2344 bool changed = false;
2345
2346 if (hotKeyIsDefault)
2347 {
2348 TCUserDefaults::setSessionName(NULL, PREFERENCE_SET_KEY);
2349 changed = true;
2350 }
2351 else
2352 {
2353 TCStringArray *sessionNames =
2354 TCUserDefaults::getAllSessionNames();
2355
2356 std::string utf8Name;
2357 ucstringtoutf8(utf8Name, hotKeyPrefSetName);
2358 if (sessionNames->indexOfString(utf8Name.c_str()) != -1)
2359 {
2360 TCUserDefaults::setSessionName(utf8Name.c_str(),
2361 PREFERENCE_SET_KEY);
2362 {
2363 changed = true;
2364 }
2365 }
2366 sessionNames->release();
2367 }
2368 if (changed)
2369 {
2370 loadSettings();
2371 applySettings();
2372 retValue = true;
2373 }
2374 }
2375 }
2376 return retValue;
2377 }
2378
saveCurrentHotKey(void)2379 void LDViewPreferences::saveCurrentHotKey(void)
2380 {
2381 int currentHotKey = getCurrentHotKey();
2382
2383 if (currentHotKey >= 0)
2384 {
2385 char key[128];
2386
2387 sprintf(key, "%s/Key%d", HOT_KEYS_KEY, currentHotKey);
2388 TCUserDefaults::removeValue(key, false);
2389 }
2390 if (hotKeyIndex > 0)
2391 {
2392 char key[128];
2393 ucstring currentSessionName = getSelectedPrefSet();
2394
2395 sprintf(key, "%s/Key%d", HOT_KEYS_KEY, hotKeyIndex % 10);
2396 TCUserDefaults::setStringForKey(currentSessionName.c_str(), key, false);
2397 }
2398 }
2399
doPrefSetHotKey(void)2400 void LDViewPreferences::doPrefSetHotKey(void)
2401 {
2402 hotKeyIndex = getCurrentHotKey();
2403
2404 if (hotKeyIndex == -1)
2405 {
2406 hotKeyIndex++;
2407 }
2408 else if (hotKeyIndex == 0)
2409 {
2410 hotKeyIndex = 10;
2411 }
2412 if (DialogBoxParam(getLanguageModule(), MAKEINTRESOURCE(IDD_HOTKEY),
2413 hPropSheet, staticDialogProc, (LPARAM)this) == IDOK)
2414 {
2415 if (hotKeyIndex != CB_ERR)
2416 {
2417 saveCurrentHotKey();
2418 }
2419 }
2420 }
2421
doPrefSetsClick(int controlId,HWND)2422 void LDViewPreferences::doPrefSetsClick(int controlId, HWND /*controlHWnd*/)
2423 {
2424 switch (controlId)
2425 {
2426 case IDC_DELETE_PREF_SET:
2427 doDeletePrefSet();
2428 break;
2429 case IDC_NEW_PREF_SET:
2430 doNewPrefSet();
2431 break;
2432 case IDC_PREF_SET_HOT_KEY:
2433 doPrefSetHotKey();
2434 break;
2435 }
2436 enableApply(hPrefSetsPage);
2437 }
2438
doOtherClick(HWND hDlg,int controlId,HWND)2439 void LDViewPreferences::doOtherClick(HWND hDlg, int controlId,
2440 HWND /*controlHWnd*/)
2441 {
2442 if (controlId == IDC_NEW_PREF_SET_CANCEL)
2443 {
2444 EndDialog(hDlg, IDCANCEL);
2445 }
2446 else if (controlId == IDC_NEW_PREF_SET_OK)
2447 {
2448 ucstring editText;
2449
2450 CUIDialog::windowGetText(hDlg, IDC_NEW_PREF_SET_FIELD, editText);
2451 if (!editText.empty())
2452 {
2453 int index = listBoxFindStringExact(hPrefSetsList, editText);
2454
2455 if (index == LB_ERR)
2456 {
2457 if (editText.find('/') < editText.size() || editText.find('\\') < editText.size())
2458 {
2459 messageBoxUC(hDlg,
2460 ls(_UC("PrefSetNameBadChars")),
2461 ls(_UC("InvalidName")),
2462 MB_OK | MB_ICONWARNING);
2463 }
2464 else
2465 {
2466 newPrefSetName = editText;
2467 EndDialog(hDlg, IDOK);
2468 }
2469 }
2470 else
2471 {
2472 messageBoxUC(hDlg,
2473 ls(_UC("PrefSetAlreadyExists")),
2474 ls(_UC("DuplicateName")),
2475 MB_OK | MB_ICONWARNING);
2476 }
2477 }
2478 else
2479 {
2480 messageBoxUC(hDlg,
2481 ls(_UC("PrefSetNameRequired")),
2482 ls(_UC("EmptyName")), MB_OK | MB_ICONWARNING);
2483 }
2484 }
2485 else if (controlId == IDC_HOTKEY_OK)
2486 {
2487 hotKeyIndex = CUIDialog::comboGetCurSel(hDlg, IDC_HOTKEY_COMBO);
2488 EndDialog(hDlg, IDOK);
2489 }
2490 else if (controlId == IDC_APPLY || controlId == IDC_ABANDON ||
2491 controlId == IDCANCEL)
2492 {
2493 EndDialog(hDlg, controlId);
2494 }
2495 }
2496
setAniso(int value)2497 void LDViewPreferences::setAniso(int value)
2498 {
2499 UCCHAR label[128];
2500 float level = anisoFromSliderValue(value);
2501 int intLevel = (int)(level + 0.5);
2502
2503 ldPrefs->setAnisoLevel(level);
2504 if (intLevel >= 2)
2505 {
2506 sucprintf(label, COUNT_OF(label), ls(_UC("AnisoNx")), intLevel);
2507 }
2508 else
2509 {
2510 label[0] = 0;
2511 }
2512 windowSetText(hAnisoLevelLabel, label);
2513 }
2514
doPrimitivesClick(int controlId,HWND)2515 void LDViewPreferences::doPrimitivesClick(int controlId, HWND /*controlHWnd*/)
2516 {
2517 bool bDisableAniso = false;
2518
2519 switch (controlId)
2520 {
2521 case IDC_PRIMITIVE_SUBSTITUTION:
2522 doPrimitives();
2523 break;
2524 case IDC_TEXTURE_STUDS:
2525 doTextureStuds();
2526 break;
2527 case IDC_TEXMAPS:
2528 doTexmaps();
2529 break;
2530 case IDC_TEXTURE_NEAREST:
2531 ldPrefs->setTextureFilterType(GL_NEAREST_MIPMAP_NEAREST);
2532 bDisableAniso = true;
2533 break;
2534 case IDC_TEXTURE_BILINEAR:
2535 ldPrefs->setTextureFilterType(GL_LINEAR_MIPMAP_NEAREST);
2536 bDisableAniso = true;
2537 break;
2538 case IDC_TEXTURE_TRILINEAR:
2539 ldPrefs->setTextureFilterType(GL_LINEAR_MIPMAP_LINEAR);
2540 bDisableAniso = true;
2541 break;
2542 case IDC_TEXTURE_ANISO:
2543 {
2544 ldPrefs->setTextureFilterType(GL_LINEAR_MIPMAP_LINEAR);
2545 setAniso(trackBarGetPos(hAnisoLevelSlider));
2546 EnableWindow(hAnisoLevelSlider, TRUE);
2547 }
2548 break;
2549 case IDC_PRIMITIVES_RESET:
2550 ldPrefs->loadDefaultPrimitivesSettings(false);
2551 setupPrimitivesPage();
2552 break;
2553 }
2554 if (bDisableAniso)
2555 {
2556 setAniso(0);
2557 EnableWindow(hAnisoLevelSlider, FALSE);
2558 }
2559 enableApply(hPrimitivesPage);
2560 }
2561
doCheckPartTracker(void)2562 void LDViewPreferences::doCheckPartTracker(void)
2563 {
2564 if (getCheck(hUpdatesPage, IDC_CHECK_PART_TRACKER))
2565 {
2566 enableCheckPartTracker();
2567 }
2568 else
2569 {
2570 disableCheckPartTracker();
2571 }
2572 }
2573
doUpdatesClick(int controlId,HWND)2574 void LDViewPreferences::doUpdatesClick(int controlId, HWND /*controlHWnd*/)
2575 {
2576 ucstring tempString;
2577 int tempNum;
2578
2579 windowGetText(hProxyServer, tempString);
2580 if (!tempString.empty())
2581 {
2582 std::string utf8Temp;
2583 ucstringtoutf8(utf8Temp, tempString);
2584 ldPrefs->setProxyServer(utf8Temp.c_str());
2585 }
2586 if (windowGetValue(hProxyPort, tempNum))
2587 {
2588 ldPrefs->setProxyPort(tempNum);
2589 }
2590 switch (controlId)
2591 {
2592 case IDC_PROXY_NONE:
2593 ldPrefs->setProxyType(0);
2594 disableProxyServer();
2595 break;
2596 case IDC_PROXY_WINDOWS:
2597 ldPrefs->setProxyType(1);
2598 disableProxyServer();
2599 break;
2600 case IDC_PROXY_MANUAL:
2601 ldPrefs->setProxyType(2);
2602 enableProxyServer();
2603 break;
2604 case IDC_UPDATES_RESET:
2605 ldPrefs->loadDefaultUpdatesSettings(false);
2606 setupUpdatesPage();
2607 break;
2608 case IDC_RESET_TIMES:
2609 LDrawModelViewer::resetUnofficialDownloadTimes();
2610 break;
2611 case IDC_CHECK_PART_TRACKER:
2612 doCheckPartTracker();
2613 break;
2614 }
2615 enableApply(hUpdatesPage);
2616 }
2617
doComboSelChange(HWND hPage,int controlId,HWND)2618 DWORD LDViewPreferences::doComboSelChange(HWND hPage, int controlId,
2619 HWND /*controlHWnd*/)
2620 {
2621 ucstring selectedString;
2622 switch (controlId)
2623 {
2624 case IDC_FSAA_COMBO:
2625 int fsaaMode;
2626
2627 CUIDialog::windowGetText(hPage, controlId, selectedString);
2628 if (selectedString == ls(_UC("FsaaNone")))
2629 {
2630 fsaaMode = 0;
2631 }
2632 else
2633 {
2634 sucscanf(selectedString.c_str(), _UC("%d"), &fsaaMode);
2635 if (fsaaMode > 4)
2636 {
2637 fsaaMode = fsaaMode << 3;
2638 }
2639 else if (selectedString.find(ls(_UC("FsaaEnhanced"))) <
2640 selectedString.size())
2641 {
2642 fsaaMode |= 1;
2643 }
2644 }
2645 ldPrefs->setFsaaMode(fsaaMode);
2646 enableApply(hPage);
2647 break;
2648 case IDC_MEMORY_COMBO:
2649 enableApply(hPage);
2650 break;
2651 case IDC_SNAPSHOTS_DIR_COMBO:
2652 snapshotDirMode = (LDPreferences::DefaultDirMode)comboGetCurSel(
2653 hSnapshotDirCombo);
2654 updateSaveDir(hSnapshotDirField, hSnapshotBrowseButton, snapshotDirMode,
2655 snapshotDir);
2656 enableApply(hPage);
2657 break;
2658 case IDC_PARTS_LIST_DIR_COMBO:
2659 partsListDirMode = (LDPreferences::DefaultDirMode)comboGetCurSel(
2660 hPartsListDirCombo);
2661 updateSaveDir(hPartsListDirField, hPartsListBrowseButton,
2662 partsListDirMode, partsListDir);
2663 enableApply(hPage);
2664 break;
2665 case IDC_EXPORT_DIR_COMBO:
2666 exportDirMode = (LDPreferences::DefaultDirMode)comboGetCurSel(
2667 hExportDirCombo);
2668 updateSaveDir(hExportDirField, hExportBrowseButton, exportDirMode,
2669 exportDir);
2670 enableApply(hPage);
2671 break;
2672 }
2673 return 0;
2674 }
2675
doClick(HWND hPage,int controlId,HWND controlHWnd)2676 DWORD LDViewPreferences::doClick(HWND hPage, int controlId, HWND controlHWnd)
2677 {
2678 bool wasPaused = true;
2679
2680 if (modelViewer)
2681 {
2682 wasPaused = modelViewer->getPaused() != 0;
2683 if (!wasPaused)
2684 {
2685 modelViewer->pause();
2686 }
2687 }
2688 if (hPage == hGeneralPage)
2689 {
2690 doGeneralClick(controlId, controlHWnd);
2691 }
2692 else if (hPage == hGeometryPage)
2693 {
2694 doGeometryClick(controlId, controlHWnd);
2695 }
2696 else if (hPage == hEffectsPage)
2697 {
2698 doEffectsClick(controlId, controlHWnd);
2699 }
2700 else if (hPage == hPrimitivesPage)
2701 {
2702 doPrimitivesClick(controlId, controlHWnd);
2703 }
2704 else if (hPage == hUpdatesPage)
2705 {
2706 doUpdatesClick(controlId, controlHWnd);
2707 }
2708 else if (hPage == hPrefSetsPage)
2709 {
2710 doPrefSetsClick(controlId, controlHWnd);
2711 }
2712 else
2713 {
2714 doOtherClick(hPage, controlId, controlHWnd);
2715 }
2716 if (!wasPaused)
2717 {
2718 modelViewer->unpause();
2719 }
2720 return 0;
2721 }
2722
doFSRefresh(void)2723 void LDViewPreferences::doFSRefresh(void)
2724 {
2725 if (getCheck(hGeneralPage, IDC_FS_REFRESH))
2726 {
2727 EnableWindow(hFullScreenRateField, TRUE);
2728 }
2729 else
2730 {
2731 CUIDialog::windowSetText(hGeneralPage, IDC_FS_RATE, _UC(""));
2732 EnableWindow(hFullScreenRateField, FALSE);
2733 }
2734 }
2735
doStipple(void)2736 void LDViewPreferences::doStipple(void)
2737 {
2738 if (getCheck(hEffectsPage, IDC_STIPPLE))
2739 {
2740 setCheck(hEffectsPage, IDC_SORT, false);
2741 }
2742 }
2743
doSort(void)2744 void LDViewPreferences::doSort(void)
2745 {
2746 if (getCheck(hEffectsPage, IDC_SORT))
2747 {
2748 setCheck(hEffectsPage, IDC_STIPPLE, false);
2749 }
2750 }
2751
doFlatShading(void)2752 void LDViewPreferences::doFlatShading(void)
2753 {
2754 if (getCheck(hEffectsPage, IDC_FLAT_SHADING))
2755 {
2756 setCheck(hEffectsPage, IDC_SMOOTH_CURVES, false);
2757 }
2758 }
2759
doSmoothCurves(void)2760 void LDViewPreferences::doSmoothCurves(void)
2761 {
2762 if (getCheck(hEffectsPage, IDC_SMOOTH_CURVES))
2763 {
2764 setCheck(hEffectsPage, IDC_FLAT_SHADING, false);
2765 }
2766 }
2767
doHighlights(void)2768 void LDViewPreferences::doHighlights(void)
2769 {
2770 if (getCachedCheck(hGeometryPage, IDC_HIGHLIGHTS, true))
2771 {
2772 enableEdges();
2773 }
2774 else
2775 {
2776 disableEdges();
2777 }
2778 }
2779
doConditionals(void)2780 void LDViewPreferences::doConditionals(void)
2781 {
2782 if (getCheck(hGeometryPage, IDC_CONDITIONAL_HIGHLIGHTS))
2783 {
2784 enableConditionals();
2785 }
2786 else
2787 {
2788 disableConditionals();
2789 }
2790 }
2791
setCheck(HWND hPage,int buttonId,bool value)2792 void LDViewPreferences::setCheck(HWND hPage, int buttonId, bool value)
2793 {
2794 CUIDialog::buttonSetChecked(hPage, buttonId, value);
2795 }
2796
getCheck(HWND hPage,int buttonId)2797 bool LDViewPreferences::getCheck(HWND hPage, int buttonId)
2798 {
2799 return CUIDialog::buttonIsChecked(hPage, buttonId);
2800 }
2801
getCachedCheck(HWND hPage,int buttonId,bool action)2802 bool LDViewPreferences::getCachedCheck(HWND hPage, int buttonId, bool action)
2803 {
2804 if (hButtonTheme)
2805 {
2806 HWND hButton = GetDlgItem(hPage, buttonId);
2807
2808 if (action)
2809 {
2810 checkStates[hButton] = !checkStates[hButton];
2811 }
2812 return checkStates[hButton];
2813 }
2814 else
2815 {
2816 return getCheck(hPage, buttonId);
2817 }
2818 }
2819
doWireframe(void)2820 void LDViewPreferences::doWireframe(void)
2821 {
2822 if (getCachedCheck(hGeometryPage, IDC_WIREFRAME, true))
2823 {
2824 enableWireframe();
2825 }
2826 else
2827 {
2828 disableWireframe();
2829 }
2830 }
2831
doBfc(void)2832 void LDViewPreferences::doBfc(void)
2833 {
2834 if (getCachedCheck(hGeometryPage, IDC_BFC, true))
2835 {
2836 enableBfc();
2837 }
2838 else
2839 {
2840 disableBfc();
2841 }
2842 }
2843
doLighting(void)2844 void LDViewPreferences::doLighting(void)
2845 {
2846 if (getCachedCheck(hEffectsPage, IDC_LIGHTING, true))
2847 {
2848 enableLighting();
2849 }
2850 else
2851 {
2852 disableLighting();
2853 }
2854 }
2855
doDrawLightDats(void)2856 void LDViewPreferences::doDrawLightDats(void)
2857 {
2858 BOOL enabled = FALSE;
2859 BOOL checked = FALSE;
2860
2861 if (getCachedCheck(hEffectsPage, IDC_DRAW_LIGHT_DATS, true))
2862 {
2863 enabled = TRUE;
2864 checked = ldPrefs->getOptionalStandardLight() ? TRUE : FALSE;
2865 }
2866 EnableWindow(hLightOptionalStandardButton, enabled);
2867 buttonSetCheck(hLightOptionalStandardButton, checked);
2868 }
2869
doStereo(void)2870 void LDViewPreferences::doStereo(void)
2871 {
2872 if (getCachedCheck(hEffectsPage, IDC_STEREO, true))
2873 {
2874 ldPrefs->setStereoMode(LDVStereoCrossEyed);
2875 enableStereo();
2876 }
2877 else
2878 {
2879 ldPrefs->setStereoMode(LDVStereoNone);
2880 disableStereo();
2881 }
2882 }
2883
doCutaway(void)2884 void LDViewPreferences::doCutaway(void)
2885 {
2886 if (getCachedCheck(hEffectsPage, IDC_CUTAWAY, true))
2887 {
2888 ldPrefs->setCutawayMode(LDVCutawayWireframe);
2889 enableCutaway();
2890 }
2891 else
2892 {
2893 ldPrefs->setCutawayMode(LDVCutawayNormal);
2894 disableCutaway();
2895 }
2896 }
2897
doSeams(void)2898 void LDViewPreferences::doSeams(void)
2899 {
2900 if (getCheck(hGeometryPage, IDC_SEAMS))
2901 {
2902 enableSeams();
2903 }
2904 else
2905 {
2906 disableSeams();
2907 }
2908 }
2909
doPrimitives(void)2910 void LDViewPreferences::doPrimitives(void)
2911 {
2912 if (getCachedCheck(hPrimitivesPage, IDC_PRIMITIVE_SUBSTITUTION, true))
2913 {
2914 enablePrimitives();
2915 }
2916 else
2917 {
2918 disablePrimitives();
2919 }
2920 }
2921
updateTextureFilteringEnabled(void)2922 void LDViewPreferences::updateTextureFilteringEnabled(void)
2923 {
2924 if (getCheck(hPrimitivesPage, IDC_TEXMAPS) ||
2925 (getCachedCheck(hPrimitivesPage, IDC_PRIMITIVE_SUBSTITUTION, false) &&
2926 getCheck(hPrimitivesPage, IDC_TEXTURE_STUDS)))
2927 {
2928 enableTextureFiltering();
2929 }
2930 else
2931 {
2932 disableTextureFiltering();
2933 }
2934 }
2935
updateTexmapsEnabled(void)2936 void LDViewPreferences::updateTexmapsEnabled(void)
2937 {
2938 if (getCheck(hPrimitivesPage, IDC_TEXMAPS))
2939 {
2940 enableTexmaps();
2941 }
2942 else
2943 {
2944 disableTexmaps();
2945 }
2946 }
2947
doTextureStuds(void)2948 void LDViewPreferences::doTextureStuds(void)
2949 {
2950 updateTextureFilteringEnabled();
2951 }
2952
doTexmaps(void)2953 void LDViewPreferences::doTexmaps(void)
2954 {
2955 updateTextureFilteringEnabled();
2956 updateTexmapsEnabled();
2957 }
2958
doReset(void)2959 void LDViewPreferences::doReset(void)
2960 {
2961 loadSettings();
2962 }
2963
doDialogVScroll(HWND hDlg,int scrollCode,int position,HWND hScrollBar)2964 BOOL LDViewPreferences::doDialogVScroll(HWND hDlg, int scrollCode, int position,
2965 HWND hScrollBar)
2966 {
2967 if (scrollCode == SB_THUMBPOSITION && hScrollBar == hSeamSpin)
2968 {
2969 UCCHAR seamWidthString[128];
2970 int seamWidth = ldPrefs->getSeamWidth();
2971
2972 seamWidth += (position - seamWidth);
2973 ldPrefs->setSeamWidth(seamWidth);
2974 sucprintf(seamWidthString, COUNT_OF(seamWidthString), _UC("%0.2f"),
2975 seamWidth / 100.0f);
2976 CUIDialog::windowSetText(hDlg, IDC_SEAM_WIDTH_FIELD, seamWidthString);
2977 SendDlgItemMessage(hDlg, IDC_SEAM_SPIN, UDM_SETPOS, 0, seamWidth);
2978 setCheck(hGeometryPage, IDC_SEAMS, seamWidth != 0);
2979 enableApply(hGeometryPage);
2980 }
2981 return TRUE;
2982 }
2983
setupPage(int pageNumber)2984 void LDViewPreferences::setupPage(int pageNumber)
2985 {
2986 if (pageNumber == generalPageNumber)
2987 {
2988 setupGeneralPage();
2989 }
2990 else if (pageNumber == geometryPageNumber)
2991 {
2992 setupGeometryPage();
2993 }
2994 else if (pageNumber == effectsPageNumber)
2995 {
2996 setupEffectsPage();
2997 }
2998 else if (pageNumber == primitivesPageNumber)
2999 {
3000 setupPrimitivesPage();
3001 }
3002 else if (pageNumber == updatesPageNumber)
3003 {
3004 setupUpdatesPage();
3005 }
3006 else if (pageNumber == prefSetsPageNumber)
3007 {
3008 setupPrefSetsPage();
3009 }
3010 disableApply(hwndArray->pointerAtIndex(pageNumber));
3011 }
3012
setupFov(bool warn)3013 void LDViewPreferences::setupFov(bool warn)
3014 {
3015 UCCHAR buf[1024];
3016 TCFloat minFov = getMinFov();
3017 TCFloat maxFov = getMaxFov();
3018
3019 SendDlgItemMessage(hGeneralPage, IDC_FOV, EM_SETLIMITTEXT, 5, 0);
3020 sucprintf(buf, COUNT_OF(buf), _UC("%.4g"), ldPrefs->getFov());
3021 CUIDialog::windowSetText(hGeneralPage, IDC_FOV, buf);
3022 sucprintf(buf, COUNT_OF(buf), _UC("(%g - %g)"), minFov, maxFov);
3023 CUIDialog::windowSetText(hGeneralPage, IDC_FOV_RANGE_LABEL, buf);
3024 if (warn)
3025 {
3026 sucprintf(buf, COUNT_OF(buf), ls(_UC("FovRangeError")), minFov, maxFov);
3027 messageBoxUC(hPropSheet, buf, ls(_UC("InvalidValue")),
3028 MB_OK | MB_ICONWARNING);
3029 }
3030 }
3031
setupMemoryUsage(void)3032 void LDViewPreferences::setupMemoryUsage(void)
3033 {
3034 CUIDialog::comboResetContent(hGeneralPage, IDC_MEMORY_COMBO);
3035 CUIDialog::comboAddString(hGeneralPage, IDC_MEMORY_COMBO, ls(_UC("Low")));
3036 CUIDialog::comboAddString(hGeneralPage, IDC_MEMORY_COMBO, ls(_UC("Medium")));
3037 CUIDialog::comboAddString(hGeneralPage, IDC_MEMORY_COMBO, ls(_UC("High")));
3038 CUIDialog::comboSetCurSel(hGeneralPage, IDC_MEMORY_COMBO, ldPrefs->getMemoryUsage());
3039 }
3040
updateSaveDir(HWND hTextField,HWND hBrowseButton,LDPreferences::DefaultDirMode dirMode,const ucstring & filename)3041 void LDViewPreferences::updateSaveDir(
3042 HWND hTextField,
3043 HWND hBrowseButton,
3044 LDPreferences::DefaultDirMode dirMode,
3045 const ucstring &filename)
3046 {
3047 BOOL enable = FALSE;
3048
3049 if (dirMode == LDPreferences::DDMSpecificDir)
3050 {
3051 SetWindowText(hTextField, filename.c_str());
3052 enable = TRUE;
3053 }
3054 else
3055 {
3056 SetWindowText(hTextField, _UC(""));
3057 }
3058 EnableWindow(hTextField, enable);
3059 EnableWindow(hBrowseButton, enable);
3060 }
3061
setupSaveDir(HWND hComboBox,HWND hTextField,HWND hBrowseButton,LDPreferences::DefaultDirMode dirMode,const ucstring & filename,CUCSTR nameKey)3062 void LDViewPreferences::setupSaveDir(
3063 HWND hComboBox,
3064 HWND hTextField,
3065 HWND hBrowseButton,
3066 LDPreferences::DefaultDirMode dirMode,
3067 const ucstring &filename,
3068 CUCSTR nameKey)
3069 {
3070 ucstring lastSaved = ls(_UC("LastSaved"));
3071
3072 lastSaved += ls(nameKey);
3073 comboResetContent(hComboBox);
3074 comboAddString(hComboBox, ls(_UC("Model")));
3075 comboAddString(hComboBox, lastSaved.c_str());
3076 comboAddString(hComboBox, ls(_UC("Specified")));
3077 comboSetCurSel(hComboBox, dirMode);
3078 updateSaveDir(hTextField, hBrowseButton, dirMode, filename);
3079 }
3080
setupSaveDirs(void)3081 void LDViewPreferences::setupSaveDirs(void)
3082 {
3083 hSnapshotDirCombo = GetDlgItem(hGeneralPage, IDC_SNAPSHOTS_DIR_COMBO);
3084 hSnapshotDirField = GetDlgItem(hGeneralPage, IDC_SNAPSHOTS_DIR);
3085 hSnapshotBrowseButton = GetDlgItem(hGeneralPage, IDC_BROWSE_SNAPSHOTS_DIR);
3086 snapshotDirMode = ldPrefs->getSaveDirMode(LDPreferences::SOSnapshot);
3087 utf8toucstring(snapshotDir,
3088 ldPrefs->getSaveDir(LDPreferences::SOSnapshot));
3089 setupSaveDir(hSnapshotDirCombo, hSnapshotDirField, hSnapshotBrowseButton,
3090 snapshotDirMode, snapshotDir, _UC("Snapshot"));
3091
3092 hPartsListDirCombo = GetDlgItem(hGeneralPage, IDC_PARTS_LIST_DIR_COMBO);
3093 hPartsListDirField = GetDlgItem(hGeneralPage, IDC_PARTS_LIST_DIR);
3094 hPartsListBrowseButton = GetDlgItem(hGeneralPage,
3095 IDC_BROWSE_PARTS_LIST_DIR);
3096 partsListDirMode = ldPrefs->getSaveDirMode(LDPreferences::SOPartsList);
3097 utf8toucstring(partsListDir,
3098 ldPrefs->getSaveDir(LDPreferences::SOPartsList));
3099 setupSaveDir(hPartsListDirCombo, hPartsListDirField, hPartsListBrowseButton,
3100 partsListDirMode, partsListDir, _UC("PartsList"));
3101
3102 hExportDirCombo = GetDlgItem(hGeneralPage, IDC_EXPORT_DIR_COMBO);
3103 hExportDirField = GetDlgItem(hGeneralPage, IDC_EXPORT_DIR);
3104 hExportBrowseButton = GetDlgItem(hGeneralPage, IDC_BROWSE_EXPORT_DIR);
3105 exportDirMode = ldPrefs->getSaveDirMode(LDPreferences::SOExport);
3106 utf8toucstring(exportDir,
3107 ldPrefs->getSaveDir(LDPreferences::SOExport));
3108 setupSaveDir(hExportDirCombo, hExportDirField, hExportBrowseButton,
3109 exportDirMode, exportDir, _UC("Export"));
3110 }
3111
setupGeneralPage(void)3112 void LDViewPreferences::setupGeneralPage(void)
3113 {
3114 hGeneralPage = hwndArray->pointerAtIndex(generalPageNumber);
3115 setupAntialiasing();
3116 setCheck(hGeneralPage, IDC_TRANS_DEFAULT_COLOR,
3117 ldPrefs->getTransDefaultColor());
3118 setCheck(hGeneralPage, IDC_PROCESS_LDCONFIG,
3119 ldPrefs->getProcessLdConfig());
3120 setCheck(hGeneralPage, IDC_RANDOM_COLORS, ldPrefs->getRandomColors());
3121 setCheck(hGeneralPage, IDC_FRAME_RATE, ldPrefs->getShowFps());
3122 setCheck(hGeneralPage, IDC_SHOW_AXES, ldPrefs->getShowAxes());
3123 setCheck(hGeneralPage, IDC_SHOW_ERRORS, ldPrefs->getShowErrors());
3124 setupFov();
3125 setupFullScreenRefresh();
3126 setupBackgroundColorButton();
3127 setupDefaultColorButton();
3128 setupMemoryUsage();
3129 setupSaveDirs();
3130 }
3131
enableWireframe(BOOL enable)3132 void LDViewPreferences::enableWireframe(BOOL enable /*= TRUE*/)
3133 {
3134 EnableWindow(hWireframeFogButton, enable);
3135 EnableWindow(hRemoveHiddenLinesButton, enable);
3136 EnableWindow(hWireframeThicknessLabel, enable);
3137 EnableWindow(hWireframeThicknessSlider, enable);
3138 }
3139
disableWireframe(void)3140 void LDViewPreferences::disableWireframe(void)
3141 {
3142 enableWireframe(FALSE);
3143 }
3144
enableBfc(BOOL enable)3145 void LDViewPreferences::enableBfc(BOOL enable /*= TRUE*/)
3146 {
3147 EnableWindow(hRedBackFacesButton, enable);
3148 EnableWindow(hGreenFrontFacesButton, enable);
3149 EnableWindow(hBlueNeutralFacesButton, enable);
3150 }
3151
disableBfc(void)3152 void LDViewPreferences::disableBfc(void)
3153 {
3154 enableBfc(FALSE);
3155 }
3156
initThemesButton(HWND hButton)3157 void LDViewPreferences::initThemesButton(HWND hButton)
3158 {
3159 if (CUIThemes::isThemeLibLoaded() && !hButtonTheme)
3160 {
3161 hButtonTheme = CUIThemes::openThemeData(hButton, L"Button");
3162 }
3163 }
3164
3165 /*
3166 void LDViewPreferences::initThemesTab(HWND hStatic)
3167 {
3168 if (CUIThemes::isThemeLibLoaded() && !hTabTheme)
3169 {
3170 hTabTheme = CUIThemes::openThemeData(hStatic, L"Tab");
3171 }
3172 }
3173 */
3174
setupGroupCheckButton(HWND hPage,int buttonId,bool state)3175 void LDViewPreferences::setupGroupCheckButton(HWND hPage, int buttonId,
3176 bool state)
3177 {
3178 bool done = false;
3179 HWND hButton = GetDlgItem(hPage, buttonId);
3180 checkStates[hButton] = state;
3181 if (CUIThemes::isThemeLibLoaded() && !haveWindowsVistaOrLater())
3182 {
3183 // This is really only useful in Windows XP, since all it does
3184 // is make the button text color match XP's group box text color.
3185 // Later versions of Windows don't use a special group box text
3186 // color. And in Windows 10, for some reason the check box comes
3187 // out too big on a screen set to 96DPI.
3188
3189 if (hButton)
3190 {
3191 initThemesButton(hButton);
3192 if (hButtonTheme)
3193 {
3194 DWORD dwStyle = GetWindowLong(hButton, GWL_STYLE);
3195
3196 if ((dwStyle & BS_TYPEMASK) != BS_OWNERDRAW)
3197 {
3198 dwStyle = (dwStyle & ~BS_TYPEMASK) | BS_OWNERDRAW;
3199 buttonSetStyle(hButton, dwStyle);
3200 }
3201 if (GetWindowLongPtr(hButton, GWLP_WNDPROC) !=
3202 (LONG_PTR)staticGroupCheckButtonProc)
3203 {
3204 SetWindowLongPtr(hButton, GWLP_USERDATA, (LONG_PTR)this);
3205 if (origButtonWindowProc)
3206 {
3207 SetWindowLongPtr(hButton, GWLP_WNDPROC,
3208 (LONG_PTR)staticGroupCheckButtonProc);
3209 }
3210 else
3211 {
3212 origButtonWindowProc = SetWindowLongPtr(hButton,
3213 GWLP_WNDPROC, (LONG_PTR)staticGroupCheckButtonProc);
3214 }
3215 }
3216 fixControlSize(hButton);
3217 InvalidateRect(hButton, NULL, TRUE);
3218 done = true;
3219 }
3220 else if (origButtonWindowProc)
3221 {
3222 SetWindowLongPtr(hButton, GWLP_WNDPROC,
3223 (LONG_PTR)origButtonWindowProc);
3224 }
3225 }
3226 }
3227 if (!done)
3228 {
3229 setCheck(hPage, buttonId, state);
3230 }
3231 }
3232
setupWireframe(void)3233 void LDViewPreferences::setupWireframe(void)
3234 {
3235 setupGroupCheckButton(hGeometryPage, IDC_WIREFRAME,
3236 ldPrefs->getDrawWireframe());
3237 hWireframeFogButton = GetDlgItem(hGeometryPage, IDC_WIREFRAME_FOG);
3238 hRemoveHiddenLinesButton = GetDlgItem(hGeometryPage,
3239 IDC_REMOVE_HIDDEN_LINES);
3240 hWireframeThicknessLabel = GetDlgItem(hGeometryPage,
3241 IDC_WIREFRAME_THICKNESS_LABEL);
3242 hWireframeThicknessSlider = GetDlgItem(hGeometryPage,
3243 IDC_WIREFRAME_THICKNESS);
3244 setCheck(hGeometryPage, IDC_WIREFRAME_FOG, ldPrefs->getUseWireframeFog());
3245 setCheck(hGeometryPage, IDC_REMOVE_HIDDEN_LINES,
3246 ldPrefs->getRemoveHiddenLines());
3247 CUIDialog::trackBarSetup(hGeometryPage, IDC_WIREFRAME_THICKNESS, 0, 5, 1,
3248 ldPrefs->getWireframeThickness());
3249 if (ldPrefs->getDrawWireframe())
3250 {
3251 enableWireframe();
3252 }
3253 else
3254 {
3255 disableWireframe();
3256 }
3257 }
3258
setupBfc(void)3259 void LDViewPreferences::setupBfc(void)
3260 {
3261 setupGroupCheckButton(hGeometryPage, IDC_BFC, ldPrefs->getBfc());
3262 hRedBackFacesButton = GetDlgItem(hGeometryPage, IDC_RED_BACK_FACES);
3263 hGreenFrontFacesButton = GetDlgItem(hGeometryPage, IDC_GREEN_FRONT_FACES);
3264 hBlueNeutralFacesButton = GetDlgItem(hGeometryPage, IDC_BLUE_NEUTRAL_FACES);
3265 setCheck(hGeometryPage, IDC_RED_BACK_FACES, ldPrefs->getRedBackFaces());
3266 setCheck(hGeometryPage, IDC_GREEN_FRONT_FACES,
3267 ldPrefs->getGreenFrontFaces());
3268 setCheck(hGeometryPage, IDC_BLUE_NEUTRAL_FACES,
3269 ldPrefs->getBlueNeutralFaces());
3270 if (ldPrefs->getBfc())
3271 {
3272 enableBfc();
3273 }
3274 else
3275 {
3276 disableBfc();
3277 }
3278 }
3279
enableConditionals(void)3280 void LDViewPreferences::enableConditionals(void)
3281 {
3282 EnableWindow(hShowAllConditionalButton, TRUE);
3283 EnableWindow(hShowConditionalControlsButton, TRUE);
3284 setCheck(hGeometryPage, IDC_ALL_CONDITIONAL,
3285 ldPrefs->getShowAllConditionalLines());
3286 setCheck(hGeometryPage, IDC_CONDITIONAL_CONTROLS,
3287 ldPrefs->getShowConditionalControlPoints());
3288 }
3289
disableConditionals(void)3290 void LDViewPreferences::disableConditionals(void)
3291 {
3292 EnableWindow(hShowAllConditionalButton, FALSE);
3293 EnableWindow(hShowConditionalControlsButton, FALSE);
3294 setCheck(hGeometryPage, IDC_ALL_CONDITIONAL, false);
3295 setCheck(hGeometryPage, IDC_CONDITIONAL_CONTROLS, false);
3296 }
3297
enableEdges(void)3298 void LDViewPreferences::enableEdges(void)
3299 {
3300 EnableWindow(hConditionalHighlightsButton, TRUE);
3301 EnableWindow(hEdgesOnlyButton, TRUE);
3302 EnableWindow(hQualityLinesButton, TRUE);
3303 EnableWindow(hAlwaysBlackButton, TRUE);
3304 EnableWindow(hEdgeThicknessLabel, TRUE);
3305 EnableWindow(hEdgeThicknessSlider, TRUE);
3306 if (ldPrefs->getDrawConditionalHighlights())
3307 {
3308 enableConditionals();
3309 }
3310 else
3311 {
3312 disableConditionals();
3313 }
3314 setCheck(hGeometryPage, IDC_EDGES_ONLY, ldPrefs->getEdgesOnly());
3315 setCheck(hGeometryPage, IDC_CONDITIONAL_HIGHLIGHTS,
3316 ldPrefs->getDrawConditionalHighlights());
3317 setCheck(hGeometryPage, IDC_QUALITY_LINES, ldPrefs->getUsePolygonOffset());
3318 setCheck(hGeometryPage, IDC_ALWAYS_BLACK, ldPrefs->getBlackHighlights());
3319 }
3320
disableEdges(void)3321 void LDViewPreferences::disableEdges(void)
3322 {
3323 EnableWindow(hConditionalHighlightsButton, FALSE);
3324 EnableWindow(hEdgesOnlyButton, FALSE);
3325 EnableWindow(hQualityLinesButton, FALSE);
3326 EnableWindow(hAlwaysBlackButton, FALSE);
3327 EnableWindow(hEdgeThicknessLabel, FALSE);
3328 EnableWindow(hEdgeThicknessSlider, FALSE);
3329 disableConditionals();
3330 setCheck(hGeometryPage, IDC_EDGES_ONLY, false);
3331 setCheck(hGeometryPage, IDC_CONDITIONAL_HIGHLIGHTS, false);
3332 setCheck(hGeometryPage, IDC_QUALITY_LINES, false);
3333 setCheck(hGeometryPage, IDC_ALWAYS_BLACK, false);
3334 }
3335
setupEdgeLines(void)3336 void LDViewPreferences::setupEdgeLines(void)
3337 {
3338 setupGroupCheckButton(hGeometryPage, IDC_HIGHLIGHTS,
3339 ldPrefs->getShowHighlightLines());
3340 hConditionalHighlightsButton = GetDlgItem(hGeometryPage,
3341 IDC_CONDITIONAL_HIGHLIGHTS);
3342 hShowAllConditionalButton = GetDlgItem(hGeometryPage, IDC_ALL_CONDITIONAL);
3343 hShowConditionalControlsButton = GetDlgItem(hGeometryPage,
3344 IDC_CONDITIONAL_CONTROLS);
3345 hEdgesOnlyButton = GetDlgItem(hGeometryPage, IDC_EDGES_ONLY);
3346 hQualityLinesButton = GetDlgItem(hGeometryPage, IDC_QUALITY_LINES);
3347 hAlwaysBlackButton = GetDlgItem(hGeometryPage, IDC_ALWAYS_BLACK);
3348 hEdgeThicknessLabel = GetDlgItem(hGeometryPage, IDC_EDGE_THICKNESS_LABEL);
3349 hEdgeThicknessSlider = GetDlgItem(hGeometryPage, IDC_EDGE_THICKNESS);
3350 CUIDialog::trackBarSetup(hGeometryPage, IDC_EDGE_THICKNESS, 0, 5, 1,
3351 ldPrefs->getEdgeThickness());
3352 if (ldPrefs->getShowHighlightLines())
3353 {
3354 enableEdges();
3355 }
3356 else
3357 {
3358 disableEdges();
3359 }
3360 }
3361
setupGeometryPage(void)3362 void LDViewPreferences::setupGeometryPage(void)
3363 {
3364 hGeometryPage = hwndArray->pointerAtIndex(geometryPageNumber);
3365 setCheck(hGeometryPage, IDC_PART_BOUNDING_BOXES,
3366 ldPrefs->getBoundingBoxesOnly());
3367 setupSeamWidth();
3368 setupWireframe();
3369 setupBfc();
3370 setupEdgeLines();
3371 }
3372
setupOpacitySlider(void)3373 void LDViewPreferences::setupOpacitySlider(void)
3374 {
3375 if (ldPrefs->getCutawayMode() == LDVCutawayWireframe &&
3376 !LDVExtensionsSetup::haveAlpha())
3377 {
3378 ldPrefs->setCutawayAlpha(100);
3379 EnableWindow(hCutawayOpacitySlider, FALSE);
3380 EnableWindow(hCutawayOpacityLabel, FALSE);
3381 CUIDialog::trackBarSetPos(hEffectsPage, IDC_CUTAWAY_OPACITY, 100);
3382 }
3383 else
3384 {
3385 EnableWindow(hCutawayOpacitySlider, TRUE);
3386 EnableWindow(hCutawayOpacityLabel, TRUE);
3387 }
3388 }
3389
enableCutaway(void)3390 void LDViewPreferences::enableCutaway(void)
3391 {
3392 int activeCutaway = 0;
3393
3394 EnableWindow(hCutawayColorButton, TRUE);
3395 if (LDVExtensionsSetup::haveStencil())
3396 {
3397 EnableWindow(hCutawayMonochromButton, TRUE);
3398 }
3399 else
3400 {
3401 if (ldPrefs->getCutawayMode() == LDVCutawayStencil)
3402 {
3403 ldPrefs->setCutawayMode(LDVCutawayWireframe);
3404 }
3405 EnableWindow(hCutawayMonochromButton, FALSE);
3406 }
3407 setupOpacitySlider();
3408 EnableWindow(hCutawayThicknessSlider, TRUE);
3409 EnableWindow(hCutawayThicknessLabel, TRUE);
3410 setCheck(hEffectsPage, IDC_CUTAWAY_COLOR, false);
3411 setCheck(hEffectsPage, IDC_CUTAWAY_MONOCHROME, false);
3412 switch (ldPrefs->getCutawayMode())
3413 {
3414 case LDVCutawayWireframe:
3415 activeCutaway = IDC_CUTAWAY_COLOR;
3416 break;
3417 case LDVCutawayStencil:
3418 activeCutaway = IDC_CUTAWAY_MONOCHROME;
3419 break;
3420 }
3421 setCheck(hEffectsPage, activeCutaway, true);
3422 }
3423
disableCutaway(void)3424 void LDViewPreferences::disableCutaway(void)
3425 {
3426 EnableWindow(hCutawayColorButton, FALSE);
3427 EnableWindow(hCutawayMonochromButton, FALSE);
3428 EnableWindow(hCutawayOpacityLabel, FALSE);
3429 EnableWindow(hCutawayOpacitySlider, FALSE);
3430 EnableWindow(hCutawayThicknessLabel, FALSE);
3431 EnableWindow(hCutawayThicknessSlider, FALSE);
3432 setCheck(hEffectsPage, IDC_CUTAWAY_COLOR, false);
3433 setCheck(hEffectsPage, IDC_CUTAWAY_MONOCHROME, false);
3434 }
3435
setupCutaway(void)3436 void LDViewPreferences::setupCutaway(void)
3437 {
3438 setupGroupCheckButton(hEffectsPage, IDC_CUTAWAY,
3439 ldPrefs->getCutawayMode() != LDVCutawayNormal);
3440 hCutawayColorButton = GetDlgItem(hEffectsPage, IDC_CUTAWAY_COLOR);
3441 hCutawayMonochromButton = GetDlgItem(hEffectsPage, IDC_CUTAWAY_MONOCHROME);
3442 hCutawayOpacityLabel = GetDlgItem(hEffectsPage, IDC_CUTAWAY_OPACITY_LABEL);
3443 hCutawayOpacitySlider = GetDlgItem(hEffectsPage, IDC_CUTAWAY_OPACITY);
3444 hCutawayThicknessLabel = GetDlgItem(hEffectsPage,
3445 IDC_CUTAWAY_THICKNESS_LABEL);
3446 hCutawayThicknessSlider = GetDlgItem(hEffectsPage, IDC_CUTAWAY_THICKNESS);
3447 CUIDialog::trackBarSetup(hEffectsPage, IDC_CUTAWAY_OPACITY, 1, 100, 10,
3448 ldPrefs->getCutawayAlpha());
3449 CUIDialog::trackBarSetup(hEffectsPage, IDC_CUTAWAY_THICKNESS, 0, 5, 1,
3450 ldPrefs->getCutawayThickness());
3451 if (ldPrefs->getCutawayMode() == LDVCutawayNormal)
3452 {
3453 disableCutaway();
3454 }
3455 else
3456 {
3457 enableCutaway();
3458 }
3459 }
3460
enableStereo(void)3461 void LDViewPreferences::enableStereo(void)
3462 {
3463 int activeStereo = 0;
3464
3465 EnableWindow(hHardwareStereoButton, TRUE);
3466 EnableWindow(hCrossEyedStereoButton, TRUE);
3467 EnableWindow(hParallelStereoButton, TRUE);
3468 EnableWindow(hStereoSpacingSlider, TRUE);
3469 EnableWindow(hStereoSpacingLabel, TRUE);
3470 setCheck(hEffectsPage, IDC_HARDWARE_STEREO, false);
3471 setCheck(hEffectsPage, IDC_CROSS_EYED_STEREO, false);
3472 setCheck(hEffectsPage, IDC_PARALLEL_STEREO, false);
3473 switch (ldPrefs->getStereoMode())
3474 {
3475 case LDVStereoHardware:
3476 activeStereo = IDC_HARDWARE_STEREO;
3477 break;
3478 case LDVStereoCrossEyed:
3479 activeStereo = IDC_CROSS_EYED_STEREO;
3480 break;
3481 case LDVStereoParallel:
3482 activeStereo = IDC_PARALLEL_STEREO;
3483 break;
3484 }
3485 setCheck(hEffectsPage, activeStereo, true);
3486 }
3487
disableStereo(void)3488 void LDViewPreferences::disableStereo(void)
3489 {
3490 EnableWindow(hHardwareStereoButton, FALSE);
3491 EnableWindow(hCrossEyedStereoButton, FALSE);
3492 EnableWindow(hParallelStereoButton, FALSE);
3493 EnableWindow(hStereoSpacingSlider, FALSE);
3494 EnableWindow(hStereoSpacingLabel, FALSE);
3495 setCheck(hEffectsPage, IDC_HARDWARE_STEREO, false);
3496 setCheck(hEffectsPage, IDC_CROSS_EYED_STEREO, false);
3497 setCheck(hEffectsPage, IDC_PARALLEL_STEREO, false);
3498 }
3499
setupStereo(void)3500 void LDViewPreferences::setupStereo(void)
3501 {
3502 setupGroupCheckButton(hEffectsPage, IDC_STEREO,
3503 ldPrefs->getStereoMode() != LDVStereoNone);
3504 hHardwareStereoButton = GetDlgItem(hEffectsPage, IDC_HARDWARE_STEREO);
3505 hCrossEyedStereoButton = GetDlgItem(hEffectsPage, IDC_CROSS_EYED_STEREO);
3506 hParallelStereoButton = GetDlgItem(hEffectsPage, IDC_PARALLEL_STEREO);
3507 hStereoSpacingSlider = GetDlgItem(hEffectsPage, IDC_STEREO_SPACING);
3508 hStereoSpacingLabel = GetDlgItem(hEffectsPage, IDC_STEREO_SPACING_LABEL);
3509 CUIDialog::trackBarSetup(hEffectsPage, IDC_STEREO_SPACING, 0, 100, 10,
3510 ldPrefs->getStereoEyeSpacing());
3511 if (ldPrefs->getStereoMode() == LDVStereoNone)
3512 {
3513 disableStereo();
3514 }
3515 else
3516 {
3517 enableStereo();
3518 }
3519 }
3520
uncheckLightDirections(void)3521 void LDViewPreferences::uncheckLightDirections(void)
3522 {
3523 for (IntIntMap::const_iterator it = lightDirIndexToId.begin()
3524 ; it != lightDirIndexToId.end(); it++)
3525 {
3526 checkStates[GetDlgItem(hEffectsPage, it->second)] = false;
3527 if (!CUIThemes::isThemeLibLoaded())
3528 {
3529 setCheck(hEffectsPage, it->second, false);
3530 }
3531 }
3532 }
3533
enableLighting(void)3534 void LDViewPreferences::enableLighting(void)
3535 {
3536 int lightDirButton = -1;
3537 BOOL enabled = TRUE;
3538
3539 EnableWindow(hLightQualityButton, TRUE);
3540 EnableWindow(hLightSubduedButton, TRUE);
3541 EnableWindow(hLightSpecularButton, TRUE);
3542 EnableWindow(hLightAlternateButton, TRUE);
3543 EnableWindow(hLightDrawLightDatsButton, TRUE);
3544 if (!ldPrefs->getDrawLightDats())
3545 {
3546 enabled = FALSE;
3547 }
3548 EnableWindow(hLightOptionalStandardButton, enabled);
3549 EnableWindow(GetDlgItem(hEffectsPage, IDC_LIGHT_DIR), TRUE);
3550 setCheck(hEffectsPage, IDC_LIGHTING_QUALITY, ldPrefs->getQualityLighting());
3551 setCheck(hEffectsPage, IDC_LIGHTING_SUBDUED, ldPrefs->getSubduedLighting());
3552 setCheck(hEffectsPage, IDC_SPECULAR, ldPrefs->getUseSpecular());
3553 setCheck(hEffectsPage, IDC_ALTERNATE_LIGHTING, ldPrefs->getOneLight());
3554 setCheck(hEffectsPage, IDC_DRAW_LIGHT_DATS, ldPrefs->getDrawLightDats());
3555 setCheck(hEffectsPage, IDC_OPTIONAL_STANDARD_LIGHT,
3556 ldPrefs->getOptionalStandardLight());
3557 lightDirButton = lightDirIndexToId[(int)ldPrefs->getLightDirection() - 1];
3558 uncheckLightDirections();
3559 if (lightDirButton != 0)
3560 {
3561 checkStates[GetDlgItem(hEffectsPage, lightDirButton)] = true;
3562 if (!CUIThemes::isThemeLibLoaded())
3563 {
3564 setCheck(hEffectsPage, lightDirButton, true);
3565 }
3566 }
3567 for (int i = 0; i < (int)lightAngleButtons.size(); i++)
3568 {
3569 EnableWindow(lightAngleButtons[i], TRUE);
3570 }
3571 }
3572
disableLighting(void)3573 void LDViewPreferences::disableLighting(void)
3574 {
3575 EnableWindow(hLightQualityButton, FALSE);
3576 EnableWindow(hLightSubduedButton, FALSE);
3577 EnableWindow(hLightSpecularButton, FALSE);
3578 EnableWindow(hLightAlternateButton, FALSE);
3579 EnableWindow(hLightDrawLightDatsButton, FALSE);
3580 EnableWindow(hLightOptionalStandardButton, FALSE);
3581 EnableWindow(GetDlgItem(hEffectsPage, IDC_LIGHT_DIR), FALSE);
3582 // Don't disable IDC_HIDE_LIGHT_DAT.
3583 for (int i = 0; i < (int)lightAngleButtons.size(); i++)
3584 {
3585 EnableWindow(lightAngleButtons[i], FALSE);
3586 }
3587 setCheck(hEffectsPage, IDC_LIGHTING, false);
3588 setCheck(hEffectsPage, IDC_LIGHTING_QUALITY, false);
3589 setCheck(hEffectsPage, IDC_LIGHTING_SUBDUED, false);
3590 setCheck(hEffectsPage, IDC_SPECULAR, false);
3591 setCheck(hEffectsPage, IDC_ALTERNATE_LIGHTING, false);
3592 setCheck(hEffectsPage, IDC_DRAW_LIGHT_DATS, false);
3593 setCheck(hEffectsPage, IDC_OPTIONAL_STANDARD_LIGHT, false);
3594 uncheckLightDirections();
3595 }
3596
setupLightAngleButtons(void)3597 void LDViewPreferences::setupLightAngleButtons(void)
3598 {
3599 lightAngleButtons.clear();
3600 double scaleFactor = getScaleFactor();
3601 HIMAGELIST hImageList = NULL;
3602 SIZE size;
3603 size.cx = size.cy = scalePoints(16);
3604 hImageList = ImageList_Create(size.cx, size.cy, ILC_COLOR32, 9, 0);
3605 for (IntIntMap::const_iterator it = lightDirIndexToId.begin()
3606 ; it != lightDirIndexToId.end(); it++)
3607 {
3608 HWND hButton = GetDlgItem(hEffectsPage, it->second);
3609
3610 if (hButton)
3611 {
3612 RECT buttonRect;
3613 GetWindowRect(hButton, &buttonRect);
3614 LONG buttonSize = buttonRect.bottom - buttonRect.top;
3615 screenToClient(hEffectsPage, &buttonRect);
3616 // For some reason, Windows messes up the sizes of these buttons,
3617 // making them a bunch of different widths, which looks awful,
3618 // since they are arranged in a 3x3 grid.
3619 MoveWindow(hButton, buttonRect.left, buttonRect.top,
3620 buttonSize, buttonSize, TRUE);
3621 HICON hIcon = NULL;
3622 if (scaleFactor > 1.0)
3623 {
3624 TCImage *image = TCImage::createFromResource(NULL, it->second, 4, true, scaleFactor);
3625 if (image != NULL)
3626 {
3627 int index = addImageToImageList(hImageList, image, size);
3628 UINT flags = ILD_TRANSPARENT;
3629 if (!CUIScaler::use32bit())
3630 {
3631 // Note: this doesn't work quite right, but it's close.
3632 flags = ILD_IMAGE;
3633 }
3634 hIcon = ImageList_GetIcon(hImageList, index, flags);
3635 image->release();
3636 }
3637 }
3638 if (!hIcon)
3639 {
3640 hIcon = (HICON)LoadImage(hInstance, MAKEINTRESOURCE(it->second),
3641 IMAGE_ICON, 16, 16, LR_DEFAULTCOLOR);
3642 }
3643 if (hIcon)
3644 {
3645 lightAngleButtons.push_back(hButton);
3646 HICON hOldIcon = buttonSetIcon(hButton, hIcon);
3647 if (hOldIcon != NULL)
3648 {
3649 DestroyIcon(hOldIcon);
3650 }
3651 setupIconButton(hButton);
3652 }
3653 }
3654 }
3655 ImageList_Destroy(hImageList);
3656 }
3657
setupLighting(void)3658 void LDViewPreferences::setupLighting(void)
3659 {
3660 setupGroupCheckButton(hEffectsPage, IDC_LIGHTING,
3661 ldPrefs->getUseLighting());
3662 hLightQualityButton = GetDlgItem(hEffectsPage, IDC_LIGHTING_QUALITY);
3663 hLightSubduedButton = GetDlgItem(hEffectsPage, IDC_LIGHTING_SUBDUED);
3664 hLightSpecularButton = GetDlgItem(hEffectsPage, IDC_SPECULAR);
3665 hLightAlternateButton = GetDlgItem(hEffectsPage, IDC_ALTERNATE_LIGHTING);
3666 hLightDrawLightDatsButton = GetDlgItem(hEffectsPage, IDC_DRAW_LIGHT_DATS);
3667 checkStates[hLightDrawLightDatsButton] = ldPrefs->getDrawLightDats();
3668 hLightOptionalStandardButton = GetDlgItem(hEffectsPage,
3669 IDC_OPTIONAL_STANDARD_LIGHT);
3670 setupLightAngleButtons();
3671 if (ldPrefs->getUseLighting())
3672 {
3673 enableLighting();
3674 }
3675 else
3676 {
3677 disableLighting();
3678 }
3679 setCheck(hEffectsPage, IDC_HIDE_LIGHT_DAT, ldPrefs->getNoLightGeom());
3680 }
3681
setupEffectsPage(void)3682 void LDViewPreferences::setupEffectsPage(void)
3683 {
3684 hEffectsPage = hwndArray->pointerAtIndex(effectsPageNumber);
3685 setupLighting();
3686 setupStereo();
3687 setupCutaway();
3688 setCheck(hEffectsPage, IDC_STIPPLE, ldPrefs->getUseStipple());
3689 setCheck(hEffectsPage, IDC_SORT, ldPrefs->getSortTransparent());
3690 setCheck(hEffectsPage, IDC_FLAT_SHADING, ldPrefs->getUseFlatShading());
3691 setCheck(hEffectsPage, IDC_SMOOTH_CURVES, ldPrefs->getPerformSmoothing());
3692 }
3693
sliderValueFromTextureOffset(double value)3694 int LDViewPreferences::sliderValueFromTextureOffset(double value)
3695 {
3696 return (int)(value * 10.0);
3697 }
3698
textureOffsetFromSliderValue(int value)3699 TCFloat32 LDViewPreferences::textureOffsetFromSliderValue(int value)
3700 {
3701 return (TCFloat32)(value / 10.0f);
3702 }
3703
sliderValueFromAniso(double value)3704 int LDViewPreferences::sliderValueFromAniso(double value)
3705 {
3706 return (int)(log(value) / log(2.0) + 0.5f);
3707 }
3708
anisoFromSliderValue(int value)3709 TCFloat32 LDViewPreferences::anisoFromSliderValue(int value)
3710 {
3711 return (TCFloat32)(1 << value);
3712 }
3713
setupSubstitution(void)3714 void LDViewPreferences::setupSubstitution(void)
3715 {
3716 setupGroupCheckButton(hPrimitivesPage, IDC_PRIMITIVE_SUBSTITUTION,
3717 ldPrefs->getAllowPrimitiveSubstitution());
3718 hCurveQualityLabel = GetDlgItem(hPrimitivesPage, IDC_CURVE_QUALITY_LABEL);
3719 hCurveQualitySlider = GetDlgItem(hPrimitivesPage, IDC_CURVE_QUALITY);
3720 CUIDialog::trackBarSetup(hPrimitivesPage, IDC_CURVE_QUALITY, 1, 12, 1,
3721 ldPrefs->getCurveQuality());
3722 if (ldPrefs->getAllowPrimitiveSubstitution())
3723 {
3724 enablePrimitives();
3725 }
3726 else
3727 {
3728 disablePrimitives();
3729 }
3730 }
3731
setupTextures(void)3732 void LDViewPreferences::setupTextures(void)
3733 {
3734 GLfloat maxAniso = TREGLExtensions::getMaxAnisoLevel();
3735 short numAnisoLevels = (short)sliderValueFromAniso(maxAniso);
3736 TCFloat32 anisoLevel = ldPrefs->getAnisoLevel();
3737 TCFloat32 textureOffset = ldPrefs->getTextureOffsetFactor();
3738
3739 hTextureStudsButton = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_STUDS);
3740 hTextureOffsetLabel = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_OFFSET_LABEL);
3741 hTextureOffsetSlider = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_OFFSET);
3742 hTextureNearestButton = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_NEAREST);
3743 hTextureBilinearButton = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_BILINEAR);
3744 hTextureTrilinearButton = GetDlgItem(hPrimitivesPage,
3745 IDC_TEXTURE_TRILINEAR);
3746 hTextureAnisoButton = GetDlgItem(hPrimitivesPage, IDC_TEXTURE_ANISO);
3747 hAnisoLevelSlider = GetDlgItem(hPrimitivesPage, IDC_ANISO_LEVEL);
3748 hAnisoLevelLabel = GetDlgItem(hPrimitivesPage, IDC_ANISO_LEVEL_LABEL);
3749 CUIDialog::trackBarSetup(hPrimitivesPage, IDC_TEXTURE_OFFSET, 10, 100, 10,
3750 sliderValueFromTextureOffset(textureOffset));
3751 if (anisoLevel > maxAniso)
3752 {
3753 anisoLevel = (TCFloat32)maxAniso;
3754 }
3755 setAniso(sliderValueFromAniso(anisoLevel));
3756 if (anisoLevel < 2.0f)
3757 {
3758 anisoLevel = 2.0f;
3759 }
3760 CUIDialog::trackBarSetup(hPrimitivesPage, IDC_ANISO_LEVEL, 1, numAnisoLevels, 1,
3761 sliderValueFromAniso(anisoLevel));
3762 setCheck(hPrimitivesPage, IDC_TEXMAPS, ldPrefs->getTexmaps());
3763 updateTextureFilteringEnabled();
3764 updateTexmapsEnabled();
3765 }
3766
setupPrimitivesPage(void)3767 void LDViewPreferences::setupPrimitivesPage(void)
3768 {
3769 hPrimitivesPage = hwndArray->pointerAtIndex(primitivesPageNumber);
3770 setupTextures();
3771 setupSubstitution();
3772 setCheck(hPrimitivesPage, IDC_STUD_QUALITY, !ldPrefs->getQualityStuds());
3773 setCheck(hPrimitivesPage, IDC_HI_RES, ldPrefs->getHiResPrimitives());
3774 }
3775
enableProxyServer(void)3776 void LDViewPreferences::enableProxyServer(void)
3777 {
3778 UCCHAR proxyPortString[128];
3779
3780 EnableWindow(hProxyServerLabel, TRUE);
3781 EnableWindow(hProxyServer, TRUE);
3782 EnableWindow(hProxyPortLabel, TRUE);
3783 EnableWindow(hProxyPort, TRUE);
3784 ucstring ucProxyServerString;
3785 utf8toucstring(ucProxyServerString, ldPrefs->getProxyServer());
3786 windowSetText(hProxyServer, ucProxyServerString);
3787 sucprintf(proxyPortString, COUNT_OF(proxyPortString), _UC("%d"),
3788 ldPrefs->getProxyPort());
3789 windowSetText(hProxyPort, proxyPortString);
3790 }
3791
disableProxyServer(void)3792 void LDViewPreferences::disableProxyServer(void)
3793 {
3794 EnableWindow(hProxyServerLabel, FALSE);
3795 EnableWindow(hProxyServer, FALSE);
3796 EnableWindow(hProxyPortLabel, FALSE);
3797 EnableWindow(hProxyPort, FALSE);
3798 windowSetText(hProxyServer, _UC(""));
3799 windowSetText(hProxyPort, _UC(""));
3800 }
3801
setupProxy(void)3802 void LDViewPreferences::setupProxy(void)
3803 {
3804 int activeProxyType = IDC_PROXY_NONE;
3805
3806 setCheck(hUpdatesPage, IDC_PROXY_NONE, false);
3807 setCheck(hUpdatesPage, IDC_PROXY_WINDOWS, false);
3808 setCheck(hUpdatesPage, IDC_PROXY_MANUAL, false);
3809 switch (ldPrefs->getProxyType())
3810 {
3811 case 0:
3812 activeProxyType = IDC_PROXY_NONE;
3813 disableProxyServer();
3814 break;
3815 case 1:
3816 activeProxyType = IDC_PROXY_WINDOWS;
3817 disableProxyServer();
3818 break;
3819 case 2:
3820 activeProxyType = IDC_PROXY_MANUAL;
3821 enableProxyServer();
3822 break;
3823 }
3824 setCheck(hUpdatesPage, activeProxyType, true);
3825 }
3826
enableCheckPartTracker(void)3827 void LDViewPreferences::enableCheckPartTracker(void)
3828 {
3829 UCCHAR tmpString[128];
3830
3831 EnableWindow(hMissingPartsLabel, TRUE);
3832 EnableWindow(hMissingParts, TRUE);
3833 EnableWindow(hUpdatedPartsLabel, TRUE);
3834 EnableWindow(hUpdatedParts, TRUE);
3835 sucprintf(tmpString, COUNT_OF(tmpString), _UC("%0d"),
3836 ldPrefs->getMissingPartWait());
3837 windowSetText(hMissingParts, tmpString);
3838 sucprintf(tmpString, COUNT_OF(tmpString), _UC("%0d"),
3839 ldPrefs->getUpdatedPartWait());
3840 windowSetText(hUpdatedParts, tmpString);
3841 }
3842
disableCheckPartTracker(void)3843 void LDViewPreferences::disableCheckPartTracker(void)
3844 {
3845 EnableWindow(hMissingPartsLabel, FALSE);
3846 EnableWindow(hMissingParts, FALSE);
3847 EnableWindow(hUpdatedPartsLabel, FALSE);
3848 EnableWindow(hUpdatedParts, FALSE);
3849 windowSetText(hMissingParts, _UC(""));
3850 windowSetText(hUpdatedParts, _UC(""));
3851 }
3852
setupUpdatesPage(void)3853 void LDViewPreferences::setupUpdatesPage(void)
3854 {
3855 hUpdatesPage = hwndArray->pointerAtIndex(updatesPageNumber);
3856 hProxyServerLabel = GetDlgItem(hUpdatesPage, IDC_PROXY_SERVER_LABEL);
3857 hProxyServer = GetDlgItem(hUpdatesPage, IDC_PROXY_SERVER);
3858 hProxyPortLabel = GetDlgItem(hUpdatesPage, IDC_PROXY_PORT_LABEL);
3859 hProxyPort = GetDlgItem(hUpdatesPage, IDC_PROXY_PORT);
3860 hCheckPartTracker = GetDlgItem(hUpdatesPage, IDC_CHECK_PART_TRACKER);
3861 hMissingPartsLabel = GetDlgItem(hUpdatesPage, IDC_MISSING_DAYS_LABEL);
3862 hMissingParts = GetDlgItem(hUpdatesPage, IDC_MISSING_DAYS);
3863 hUpdatedPartsLabel = GetDlgItem(hUpdatesPage, IDC_UPDATED_DAYS_LABEL);
3864 hUpdatedParts = GetDlgItem(hUpdatesPage, IDC_UPDATED_DAYS);
3865 if (ldPrefs->getCheckPartTracker())
3866 {
3867 enableCheckPartTracker();
3868 }
3869 else
3870 {
3871 disableCheckPartTracker();
3872 }
3873 setCheck(hUpdatesPage, IDC_CHECK_PART_TRACKER,
3874 ldPrefs->getCheckPartTracker());
3875 setupProxy();
3876 }
3877
selectPrefSet(const ucstring & prefSet,bool force)3878 void LDViewPreferences::selectPrefSet(const ucstring& prefSet, bool force)
3879 {
3880 if (!prefSet.empty())
3881 {
3882 listBoxSelectString(hPrefSetsList, prefSet);
3883 doPrefSetSelected(force);
3884 }
3885 else
3886 {
3887 char *savedSession =
3888 TCUserDefaults::getSavedSessionNameFromKey(PREFERENCE_SET_KEY);
3889
3890 if (savedSession && savedSession[0])
3891 {
3892 ucstring ucSavedSession;
3893 utf8toucstring(ucSavedSession, savedSession);
3894 selectPrefSet(ucSavedSession, force);
3895 }
3896 else
3897 {
3898 selectPrefSet(DEFAULT_PREF_SET, force);
3899 }
3900 delete savedSession;
3901 }
3902 }
3903
setupPrefSetsList(void)3904 void LDViewPreferences::setupPrefSetsList(void)
3905 {
3906 TCStringArray *sessionNames = TCUserDefaults::getAllSessionNames();
3907 int i;
3908 int count = sessionNames->getCount();
3909
3910 hPrefSetsList = GetDlgItem(hPrefSetsPage, IDC_PREFSETS_LIST);
3911 listBoxAddString(hPrefSetsList, DEFAULT_PREF_SET);
3912 for (i = 0; i < count; i++)
3913 {
3914 ucstring ucSessionName;
3915 utf8toucstring(ucSessionName, sessionNames->stringAtIndex(i));
3916 listBoxAddString(hPrefSetsList, ucSessionName);
3917 }
3918 selectPrefSet();
3919 sessionNames->release();
3920 }
3921
setupPrefSetsPage(void)3922 void LDViewPreferences::setupPrefSetsPage(void)
3923 {
3924 hPrefSetsPage = hwndArray->pointerAtIndex(prefSetsPageNumber);
3925 hDeletePrefSetButton = GetDlgItem(hPrefSetsPage, IDC_DELETE_PREF_SET);
3926 hNewPrefSetButton = GetDlgItem(hPrefSetsPage, IDC_NEW_PREF_SET);
3927 hPrefSetHotKeyButton = GetDlgItem(hPrefSetsPage, IDC_PREF_SET_HOT_KEY);
3928 setupPrefSetsList();
3929 }
3930
setupAntialiasing(void)3931 void LDViewPreferences::setupAntialiasing(void)
3932 {
3933 TCIntArray *fsaaModes = LDVExtensionsSetup::getFSAAModes();
3934 UCCHAR modeString[1024];
3935
3936 // Remove all items from FSAA combo box list.
3937 CUIDialog::comboResetContent(hGeneralPage, IDC_FSAA_COMBO);
3938 // Add "None" to FSAA combo box list as only item.
3939 CUIDialog::comboAddString(hGeneralPage, IDC_FSAA_COMBO, ls(_UC("FsaaNone")));
3940 // Select "None", just in case something else doesn't get selected later.
3941 CUIDialog::comboSetCurSel(hGeneralPage, IDC_FSAA_COMBO, 0);
3942 // The following array should always exist, even if it is empty, but check
3943 // just to be sure.
3944 if (fsaaModes)
3945 {
3946 int i;
3947 int count = fsaaModes->getCount();
3948
3949 // Note that fsaaModes contains a sorted array of unique FSAA factors.
3950 for (i = 0; i < count; i++)
3951 {
3952 int value = (*fsaaModes)[i];
3953
3954 sucprintf(modeString, COUNT_OF(modeString),
3955 ls(_UC("FsaaNx")), value);
3956 CUIDialog::comboAddString(hGeneralPage, IDC_FSAA_COMBO, modeString);
3957 // nVidia hardare supports Quincunx and 9-box pattern, so add an
3958 // "Enhanced" item to the list if the extension is supported and
3959 // the current factor is 2 or 4.
3960 if ((value == 2 || value == 4) &&
3961 TREGLExtensions::haveNvMultisampleFilterHintExtension())
3962 {
3963 sucprintf(modeString, COUNT_OF(modeString),
3964 ls(_UC("FsaaNx")), value);
3965 ucstrcat(modeString, _UC(" "));
3966 ucstrcat(modeString, ls(_UC("FsaaEnhanced")));
3967 CUIDialog::comboAddString(hGeneralPage, IDC_FSAA_COMBO, modeString);
3968 }
3969 }
3970 }
3971 if (ldPrefs->getFsaaMode())
3972 {
3973 sucprintf(modeString, COUNT_OF(modeString),
3974 ls(_UC("FsaaNx")), getFSAAFactor());
3975 if (getUseNvMultisampleFilter())
3976 {
3977 ucstrcat(modeString, _UC(" "));
3978 ucstrcat(modeString, ls(_UC("FsaaEnhanced")));
3979 }
3980 if (CUIDialog::comboSelectString(hGeneralPage, IDC_FSAA_COMBO, 0,
3981 modeString) == CB_ERR)
3982 {
3983 // We didn't find the selected mode, so reset to none.
3984 ldPrefs->setFsaaMode(0);
3985 }
3986 }
3987 setCheck(hGeneralPage, IDC_LINE_AA, ldPrefs->getLineSmoothing());
3988 }
3989
doApply(void)3990 bool LDViewPreferences::doApply(void)
3991 {
3992 applyChanges();
3993 checkAbandon = true;
3994 return true;
3995 }
3996
clear(void)3997 void LDViewPreferences::clear(void)
3998 {
3999 if (hBackgroundColorBitmap)
4000 {
4001 DeleteObject(hBackgroundColorBitmap);
4002 hBackgroundColorBitmap = NULL;
4003 }
4004 if (hDefaultColorBitmap)
4005 {
4006 DeleteObject(hDefaultColorBitmap);
4007 hDefaultColorBitmap = NULL;
4008 }
4009 if (hButtonColorDC)
4010 {
4011 DeleteDC(hButtonColorDC);
4012 hButtonColorDC = NULL;
4013 }
4014 hGeneralPage = NULL;
4015 hGeometryPage = NULL;
4016 hEffectsPage = NULL;
4017 hPrimitivesPage = NULL;
4018 hUpdatesPage = NULL;
4019 hPrefSetsPage = NULL;
4020 CUIPropertySheet::clear();
4021 }
4022
doNewPrefSetInit(HWND,HWND hNewPrefSetField)4023 BOOL LDViewPreferences::doNewPrefSetInit(HWND /*hDlg*/, HWND hNewPrefSetField)
4024 {
4025 SendMessage(hNewPrefSetField, EM_LIMITTEXT, 32, 0);
4026 return TRUE;
4027 }
4028
doHotKeyInit(HWND hDlg,HWND)4029 BOOL LDViewPreferences::doHotKeyInit(HWND hDlg, HWND /*hHotKeyCombo*/)
4030 {
4031 int i;
4032 ucstring prefSetName = getSelectedPrefSet();
4033
4034 if (!prefSetName.empty())
4035 {
4036 windowSetText(hDlg, prefSetName);
4037 }
4038 else
4039 {
4040 windowSetText(hDlg, _UC("???"));
4041 }
4042 CUIDialog::comboAddString(hDlg, IDC_HOTKEY_COMBO, ls(_UC("<None>")));
4043 for (i = 1; i <= 10; i++)
4044 {
4045 UCCHAR numString[5];
4046
4047 sucprintf(numString, COUNT_OF(numString), _UC("%d"), i % 10);
4048 CUIDialog::comboAddString(hDlg, IDC_HOTKEY_COMBO, numString);
4049 }
4050 CUIDialog::comboSetCurSel(hDlg, IDC_HOTKEY_COMBO, hotKeyIndex);
4051 return TRUE;
4052 }
4053
handleDpiChange(void)4054 bool LDViewPreferences::handleDpiChange(void)
4055 {
4056 if (!lightAngleButtons.empty())
4057 {
4058 setupLightAngleButtons();
4059 }
4060 if (hGeneralPage != NULL)
4061 {
4062 setupBackgroundColorButton();
4063 setupDefaultColorButton();
4064 }
4065 return true;
4066 }
4067
doDialogInit(HWND hDlg,HWND hFocusWindow,LPARAM lParam)4068 BOOL LDViewPreferences::doDialogInit(
4069 HWND hDlg,
4070 HWND hFocusWindow,
4071 LPARAM lParam)
4072 {
4073 CUIPropertySheet::doDialogInit(hDlg, hFocusWindow, lParam);
4074 HWND hNewPrefSetField = NULL;
4075 HWND hHotKeyCombo = NULL;
4076
4077 hNewPrefSetField = GetDlgItem(hDlg, IDC_NEW_PREF_SET_FIELD);
4078 if (hNewPrefSetField)
4079 {
4080 return doNewPrefSetInit(hDlg, hNewPrefSetField);
4081 }
4082 hHotKeyCombo = GetDlgItem(hDlg, IDC_HOTKEY_COMBO);
4083 if (hHotKeyCombo)
4084 {
4085 return doHotKeyInit(hDlg, hHotKeyCombo);
4086 }
4087 return TRUE;
4088 }
4089
shouldSetActive(int index)4090 bool LDViewPreferences::shouldSetActive(int index)
4091 {
4092 if (applyEnabledArray->itemAtIndex(prefSetsPageNumber) &&
4093 index != prefSetsPageNumber)
4094 {
4095 if (!setActiveWarned)
4096 {
4097 setActiveWarned = true;
4098 messageBoxUC(hWindow,
4099 ls(_UC("PrefSetApplyBeforeLeave")),
4100 ls(_UC("Error")), MB_OK | MB_ICONWARNING);
4101 }
4102 return false;
4103 }
4104 setActiveWarned = false;
4105 return true;
4106 }
4107
getFSAAFactor(void)4108 int LDViewPreferences::getFSAAFactor(void)
4109 {
4110 int fsaaMode = ldPrefs->getFsaaMode();
4111
4112 if (fsaaMode && LDVExtensionsSetup::haveMultisampleExtension())
4113 {
4114 if (fsaaMode <= 5)
4115 {
4116 return fsaaMode & 0x6; // Mask off bottom bit
4117 }
4118 else
4119 {
4120 return fsaaMode >> 3;
4121 }
4122 }
4123 else
4124 {
4125 return 0;
4126 }
4127 }
4128
getUseNvMultisampleFilter(void)4129 bool LDViewPreferences::getUseNvMultisampleFilter(void)
4130 {
4131 int fsaaMode = ldPrefs->getFsaaMode();
4132
4133 if ((fsaaMode & 0x1) &&
4134 TREGLExtensions::haveNvMultisampleFilterHintExtension())
4135 {
4136 return true;
4137 }
4138 else
4139 {
4140 return false;
4141 }
4142 }
doDrawIconPushButton(HWND hWnd,HTHEME hTheme,LPDRAWITEMSTRUCT drawItemStruct)4143 BOOL LDViewPreferences::doDrawIconPushButton(
4144 HWND hWnd, HTHEME hTheme, LPDRAWITEMSTRUCT drawItemStruct)
4145 {
4146 HDC hDrawItemDC = drawItemStruct->hDC;
4147 bool bIsPressed = (drawItemStruct->itemState & ODS_SELECTED) != 0;
4148 bool bIsFocused = (drawItemStruct->itemState & ODS_FOCUS) != 0;
4149 bool bDrawFocusRect = (drawItemStruct->itemState & ODS_NOFOCUSRECT) == 0;
4150 bool bIsDisabled = (drawItemStruct->itemState & ODS_DISABLED) != 0;
4151 bool bIsChecked = checkStates[hWnd];
4152 RECT itemRect = drawItemStruct->rcItem;
4153 HICON hIcon;
4154
4155 SetBkMode(hDrawItemDC, TRANSPARENT);
4156 // Prepare draw... paint button background
4157 if (CUIThemes::isThemeLibLoaded() && hTheme)
4158 {
4159 DWORD state;
4160
4161 if (bIsPressed)
4162 {
4163 state = PBS_PRESSED;
4164 }
4165 else if (!bIsDisabled)
4166 {
4167 if (hMouseOverButton == hWnd)
4168 {
4169 state = PBS_HOT;
4170 }
4171 else
4172 {
4173 if (bIsChecked)
4174 {
4175 state = PBS_PRESSED;
4176 }
4177 else
4178 {
4179 state = PBS_NORMAL;
4180 }
4181 }
4182 }
4183 else
4184 {
4185 state = PBS_DISABLED;
4186 }
4187 CUIThemes::drawThemeBackground(hTheme, hDrawItemDC, BP_PUSHBUTTON, state,
4188 &itemRect, NULL);
4189 }
4190 else
4191 {
4192 if (bIsFocused)
4193 {
4194 HBRUSH br = CreateSolidBrush(RGB(0,0,0));
4195 FrameRect(hDrawItemDC, &itemRect, br);
4196 InflateRect(&itemRect, -1, -1);
4197 DeleteObject(br);
4198 } // if
4199
4200 COLORREF crColor = GetSysColor(COLOR_BTNFACE);
4201
4202 HBRUSH brBackground = CreateSolidBrush(crColor);
4203
4204 FillRect(hDrawItemDC, &itemRect, brBackground);
4205
4206 DeleteObject(brBackground);
4207
4208 // Draw pressed button
4209 if (bIsPressed)
4210 {
4211 HBRUSH brBtnShadow = CreateSolidBrush(GetSysColor(COLOR_BTNSHADOW));
4212 FrameRect(hDrawItemDC, &itemRect, brBtnShadow);
4213 DeleteObject(brBtnShadow);
4214 }
4215
4216 else // ...else draw non pressed button
4217 {
4218 UINT uState = DFCS_BUTTONPUSH |
4219 ((hMouseOverButton == hWnd) ? DFCS_HOT : 0) |
4220 ((bIsPressed) ? DFCS_PUSHED : 0);
4221
4222 DrawFrameControl(hDrawItemDC, &itemRect, DFC_BUTTON, uState);
4223 } // else
4224 }
4225
4226 // Draw the focus rect
4227 if (bIsFocused && bDrawFocusRect)
4228 {
4229 RECT focusRect = itemRect;
4230
4231 InflateRect(&focusRect, -3, -3);
4232 DrawFocusRect(hDrawItemDC, &focusRect);
4233 }
4234
4235 // Draw the icon
4236 hIcon = buttonGetIcon(hWnd);
4237 if (hIcon)
4238 {
4239 ICONINFO iconInfo;
4240
4241 //if (GetBitmapDimensionEx(hBitmap, &bitmapSize))
4242 if (GetIconInfo(hIcon, &iconInfo))
4243 {
4244 SIZE iconSize;
4245 RECT clientRect;
4246 RECT contentRect;
4247 int lwidth;
4248 int lheight;
4249 BITMAPINFO bmi;
4250
4251 memset(&bmi, 0, sizeof(bmi));
4252 bmi.bmiHeader.biSize = sizeof (bmi.bmiHeader);
4253 if (GetDIBits(hDrawItemDC, iconInfo.hbmColor, 0, 0, NULL, &bmi,
4254 DIB_RGB_COLORS))
4255 {
4256 iconSize.cx = bmi.bmiHeader.biWidth;
4257 iconSize.cy = bmi.bmiHeader.biHeight;
4258 }
4259 else
4260 {
4261 iconSize.cx = 32;
4262 iconSize.cy = 32;
4263 }
4264 GetClientRect(hWnd, &clientRect);
4265 if (CUIThemes::isThemeLibLoaded() && hTheme)
4266 {
4267 CUIThemes::getThemeBackgroundContentRect(hTheme, NULL,
4268 BP_PUSHBUTTON, PBS_HOT, &clientRect, &contentRect);
4269 }
4270 else
4271 {
4272 contentRect = clientRect;
4273 }
4274 lwidth = contentRect.right - contentRect.left;
4275 lheight = contentRect.bottom - contentRect.top;
4276 if (bIsDisabled)
4277 {
4278 HBITMAP hOldBitmap;
4279 int dstX, dstY, srcX, srcY;
4280 COLORREF shadowColor;
4281 COLORREF highlightColor;
4282 HBRUSH hHighlightBrush;
4283 HBRUSH hShadowBrush;
4284 HANDLE hOldBrush;
4285 HBITMAP hInvMask = CreateBitmap(iconSize.cx, iconSize.cy, 1, 1,
4286 NULL);
4287 HDC hTempDC = CreateCompatibleDC(hDrawItemDC);
4288
4289 CUIThemes::getThemeColor(hTheme, BP_CHECKBOX,
4290 CBS_CHECKEDDISABLED, TMT_TEXTCOLOR, &shadowColor);
4291 CUIThemes::getThemeColor(hTheme, BP_PUSHBUTTON, PBS_NORMAL,
4292 TMT_EDGEHIGHLIGHTCOLOR, &highlightColor);
4293 hShadowBrush = CreateSolidBrush(shadowColor);
4294 hHighlightBrush = CreateSolidBrush(highlightColor);
4295 SelectObject(hTempDC, iconInfo.hbmMask);
4296 hOldBitmap = (HBITMAP)SelectObject(hButtonColorDC, hInvMask);
4297 BitBlt(hButtonColorDC, 0, 0, iconSize.cx, iconSize.cy, hTempDC,
4298 0, 0, NOTSRCCOPY);
4299 if (iconSize.cx > lwidth)
4300 {
4301 dstX = contentRect.left;
4302 srcX = (iconSize.cx - lwidth) / 2;
4303 }
4304 else
4305 {
4306 dstX = contentRect.left + (lwidth - iconSize.cx) / 2;
4307 lwidth = iconSize.cx;
4308 srcX = 0;
4309 }
4310 if (iconSize.cy > lheight)
4311 {
4312 dstY = contentRect.top;
4313 srcY = (iconSize.cy - lwidth) / 2;
4314 }
4315 else
4316 {
4317 dstY = contentRect.top + (lheight - iconSize.cy) / 2;
4318 lheight = iconSize.cy;
4319 srcY = 0;
4320 }
4321 hOldBrush = SelectObject(hDrawItemDC, hHighlightBrush);
4322 // The raster op we're using is somewhat voodoo magic. However,
4323 // it means DSPDxax, according to this page here:
4324 //
4325 // http://msdn.microsoft.com/library/default.asp?url=/library/en-us/gdi/pantdraw_6n77.asp
4326 //
4327 // In any event DSPDxax means:
4328 // dst XOR src AND pat XOR dst
4329 // Where pat is the current brush in the destination DC.
4330 // What that means is that everywhere that the source is white,
4331 // the destination ends up filled with its brush. Everywhere
4332 // the source is black (1-bit bitmap), the destination remains
4333 // unchanged.
4334 BitBlt(hDrawItemDC, dstX + 1, dstY + 1, lwidth, lheight, hButtonColorDC,
4335 srcX, srcY, 0x00E20746L);
4336 SelectObject(hDrawItemDC, hShadowBrush);
4337 BitBlt(hDrawItemDC, dstX, dstY, lwidth, lheight, hButtonColorDC,
4338 srcX, srcY, 0x00E20746L);
4339 SelectObject(hDrawItemDC, hOldBrush);
4340 SelectObject(hButtonColorDC, hOldBitmap);
4341 DeleteDC(hTempDC);
4342 DeleteObject(hHighlightBrush);
4343 DeleteObject(hShadowBrush);
4344 DeleteObject(hInvMask);
4345 }
4346 else
4347 {
4348 int dstX = contentRect.left + (lwidth - iconSize.cx) / 2;
4349 int dstY = contentRect.top + (lheight - iconSize.cy) / 2;
4350
4351 if (bIsChecked)
4352 {
4353 dstX++;
4354 dstY++;
4355 }
4356 DrawIconEx(hDrawItemDC, dstX, dstY, hIcon, iconSize.cx, iconSize.cy,
4357 0, NULL, DI_NORMAL);
4358 //DrawIcon(hDrawItemDC, dstX, dstY, hIcon);
4359 }
4360 }
4361 }
4362 return TRUE;
4363 }
4364
doDrawGroupCheckBox(HWND hWnd,HTHEME hTheme,LPDRAWITEMSTRUCT drawItemStruct)4365 BOOL LDViewPreferences::doDrawGroupCheckBox(HWND hWnd, HTHEME hTheme,
4366 LPDRAWITEMSTRUCT drawItemStruct)
4367 {
4368 HDC hDrawItemDC = drawItemStruct->hDC;
4369 bool bIsPressed = (drawItemStruct->itemState & ODS_SELECTED) != 0;
4370 bool bIsFocused = (drawItemStruct->itemState & ODS_FOCUS) != 0;
4371 bool bDrawFocusRect = (drawItemStruct->itemState & ODS_NOFOCUSRECT) == 0;
4372 bool bIsDisabled = (drawItemStruct->itemState & ODS_DISABLED) != 0;
4373 bool bIsChecked = checkStates[hWnd];
4374 bool bHidePrefix =
4375 (SendMessage(hWnd, WM_QUERYUISTATE, 0, 0) & UISF_HIDEACCEL) != 0;
4376 RECT itemRect = drawItemStruct->rcItem;
4377 ucstring title;
4378
4379 windowGetText(hWnd, title);
4380 SetBkMode(hDrawItemDC, TRANSPARENT);
4381 // Prepare draw... paint button background
4382 if (CUIThemes::isThemeLibLoaded() && hTheme)
4383 {
4384 DWORD state;
4385 DWORD textFlags = DT_LEFT;
4386 SIZE boxSize;
4387 RECT boxRect = itemRect;
4388 RECT textRect;
4389
4390 if (bIsPressed)
4391 {
4392 if (bIsChecked)
4393 {
4394 state = CBS_CHECKEDPRESSED;
4395 }
4396 else
4397 {
4398 state = CBS_UNCHECKEDPRESSED;
4399 }
4400 }
4401 else if (!bIsDisabled)
4402 {
4403 if (hMouseOverButton == hWnd)
4404 {
4405 if (bIsChecked)
4406 {
4407 state = CBS_CHECKEDHOT;
4408 }
4409 else
4410 {
4411 state = CBS_UNCHECKEDHOT;
4412 }
4413 }
4414 else
4415 {
4416 if (bIsChecked)
4417 {
4418 state = CBS_CHECKEDNORMAL;
4419 }
4420 else
4421 {
4422 state = CBS_UNCHECKEDNORMAL;
4423 }
4424 }
4425 }
4426 else
4427 {
4428 state = CBS_UNCHECKEDDISABLED;
4429 }
4430 if (bHidePrefix)
4431 {
4432 textFlags |= DT_HIDEPREFIX;
4433 }
4434 CUIThemes::getThemePartSize(hTheme, hDrawItemDC, BP_CHECKBOX, state, NULL,
4435 TS_TRUE, &boxSize);
4436 boxRect.right = itemRect.left + boxSize.cx;
4437 CUIThemes::drawThemeParentBackground(hWnd, hDrawItemDC, &itemRect);
4438 CUIThemes::drawThemeBackground(hTheme, hDrawItemDC, BP_CHECKBOX, state,
4439 &boxRect, NULL);
4440 CUIThemes::getThemeTextExtent(hTheme, hDrawItemDC, BP_CHECKBOX, state,
4441 title.c_str(), -1, textFlags, &itemRect, &textRect);
4442 OffsetRect(&textRect, boxSize.cx + 3, 1);
4443 // Draw the focus rect
4444 if (bIsFocused && bDrawFocusRect)
4445 {
4446 RECT focusRect = textRect;
4447
4448 InflateRect(&focusRect, 1, 1);
4449 DrawFocusRect(hDrawItemDC, &focusRect);
4450 }
4451 // All this so that we can draw the text in the font and color of the
4452 // group box text instead of the check box text. Here's where we do
4453 // that.
4454 if (bIsDisabled)
4455 {
4456 CUIThemes::drawThemeText(hTheme, hDrawItemDC, BP_CHECKBOX, CBS_DISABLED,
4457 title.c_str(), -1, textFlags, NULL, &textRect);
4458 }
4459 else
4460 {
4461 CUIThemes::drawThemeText(hTheme, hDrawItemDC, BP_GROUPBOX, GBS_NORMAL,
4462 title.c_str(), -1, textFlags, NULL, &textRect);
4463 }
4464 }
4465 return TRUE;
4466 }
4467
doDrawColorButton(HWND hDlg,HWND hWnd,HTHEME hTheme,LPDRAWITEMSTRUCT drawItemStruct)4468 BOOL LDViewPreferences::doDrawColorButton(HWND hDlg, HWND hWnd, HTHEME hTheme,
4469 LPDRAWITEMSTRUCT drawItemStruct)
4470 {
4471 HDC hDrawItemDC = drawItemStruct->hDC;
4472 bool bIsPressed = (drawItemStruct->itemState & ODS_SELECTED) != 0;
4473 bool bIsFocused = (drawItemStruct->itemState & ODS_FOCUS) != 0;
4474 bool bDrawFocusRect = (drawItemStruct->itemState & ODS_NOFOCUSRECT) == 0;
4475 RECT itemRect = drawItemStruct->rcItem;
4476 HBITMAP hBitmap;
4477
4478 SetBkMode(hDrawItemDC, TRANSPARENT);
4479 // Prepare draw... paint button background
4480 if (CUIThemes::isThemeLibLoaded() && hTheme)
4481 {
4482 DWORD state = (bIsPressed) ? PBS_PRESSED : PBS_NORMAL;
4483
4484 if (state == PBS_NORMAL)
4485 {
4486 if (bIsFocused)
4487 {
4488 state = PBS_DEFAULTED;
4489 }
4490 if (hMouseOverButton == hWnd)
4491 {
4492 state = PBS_HOT;
4493 }
4494 }
4495 CUIThemes::drawThemeBackground(hTheme, hDrawItemDC, BP_PUSHBUTTON, state,
4496 &itemRect, NULL);
4497 }
4498 else
4499 {
4500 if (bIsFocused)
4501 {
4502 HBRUSH br = CreateSolidBrush(RGB(0,0,0));
4503 FrameRect(hDrawItemDC, &itemRect, br);
4504 InflateRect(&itemRect, -1, -1);
4505 DeleteObject(br);
4506 } // if
4507
4508 COLORREF crColor = GetSysColor(COLOR_BTNFACE);
4509
4510 HBRUSH brBackground = CreateSolidBrush(crColor);
4511
4512 FillRect(hDrawItemDC, &itemRect, brBackground);
4513
4514 DeleteObject(brBackground);
4515
4516 // Draw pressed button
4517 if (bIsPressed)
4518 {
4519 HBRUSH brBtnShadow = CreateSolidBrush(GetSysColor(COLOR_BTNSHADOW));
4520 FrameRect(hDrawItemDC, &itemRect, brBtnShadow);
4521 DeleteObject(brBtnShadow);
4522 }
4523
4524 else // ...else draw non pressed button
4525 {
4526 UINT uState = DFCS_BUTTONPUSH |
4527 ((hMouseOverButton == hWnd) ? DFCS_HOT : 0) |
4528 ((bIsPressed) ? DFCS_PUSHED : 0);
4529
4530 DrawFrameControl(hDrawItemDC, &itemRect, DFC_BUTTON, uState);
4531 } // else
4532 }
4533
4534 // Draw the focus rect
4535 if (bIsFocused && bDrawFocusRect)
4536 {
4537 RECT focusRect = itemRect;
4538
4539 InflateRect(&focusRect, -3, -3);
4540 DrawFocusRect(hDrawItemDC, &focusRect);
4541 }
4542
4543 // Draw the bitmap
4544 hBitmap = CUIDialog::buttonGetBitmap(hDlg, drawItemStruct->CtlID);
4545 if (hBitmap)
4546 {
4547 SIZE bitmapSize;
4548
4549 if (GetBitmapDimensionEx(hBitmap, &bitmapSize))
4550 {
4551 HBITMAP hOldBitmap = (HBITMAP)SelectObject(hButtonColorDC,
4552 hBitmap);
4553 RECT clientRect;
4554 RECT contentRect;
4555 int lwidth;
4556 int lheight;
4557
4558 GetClientRect(hWnd, &clientRect);
4559 if (CUIThemes::isThemeLibLoaded() && hTheme)
4560 {
4561 CUIThemes::getThemeBackgroundContentRect(hTheme, NULL,
4562 BP_PUSHBUTTON, PBS_HOT, &clientRect, &contentRect);
4563 }
4564 else
4565 {
4566 contentRect = clientRect;
4567 }
4568 lwidth = contentRect.right - contentRect.left;
4569 lheight = contentRect.bottom - contentRect.top;
4570 BitBlt(hDrawItemDC, contentRect.left + (lwidth - bitmapSize.cx) / 2,
4571 contentRect.top + (lheight - bitmapSize.cy) / 2, bitmapSize.cx,
4572 bitmapSize.cy, hButtonColorDC, 0, 0, SRCCOPY);
4573 SelectObject(hButtonColorDC, hOldBitmap);
4574 }
4575 }
4576 return TRUE;
4577 }
4578
doDrawItem(HWND hDlg,int itemId,LPDRAWITEMSTRUCT drawItemStruct)4579 BOOL LDViewPreferences::doDrawItem(HWND hDlg, int itemId,
4580 LPDRAWITEMSTRUCT drawItemStruct)
4581 {
4582 HWND hWnd = GetDlgItem(hDlg, itemId);
4583
4584 if (itemId == IDC_DEFAULT_COLOR || itemId == IDC_BACKGROUND_COLOR)
4585 {
4586 return doDrawColorButton(hDlg, hWnd, hButtonTheme, drawItemStruct);
4587 }
4588 else
4589 {
4590 switch (itemId)
4591 {
4592 case IDC_WIREFRAME:
4593 case IDC_BFC:
4594 case IDC_HIGHLIGHTS:
4595 case IDC_LIGHTING:
4596 case IDC_STEREO:
4597 case IDC_CUTAWAY:
4598 case IDC_PRIMITIVE_SUBSTITUTION:
4599 return doDrawGroupCheckBox(hWnd, hButtonTheme, drawItemStruct);
4600 break;
4601 default:
4602 return doDrawIconPushButton(hWnd, hButtonTheme, drawItemStruct);
4603 break;
4604 }
4605 }
4606 return FALSE;
4607 }
4608
dialogProc(HWND hDlg,UINT message,WPARAM wParam,LPARAM lParam)4609 INT_PTR LDViewPreferences::dialogProc(
4610 HWND hDlg,
4611 UINT message,
4612 WPARAM wParam,
4613 LPARAM lParam)
4614 {
4615 switch (message)
4616 {
4617 case WM_MOUSEMOVE:
4618 if (CUIThemes::isThemeLibLoaded())
4619 {
4620 if (hMouseOverButton)
4621 {
4622 InvalidateRect(hMouseOverButton, NULL, TRUE);
4623 hMouseOverButton = NULL;
4624 }
4625 }
4626 break;
4627 case WM_DRAWITEM:
4628 return doDrawItem(hDlg, (int)wParam, (LPDRAWITEMSTRUCT)lParam);
4629 break;
4630 }
4631 return CUIPropertySheet::dialogProc(hDlg, message, wParam, lParam);
4632 }
4633
getMinFov(void)4634 TCFloat LDViewPreferences::getMinFov(void)
4635 {
4636 return 0.1f;
4637 }
4638
getMaxFov(void)4639 TCFloat LDViewPreferences::getMaxFov(void)
4640 {
4641 return 90.0f;
4642 }
4643
checkLightVector(void)4644 void LDViewPreferences::checkLightVector(void)
4645 {
4646 if (hEffectsPage)
4647 {
4648 LDPreferences::LightDirection selectedDirection =
4649 getSelectedLightDirection();
4650 LDPreferences::LightDirection lightDirection =
4651 ldPrefs->getLightDirection();
4652
4653 if (selectedDirection != lightDirection)
4654 {
4655 int lightDirButton =
4656 lightDirIndexToId[(int)lightDirection - 1];
4657
4658 uncheckLightDirections();
4659 if ((int)selectedDirection > 0)
4660 {
4661 InvalidateRect(lightAngleButtons[(int)selectedDirection - 1], NULL,
4662 TRUE);
4663 }
4664 if (lightDirButton != 0)
4665 {
4666 checkStates[GetDlgItem(hEffectsPage, lightDirButton)] = true;
4667 InvalidateRect(lightAngleButtons[(int)lightDirection - 1], NULL,
4668 TRUE);
4669 }
4670 }
4671 }
4672 }
4673