From 50ffaff1de1b05f1bf76dd842e734eff2974afd4 Mon Sep 17 00:00:00 2001 From: H.G. Muller Date: Thu, 29 Nov 2012 21:56:02 +0100 Subject: [PATCH] Add Themes dialog (WB) This dialog, done by the generic popup, contains controls for many settings that so far could only be controlled by options. It also introduces the concept of 'themes', sets of options stored in the multi-line option -themeNames. Add some dummy routines to suppress compile errors in functions that cannot be called yet in XBoard. --- args.h | 18 +++++++++- backend.c | 56 +++++++++++++++++++++++++++++++ backend.h | 1 + common.h | 1 + dialogs.c | 10 ++++++ frontend.h | 2 + winboard/resource.h | 1 + winboard/winboard.c | 27 +++++++++++++++ winboard/winboard.h | 1 + winboard/winboard.rc | 3 +- winboard/wsettings.c | 89 +++++++++++++++++++++++++++++++++++++++++++++++++- 11 files changed, 205 insertions(+), 4 deletions(-) diff --git a/args.h b/args.h index 0979148..acfb8f7 100644 --- a/args.h +++ b/args.h @@ -107,6 +107,7 @@ char *homeDir; char *firstEngineLine; char *secondEngineLine; char *icsNick; +char *theme; void EnsureOnScreen(int *x, int *y, int minX, int minY); char StringGet(void *getClosure); @@ -195,6 +196,7 @@ ArgDescriptor argDescriptors[] = { { "secondDirectory", ArgFilename, (void *) &appData.secondDirectory, FALSE, (ArgIniType) SECOND_DIRECTORY }, { "sd", ArgFilename, (void *) &appData.secondDirectory, FALSE, INVALID }, { "variations", ArgBoolean, (void *) &appData.variations, TRUE, (ArgIniType) FALSE }, + { "theme", ArgString, (void *) &theme, FALSE, (ArgIniType) "" }, /* some options only used by the XBoard front end, and ignored in WinBoard */ /* Their saving is controlled by XBOARD, which in WinBoard is defined as FALSE */ @@ -498,6 +500,7 @@ ArgDescriptor argDescriptors[] = { TRUE, (ArgIniType) FCP_NAMES }, { "secondChessProgramNames", ArgString, (void *) &secondChessProgramNames, !XBOARD, (ArgIniType) SCP_NAMES }, + { "themeNames", ArgString, (void *) &appData.themeNames, !XBOARD, (ArgIniType) "native -upf false -ub false -ubt false -pid \"\"\n" }, { "initialMode", ArgString, (void *) &appData.initialMode, FALSE, (ArgIniType) "" }, { "mode", ArgString, (void *) &appData.initialMode, FALSE, INVALID }, { "variant", ArgString, (void *) &appData.variant, FALSE, (ArgIniType) "normal" }, @@ -513,16 +516,24 @@ ArgDescriptor argDescriptors[] = { { "secondScoreAbs", ArgBoolean, (void *) &appData.secondScoreIsAbsolute, FALSE, (ArgIniType) FALSE }, { "pgnExtendedInfo", ArgBoolean, (void *) &appData.saveExtendedInfoInPGN, TRUE, (ArgIniType) FALSE }, { "hideThinkingFromHuman", ArgBoolean, (void *) &appData.hideThinkingFromHuman, TRUE, (ArgIniType) FALSE }, - { "liteBackTextureFile", ArgString, (void *) &appData.liteBackTextureFile, TRUE, (ArgIniType) "" }, - { "darkBackTextureFile", ArgString, (void *) &appData.darkBackTextureFile, TRUE, (ArgIniType) "" }, + { "liteBackTextureFile", ArgFilename, (void *) &appData.liteBackTextureFile, TRUE, (ArgIniType) "" }, + { "lbtf", ArgFilename, (void *) &appData.liteBackTextureFile, FALSE, INVALID }, + { "darkBackTextureFile", ArgFilename, (void *) &appData.darkBackTextureFile, TRUE, (ArgIniType) "" }, + { "dbtf", ArgFilename, (void *) &appData.darkBackTextureFile, FALSE, INVALID }, { "liteBackTextureMode", ArgInt, (void *) &appData.liteBackTextureMode, TRUE, (ArgIniType) BACK_TEXTURE_MODE_PLAIN }, + { "lbtm", ArgInt, (void *) &appData.liteBackTextureMode, FALSE, INVALID }, { "darkBackTextureMode", ArgInt, (void *) &appData.darkBackTextureMode, TRUE, (ArgIniType) BACK_TEXTURE_MODE_PLAIN }, + { "dbtm", ArgInt, (void *) &appData.darkBackTextureMode, FALSE, INVALID }, { "renderPiecesWithFont", ArgString, (void *) &appData.renderPiecesWithFont, TRUE, (ArgIniType) "" }, + { "pf", ArgString, (void *) &appData.renderPiecesWithFont, FALSE, INVALID }, { "fontPieceToCharTable", ArgString, (void *) &appData.fontToPieceTable, TRUE, (ArgIniType) "" }, + { "fptc", ArgString, (void *) &appData.fontToPieceTable, FALSE, INVALID }, { "fontPieceBackColorWhite", ArgColor, (void *) 8, TRUE, (ArgIniType) WHITE_PIECE_COLOR }, { "fontPieceForeColorWhite", ArgColor, (void *) 9, TRUE, (ArgIniType) WHITE_PIECE_COLOR }, { "fontPieceBackColorBlack", ArgColor, (void *) 10, TRUE, (ArgIniType) BLACK_PIECE_COLOR }, { "fontPieceForeColorBlack", ArgColor, (void *) 11, TRUE, (ArgIniType) BLACK_PIECE_COLOR }, + { "fpfcw", ArgColor, (void *) 9, FALSE, INVALID }, + { "fpbcb", ArgColor, (void *) 10, FALSE, INVALID }, { "fontPieceSize", ArgInt, (void *) &appData.fontPieceSize, TRUE, (ArgIniType) 80 }, { "overrideLineGap", ArgInt, (void *) &appData.overrideLineGap, TRUE, (ArgIniType) 1 }, { "adjudicateLossThreshold", ArgInt, (void *) &appData.adjudicateLossThreshold, TRUE, (ArgIniType) 0 }, @@ -574,8 +585,11 @@ ArgDescriptor argDescriptors[] = { { "language", ArgFilename, (void *) &appData.language, TRUE, (ArgIniType) "" }, { "userFileDirectory", ArgFilename, (void *) &homeDir, FALSE, (ArgIniType) installDir }, { "usePieceFont", ArgBoolean, (void *) &appData.useFont, TRUE, (ArgIniType) FALSE }, + { "upf", ArgBoolean, (void *) &appData.useFont, FALSE, INVALID }, { "useBoardTexture", ArgBoolean, (void *) &appData.useBitmaps, TRUE, (ArgIniType) FALSE }, + { "ubt", ArgBoolean, (void *) &appData.useBitmaps, FALSE, INVALID }, { "useBorder", ArgBoolean, (void *) &appData.useBorder, TRUE, (ArgIniType) FALSE }, + { "ub", ArgBoolean, (void *) &appData.useBorder, FALSE, INVALID }, { "border", ArgFilename, (void *) &appData.border, TRUE, (ArgIniType) "" }, // [HGM] tournament options diff --git a/backend.c b/backend.c index 1113781..71923d7 100644 --- a/backend.c +++ b/backend.c @@ -17483,3 +17483,59 @@ LoadVariation (int index, char *text) ToNrEvent(currentMove+1); } +void +LoadTheme () +{ + char *p, *q, buf[MSG_SIZ]; + if(engineLine && engineLine[0]) { // a theme was selected from the listbox + snprintf(buf, MSG_SIZ, "-theme %s", engineLine); + ParseArgsFromString(buf); + ActivateTheme(TRUE); // also redo colors + return; + } + p = nickName; + if(*p && !strchr(p, '"')) // theme name specified and well-formed; add settings to theme list + { + int len; + q = appData.themeNames; + snprintf(buf, MSG_SIZ, "\"%s\"", nickName); + if(appData.useBitmaps) { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -ubt true -lbtf \"%s\" -dbtf \"%s\" -lbtm %d -dbtm %d", + appData.liteBackTextureFile, appData.darkBackTextureFile, + appData.liteBackTextureMode, + appData.darkBackTextureMode ); + } else { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -ubt false -lsc %s -dsc %s", + Col2Text(2), // lightSquareColor + Col2Text(3) ); // darkSquareColor + } + if(appData.useBorder) { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -ub true -border \"%s\"", + appData.border); + } else { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -ub false"); + } + if(appData.useFont) { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -upf true -pf \"%s\" -fptc \"%s\" -fpfcw %s -fpbcb %s", + appData.renderPiecesWithFont, + appData.fontToPieceTable, + Col2Text(9), // appData.fontBackColorWhite + Col2Text(10) ); // appData.fontForeColorBlack + } else { + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -upf false -pid \"%s\"", + appData.pieceDirectory); + if(!appData.pieceDirectory[0]) + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -wpc %s -bpc %s", + Col2Text(0), // whitePieceColor + Col2Text(1) ); // blackPieceColor + } + snprintf(buf+strlen(buf), MSG_SIZ-strlen(buf), " -hsc %s -phc %s\n", + Col2Text(4), // highlightSquareColor + Col2Text(5) ); // premoveHighlightColor + appData.themeNames = malloc(len = strlen(q) + strlen(buf) + 1); + if(insert != q) insert[-1] = NULLCHAR; + snprintf(appData.themeNames, len, "%s\n%s%s", q, buf, insert); + if(q) free(q); + } + ActivateTheme(FALSE); +} diff --git a/backend.h b/backend.h index fae8ee7..c678e26 100644 --- a/backend.h +++ b/backend.h @@ -436,6 +436,7 @@ void Load P((ChessProgramState *cps, int n)); int MultiPV P((ChessProgramState *cps)); void MoveHistorySet P(( char movelist[][2*MOVE_LEN], int first, int last, int current, ChessProgramStats_Move * pvInfo )); void MakeEngineOutputTitle P((void)); +void LoadTheme P((void)); /* A point in time */ typedef struct { diff --git a/common.h b/common.h index 7fc9d20..0a6a163 100644 --- a/common.h +++ b/common.h @@ -423,6 +423,7 @@ typedef struct { Boolean firstPlaysBlack; Boolean noChessProgram; char *host[ENGINES]; + char *themeNames; char *pieceDirectory; char *border; char *soundDirectory; diff --git a/dialogs.c b/dialogs.c index 690eb2a..d7ab360 100644 --- a/dialogs.c +++ b/dialogs.c @@ -2577,4 +2577,14 @@ FileNamePopUp (char *label, char *def, char *filter, FileProc proc, char *openMo #endif } +void +ActivateTheme (int col) +{ +} + +char * +Col2Text (int n) +{ + return NULL; +} diff --git a/frontend.h b/frontend.h index 949bb18..64cd79f 100644 --- a/frontend.h +++ b/frontend.h @@ -233,6 +233,8 @@ void EvalGraphPopUp P((void)); Boolean EvalGraphIsUp P((void)); int EvalGraphDialogExists P((void)); void SlavePopUp P((void)); +void ActivateTheme P((int new)); +char *Col2Text P((int n)); /* these are in xhistory.c */ Boolean MoveHistoryIsUp P((void)); diff --git a/winboard/resource.h b/winboard/resource.h index c6a1a7f..e571c68 100644 --- a/winboard/resource.h +++ b/winboard/resource.h @@ -110,6 +110,7 @@ #define DLG_NewGameFRC 457 #define DLG_GameListOptions 458 #define DLG_MoveHistory 459 +#define IDM_ThemeOptions 460 #define DLG_EvalGraph 461 #define DLG_EngineOutput 463 #define DLG_EnginePlayOptions 464 diff --git a/winboard/winboard.c b/winboard/winboard.c index e6dec36..1651947 100644 --- a/winboard/winboard.c +++ b/winboard/winboard.c @@ -1030,6 +1030,7 @@ InitTextures() backTextureSquareSize = 0; // kludge to force recalculation of texturemode if( appData.liteBackTextureFile && appData.liteBackTextureFile[0] != NULLCHAR && appData.liteBackTextureFile[0] != '*' ) { + if(liteBackTexture) DeleteObject(liteBackTexture); liteBackTexture = LoadImage( 0, appData.liteBackTextureFile, IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE ); liteBackTextureMode = appData.liteBackTextureMode; @@ -1039,6 +1040,7 @@ InitTextures() } if( appData.darkBackTextureFile && appData.darkBackTextureFile[0] != NULLCHAR && appData.darkBackTextureFile[0] != '*' ) { + if(darkBackTexture) DeleteObject(darkBackTexture); darkBackTexture = LoadImage( 0, appData.darkBackTextureFile, IMAGE_BITMAP, 0, 0, LR_LOADFROMFILE ); darkBackTextureMode = appData.darkBackTextureMode; @@ -5203,6 +5205,10 @@ WndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam) BoardOptionsPopup(hwnd); break; + case IDM_ThemeOptions: + ThemeOptionsPopup(hwnd); + break; + case IDM_EnginePlayOptions: EnginePlayOptionsPopup(hwnd); break; @@ -9999,3 +10005,24 @@ int flock(int fid, int code) } return 0; } + +char * +Col2Text (int n) +{ + static int i=0; + static char col[8][20]; + COLORREF color = *(COLORREF *) colorVariable[n]; + i = i+1 & 7; + snprintf(col[i], 20, "#%02lx%02lx%02lx", color&0xff, (color>>8)&0xff, (color>>16)&0xff); + return col[i]; +} + +void +ActivateTheme (int new) +{ // Redo initialization of features depending on options that can occur in themes + InitTextures(); + if(new) InitDrawingColors(); + fontBitmapSquareSize = 0; // request creation of new font pieces + InitDrawingSizes(-2, 0); + InvalidateRect(hwndMain, NULL, TRUE); +} diff --git a/winboard/winboard.h b/winboard/winboard.h index fe03547..f3b1439 100644 --- a/winboard/winboard.h +++ b/winboard/winboard.h @@ -139,6 +139,7 @@ VOID TourneyPopup(); VOID LoadEnginePopUp(); VOID LoadOptionsPopup(HWND hDlg); VOID InitTextures(); +void ThemeOptionsPopup(HWND hwnd); /* Constants */ diff --git a/winboard/winboard.rc b/winboard/winboard.rc index d0752c8..1457af1 100644 --- a/winboard/winboard.rc +++ b/winboard/winboard.rc @@ -1211,7 +1211,8 @@ BEGIN MENUITEM "&Comments", IDM_Comment MENUITEM SEPARATOR MENUITEM "&Game List Tags...", IDM_GameListOptions - MENUITEM "&Board...", IDM_BoardOptions + MENUITEM "Colo&rs...", IDM_BoardOptions + MENUITEM "&Board Themes...", IDM_ThemeOptions MENUITEM "&Fonts...", IDM_Fonts END POPUP "&Mode" diff --git a/winboard/wsettings.c b/winboard/wsettings.c index 53d6b16..269837b 100644 --- a/winboard/wsettings.c +++ b/winboard/wsettings.c @@ -473,7 +473,8 @@ LRESULT CALLBACK SettingsProc(HWND hDlg, UINT message, WPARAM wParam, LPARAM lPa char filter[] = "All files\0*.*\0Game files\0*.pgn;*.gam\0Position files\0*.fen;*.epd;*.pos\0" "EXE files\0*.exe\0Tournament files (*.trn)\0*.trn\0" - "BIN Files\0*.bin\0LOG Files\0*.log\0INI Files\0*.ini\0\0"; + "BIN Files\0*.bin\0LOG Files\0*.log\0INI Files\0*.ini\0" + "Image files\0*.bmp\0\0"; OPENFILENAME ofn; safeStrCpy( buf, "" , sizeof( buf)/sizeof( buf[0]) ); @@ -757,6 +758,92 @@ void LoadEnginePopUp(HWND hwnd, int nr) GenericPopup(hwnd, installOptions); } +int PickTheme P((HWND hDlg)); +void DeleteTheme P((HWND hDlg)); + +int ThemeOK() +{ + if(selected >= 0) { ASSIGN(engineLine, engineList[selected]); } + if(engineLine[0] == '#') { DisplayError(_("Select single theme from the group"), 0); return 0; } + LoadTheme(); + return 1; +} + +Option themeOptions[] = { + { 195, 14, 0, NULL, (void*) &PickTheme, (char*) &selected, engineMnemonic, ListBox, N_("Select theme from list:") }, + { 0, 0, 0, NULL, NULL, NULL, NULL, Label, N_("or specify new theme below:") }, + { 0, 0, 0, NULL, (void*) &nickName, NULL, NULL, TextBox, N_("Theme name:") }, + { 0, 0, 0, NULL, (void*) &appData.useBitmaps, NULL, NULL, CheckBox, N_("Use board textures") }, + { 0, 0, 32+0, NULL, (void*) &appData.liteBackTextureFile, NULL, NULL, FileName, N_("Light-square texture:") }, + { 0, 0, 32+0, NULL, (void*) &appData.darkBackTextureFile, NULL, NULL, FileName, N_("Dark-square texture:") }, + { 0, 0, 3, NULL, (void*) &appData.darkBackTextureMode, "", NULL, Spin, N_("Dark reorientation mode:") }, + { 0, 0, 3, NULL, (void*) &appData.liteBackTextureMode, "", NULL, Spin, N_("Light reorientation mode:") }, + { 0, 0, 0, NULL, (void*) &appData.useBorder, NULL, NULL, CheckBox, N_("Draw border around board") }, + { 0, 0, 32+0, NULL, (void*) &appData.border, NULL, NULL, FileName, N_("Optional border bitmap:") }, + { 0, 0, 0, NULL, NULL, NULL, NULL, Label, N_(" Beware: a specified piece font will prevail over piece bitmaps") }, + { 0, 0, 0, NULL, (void*) &appData.bitmapDirectory, NULL, NULL, PathName, N_("Directory with piece bitmaps:") }, + { 0, 0, 0, NULL, (void*) &appData.useFont, NULL, NULL, CheckBox, N_("Use piece font") }, + { 0, 50, 150, NULL, (void*) &appData.fontPieceSize, "", NULL, Spin, N_("Font size (%):") }, + { 0, 0, 0, NULL, (void*) &appData.renderPiecesWithFont, NULL, NULL, TextBox, N_("Font name:") }, + { 0, 0, 0, NULL, (void*) &appData.fontToPieceTable, NULL, NULL, TextBox, N_("Font piece to char:") }, +// { 0, 0, 0, NULL, (void*) &DeleteTheme, NULL, NULL, Button, N_("Up") }, +// { 0, 0, 0, NULL, (void*) &DeleteTheme, NULL, NULL, Button, N_("Down") }, + { 0, 0, 0, NULL, (void*) &DeleteTheme, NULL, NULL, Button, N_("Delete Theme") }, + { 0, 1, 0, NULL, (void*) &ThemeOK, "", NULL, EndMark , "" } +}; + +void +DeleteTheme (HWND hDlg) +{ + char *p, *q; + int i, selected = SendDlgItemMessage(hDlg, 2001+2*1, LB_GETCURSEL, 0, 0); + HANDLE hwndCombo = GetDlgItem(hDlg, 2001+2*1); + if(selected < 0) return; + if(p = strstr(appData.themeNames, engineList[selected])) { + if(q = strchr(p, '\n')) strcpy(p, q+1); + } + themeOptions[0].max = NamesToList(appData.themeNames, engineList, engineMnemonic, ""); // replace list by only the group contents + SendMessage(hwndCombo, LB_RESETCONTENT, 0, 0); + SendMessage(hwndCombo, LB_ADDSTRING, 0, (LPARAM) ""); + for(i=1; i