#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Shell.h>
+#include <X11/Xatom.h>
#include <X11/Xaw/Dialog.h>
#include <X11/Xaw/Form.h>
#include <X11/Xaw/List.h>
extern void SendToProgram P((char *message, ChessProgramState *cps));
FILE * XsraSelFile P((Widget w, char *prompt, char *ok, char *cancel, char *failed,
- char *init_path, char *mode, int (*show_entry)(), char **name_return));
+ char *init_path, char *filter, char *mode, int (*show_entry)(), char **name_return));
extern Widget formWidget, shellWidget, boardWidget, menuBarWidget;
extern Display *xDisplay;
static Option *currentOption;
extern Widget shells[];
+void CheckCallback(Widget ww, XtPointer data, XEvent *event, Boolean *b)
+{
+ Widget w = currentOption[(int)(intptr_t)data].handle;
+ Boolean s;
+ Arg args[16];
+
+ XtSetArg(args[0], XtNstate, &s);
+ XtGetValues(w, args, 1);
+ XtSetArg(args[0], XtNstate, !s);
+ XtSetValues(w, args, 1);
+}
+
void SpinCallback(w, client_data, call_data)
Widget w;
XtPointer client_data, call_data;
XtGetValues(currentOption[data].handle, args, 1);
sscanf(val, "%d", &j);
if (strcmp(name, "browse") == 0) {
- if(XsraSelFile(shells[0], currentOption[data].name, NULL, NULL, "", "",
+ char *q, *r;
+ XtSetArg(args[0], XtNstring, &q);
+ XtGetValues(currentOption[data].handle, args, 1);
+ for(r = ""; *q; q++) if(*q == '.') r = q; else if(*q == '/') r = ""; // last dot after last slash
+ if(XsraSelFile(shells[0], currentOption[data].name, NULL, NULL, "", "", r,
currentOption[data].type == PathName ? "p" : "f", NULL, &p)) {
int len = strlen(p);
if(len && p[len-1] == '/') p[len-1] = NULLCHAR;
snprintf(buf, MSG_SIZ, "%d", j);
XtSetArg(args[0], XtNstring, buf);
XtSetValues(currentOption[data].handle, args, 1);
+ SetFocus(currentOption[data].handle, shells[0], NULL, False);
}
void ComboSelect(w, addr, index) // callback for all combo items
typedef void ButtonCallback(int n);
+extern WindowPlacement wpComment, wpTags;
char *trialSound;
static int oldCores, oldPonder;
int MakeColors P((void));
Widget shells[10];
Widget marked[10];
Boolean shellUp[10];
-WindowPlacement *wp[10];
+WindowPlacement *wp[10] = { NULL, &wpComment, &wpTags };
Option *dialogOptions[10];
void MarkMenu(char *item, int dlgNr)
XtSetValues(box, args, 1);
}
-void AdjustColor(int i)
+void SetColorText(int n, char *buf)
+{
+ Arg args[5];
+ XtSetArg(args[0], XtNstring, buf);
+ XtSetValues(currentOption[n-1].handle, args, 1);
+ SetFocus(currentOption[n-1].handle, shells[0], NULL, False);
+ SetColor(buf, currentOption[n].handle);
+}
+
+void DefColor(int n)
{
- int n = currentOption[i].value, col, j, r, g, b, step = 10;
+ SetColorText(n, (char*) currentOption[n].choice);
+}
+
+void RefreshColor(int source, int n)
+{
+ int col, j, r, g, b, step = 10;
char *s, buf[MSG_SIZ]; // color string
Arg args[5];
XtSetArg(args[0], XtNstring, &s);
- XtGetValues(currentOption[i-n-1].handle, args, 1);
+ XtGetValues(currentOption[source].handle, args, 1);
if(sscanf(s, "#%x", &col) != 1) return; // malformed
b = col & 0xFF; g = col & 0xFF00; r = col & 0xFF0000;
switch(n) {
- case 1: g -= 0x100*step; b -= step; break;
- case 2: r -= 0x10000*step; b -= step; break;
- case 3: g -= 0x100*step; r -= 0x10000*step; break;
- case 4: r += 0x10000*step; g += 0x100*step; b += step; break;
+ case 1: r += 0x10000*step;break;
+ case 2: g += 0x100*step; break;
+ case 3: b += step; break;
+ case 4: r -= 0x10000*step; g -= 0x100*step; b -= step; break;
}
if(r < 0) r = 0; if(g < 0) g = 0; if(b < 0) b = 0;
if(r > 0xFF0000) r = 0xFF0000; if(g > 0xFF00) g = 0xFF00; if(b > 0xFF) b = 0xFF;
col = r | g | b;
snprintf(buf, MSG_SIZ, "#%06x", col);
for(j=1; j<7; j++) if(buf[j] >= 'a') buf[j] -= 32; // capitalize
- SetColor(buf, currentOption[i-n].handle);
- XtSetArg(args[0], XtNstring, buf);
- XtSetValues(currentOption[i-n-1].handle, args, 1);
+ SetColorText(source+1, buf);
+}
+
+void ColorChanged(Widget w, XtPointer data, XEvent *event, Boolean *b)
+{
+ char buf[10];
+ if ( (XLookupString(&(event->xkey), buf, 2, NULL, NULL) == 1) && *buf == '\r' )
+ RefreshColor((int)(intptr_t) data, 0);
+}
+
+void AdjustColor(int i)
+{
+ int n = currentOption[i].value;
+ RefreshColor(i-n-1, n);
}
void BoardOptionsOK(int n)
{
- if(appData.overrideLineGap >= 0) lineGap = appData.overrideLineGap;
+ extern int defaultLineGap;
+ if(appData.overrideLineGap >= 0) lineGap = appData.overrideLineGap; else lineGap = defaultLineGap;
MakeColors(); CreateGCs(True);
CreateXPMPieces();
CreateXPMBoard(appData.liteBackTextureFile, 1);
Option boardOptions[] = {
{ 0, 0, 70, NULL, (void*) &appData.whitePieceColor, "", NULL, TextBox, _("White Piece Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#FFFFCC", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
{ 0, 0, 70, NULL, (void*) &appData.blackPieceColor, "", NULL, TextBox, _("Black Piece Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#202020", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
{ 0, 0, 70, NULL, (void*) &appData.lightSquareColor, "", NULL, TextBox, _("Light Square Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#C8C365", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
{ 0, 0, 70, NULL, (void*) &appData.darkSquareColor, "", NULL, TextBox, _("Dark Square Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#77A26D", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
{ 0, 0, 70, NULL, (void*) &appData.highlightSquareColor, "", NULL, TextBox, _("Highlight Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#FFFF00", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
{ 0, 0, 70, NULL, (void*) &appData.premoveHighlightColor, "", NULL, TextBox, _("Premove Highlight Color:") },
-{ 1000, 1, 0, NULL, NULL, NULL, NULL, Button, " " },
+{ 1000, 1, 0, NULL, (void*) &DefColor, NULL, (char**) "#FF0000", Button, " " },
{ 1, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "R" },
{ 2, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "G" },
{ 3, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "B" },
-{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "W" },
-{ 0, 0, 0, NULL, (void*) &appData.upsideDown, "", NULL, CheckBox, _("Flip Pieces Shogi Style") },
+{ 4, 1, 0, NULL, (void*) &AdjustColor, NULL, NULL, Button, "D" },
+{ 0, 0, 0, NULL, (void*) &appData.upsideDown, "", NULL, CheckBox, _("Flip Pieces Shogi Style (Colored buttons restore default)") },
{ 0, 0, 0, NULL, (void*) &appData.allWhite, "", NULL, CheckBox, _("Use Outline Pieces for Black") },
{ 0, 0, 0, NULL, (void*) &appData.monoMode, "", NULL, CheckBox, _("Mono Mode") },
{ 0,-1, 5, NULL, (void*) &appData.overrideLineGap, "", NULL, Spin, _("Line Gap ( -1 = default for board size):") },
} else ((ButtonCallback*) currentOption[data].target)(data);
}
+static char *oneLiner = "<Key>Return: redraw-display()\n";
+
int
GenericPopUp(Option *option, char *title, int dlgNr)
{
static char pane[6] = "paneX";
Widget texts[100], forelast = NULL, anchor, widest, lastrow = NULL;
- if(shellUp[dlgNr]) return 0; // already up
+ if(shellUp[dlgNr]) return 0; // already up
if(dlgNr && shells[dlgNr]) {
XtPopup(shells[dlgNr], XtGrabNone);
shellUp[dlgNr] = True;
option[i].handle = (void*)
(textField = last = XtCreateManagedWidget("text", asciiTextWidgetClass, form, args, j));
XtAddEventHandler(last, ButtonPressMask, False, SetFocus, (XtPointer) popup);
+ if(option[i].min == 0 || option[i].type != TextBox)
+ XtOverrideTranslations(last, XtParseTranslationTable(oneLiner));
if(option[i].type == TextBox || option[i].type == Fractional) break;
}
XtSetArg(args[j], XtNwidth, w); j++;
edit = XtCreateManagedWidget(msg, commandWidgetClass, form, args, j);
- XtAddCallback(edit, XtNcallback, SpinCallback,
- (XtPointer)(intptr_t) i);
+ XtAddCallback(edit, XtNcallback, SpinCallback, (XtPointer)(intptr_t) i);
if(option[i].type != Spin) break;
XtSetArg(args[j], XtNleft, XtChainRight); j++;
XtSetArg(args[j], XtNright, XtChainRight); j++;
last = XtCreateManagedWidget("-", commandWidgetClass, form, args, j);
- XtAddCallback(last, XtNcallback, SpinCallback,
- (XtPointer)(intptr_t) i);
+ XtAddCallback(last, XtNcallback, SpinCallback, (XtPointer)(intptr_t) i);
break;
case CheckBox:
if(!currentCps) option[i].value = *(Boolean*)option[i].target;
XtSetArg(args[j], XtNborderWidth, 0); j++;
XtSetArg(args[j], XtNjustify, XtJustifyLeft); j++;
last = XtCreateManagedWidget(msg, labelWidgetClass, form, args, j);
+ if(option[i].type == CheckBox)
+ XtAddEventHandler(last, ButtonPressMask, False, CheckCallback, (XtPointer)(intptr_t) i);
break;
case SaveButton:
case Button:
}
option[i].handle = (void*)
(dialog = last = XtCreateManagedWidget(option[i].name, commandWidgetClass, form, args, j));
- if(option[i].target == NULL && !currentCps) SetColor( *(char**) option[i-1].target, last); else
+ if(option[i].choice && !currentCps) {
+ SetColor( *(char**) option[i-1].target, last);
+ XtAddEventHandler(option[i-1].handle, KeyReleaseMask, False, ColorChanged, (XtPointer)(intptr_t) i-1);
+ }
XtAddCallback(last, XtNcallback, GenericCallback,
(XtPointer)(intptr_t) i + (dlgNr<<16));
if(option[i].textValue) SetColor( option[i].textValue, last);
XtSetArg(args[j], XtNleft, XtChainRight); j++;
XtSetArg(args[j], XtNright, XtChainRight); j++;
b_ok = XtCreateManagedWidget(_("OK"), commandWidgetClass, form, args, j);
- XtAddCallback(b_ok, XtNcallback, GenericCallback, (XtPointer) dlgNr);
+ XtAddCallback(b_ok, XtNcallback, GenericCallback, (XtPointer)(intptr_t) dlgNr + (dlgNr<<16));
XtSetArg(args[0], XtNfromHoriz, b_ok);
b_cancel = XtCreateManagedWidget(_("cancel"), commandWidgetClass, form, args, j);
- XtAddCallback(b_cancel, XtNcallback, GenericCallback, (XtPointer) dlgNr);
+ XtAddCallback(b_cancel, XtNcallback, GenericCallback, (XtPointer)(intptr_t) dlgNr);
}
XtRealizeWidget(popup);
GenericPopUp(matchOptions, _("Match Options"), 0);
}
+Option textOptions[100];
+extern char *icsTextMenuString;
+void PutText P((char *text, int pos));
+
+SendString(char *p)
+{
+ char buf[MSG_SIZ], *q;
+ if(q = strstr(p, "$input")) {
+ if(!shellUp[4]) return;
+ strncpy(buf, p, MSG_SIZ);
+ strncpy(buf + (q-p), q+6, MSG_SIZ-(q-p));
+ PutText(buf, q-p);
+ return;
+ }
+ snprintf(buf, MSG_SIZ, "%s\n", p);
+ SendToICS(buf);
+}
+
+/* function called when the data to Paste is ready */
+static void
+SendTextCB(Widget w, XtPointer client_data, Atom *selection,
+ Atom *type, XtPointer value, unsigned long *len, int *format)
+{
+ char buf[MSG_SIZ], *p = (char*) textOptions[(int)(intptr_t) client_data].choice, *name = (char*) value, *q;
+ if (value==NULL || *len==0) return; /* nothing selected, abort */
+ name[*len]='\0';
+ strncpy(buf, p, MSG_SIZ);
+ q = strstr(p, "$name");
+ snprintf(buf + (q-p), MSG_SIZ -(q-p), "%s%s", name, q+5);
+ SendString(buf);
+ XtFree(value);
+}
+
+void SendText(int n)
+{
+ char *p = (char*) textOptions[n].choice;
+ if(strstr(p, "$name")) {
+ XtGetSelectionValue(menuBarWidget,
+ XA_PRIMARY, XA_STRING,
+ /* (XtSelectionCallbackProc) */ SendTextCB,
+ (XtPointer) (intptr_t) n, /* client_data passed to PastePositionCB */
+ CurrentTime
+ );
+ } else SendString(p);
+}
+
+void IcsTextProc(w, event, prms, nprms)
+ Widget w;
+ XEvent *event;
+ String *prms;
+ Cardinal *nprms;
+{
+ int i=0, j;
+ char *p, *q, *r;
+ if((p = icsTextMenuString) == NULL) return;
+ do {
+ q = r = p; while(*p && *p != ';') p++;
+ for(j=0; j<p-q; j++) textOptions[i].name[j] = *r++;
+ textOptions[i].name[j++] = 0;
+ if(!*p) break;
+ if(*++p == '\n') p++; // optional linefeed after button-text terminating semicolon
+ q = p;
+ textOptions[i].choice = (char**) (r = textOptions[i].name + j);
+ while(*p && (*p != ';' || p[1] != '\n')) textOptions[i].name[j++] = *p++;
+ textOptions[i].name[j++] = 0;
+ if(*p) p += 2;
+ textOptions[i].max = 135;
+ textOptions[i].min = i&1;
+ textOptions[i].handle = NULL;
+ textOptions[i].target = &SendText;
+ textOptions[i].textValue = strstr(r, "$input") ? "#80FF80" : strstr(r, "$name") ? "#FF8080" : "#FFFFFF";
+ textOptions[i].type = Button;
+ } while(++i < 99 && *p);
+ if(i == 0) return;
+ textOptions[i].type = EndMark;
+ textOptions[i].target = NULL;
+ textOptions[i].min = 2;
+ MarkMenu("menuView.ICStex", 3);
+ GenericPopUp(textOptions, _("ICS text menu"), 3);
+}
+
+static char *commentText;
+static int commentIndex;
+void ClearComment P((int n));
+extern char commentTranslations[];
+
+void NewComCallback(int n)
+{
+ ReplaceComment(commentIndex, commentText);
+}
+
+void SaveChanges(int n)
+{
+ Arg args[16];
+ XtSetArg(args[0], XtNstring, &commentText);
+ XtGetValues(currentOption[0].handle, args, 1);
+ ReplaceComment(commentIndex, commentText);
+}
+
+Option commentOptions[] = {
+{ 0xD, 200, 300, NULL, (void*) &commentText, "", NULL, TextBox, "" },
+{ 0, 0, 0, NULL, (void*) &ClearComment, NULL, NULL, Button, "clear" },
+{ 0, 1, 0, NULL, (void*) &SaveChanges, NULL, NULL, Button, "save changes" },
+{ 0, 1, 0, NULL, (void*) &NewComCallback, "", NULL, EndMark , "" }
+};
+
+void ClearComment(int n)
+{
+ XtCallActionProc(commentOptions[0].handle, "select-all", NULL, NULL, 0);
+ XtCallActionProc(commentOptions[0].handle, "kill-selection", NULL, NULL, 0);
+}
+
+void NewCommentPopup(char *title, char *text, int index)
+{
+ Widget edit;
+ Arg args[16];
+
+ if(shells[1]) { // if already exists, alter title and content
+ XtSetArg(args[0], XtNtitle, title);
+ XtSetValues(shells[1], args, 1);
+ XtSetArg(args[0], XtNstring, text);
+ XtSetValues(commentOptions[0].handle, args, 1);
+ }
+ commentText = text;
+ commentIndex = index;
+ MarkMenu("menuView.Show Comments", 1);
+ if(GenericPopUp(commentOptions, title, 1))
+ XtOverrideTranslations(commentOptions[0].handle, XtParseTranslationTable(commentTranslations));
+}
+
+static char *tagsText, *msgText;
+
+void NewTagsCallback(int n)
+{
+ ReplaceTags(tagsText, &gameInfo);
+}
+
+void changeTags(int n)
+{
+ Arg args[16];
+ XtSetArg(args[0], XtNstring, &tagsText);
+ XtGetValues(currentOption[0].handle, args, 1);
+ ReplaceTags(tagsText, &gameInfo);
+}
+
+Option tagsOptions[] = {
+{ 0xD, 200, 250, NULL, (void*) &tagsText, "", NULL, TextBox, "" },
+{ 0, 0, 0, NULL, NULL, NULL, NULL, Label, "" },
+{ 0, 0, 0, NULL, (void*) &changeTags, NULL, NULL, Button, "save changes" },
+{ 0, 1, 0, NULL, (void*) &NewTagsCallback, "", NULL, EndMark , "" }
+};
+
+void NewTagsPopup(char *text, char *msg)
+{
+ Widget edit;
+ Arg args[16];
+
+ if(shells[2]) { // if already exists, alter title and content
+ XtSetArg(args[0], XtNstring, text);
+ XtSetValues(tagsOptions[0].handle, args, 1);
+ }
+ tagsText = text;
+ tagsOptions[1].textValue = msg;
+ MarkMenu("menuView.Show Tags", 2);
+ GenericPopUp(tagsOptions, _("Tags"), 2);
+}
+
+extern char ICSInputTranslations[];
+char *icsText;
+
+Option boxOptions[] = {
+{ 0, 20, 400, NULL, (void*) &icsText, "", NULL, TextBox, "" },
+{ 0, 3, 0, NULL, NULL, "", NULL, EndMark , "" }
+};
+
+void PutText(char *text, int pos)
+{
+ Widget edit;
+ Arg args[16];
+ char buf[MSG_SIZ], *p;
+
+ if(strstr(text, "$add ") == text) {
+ XtSetArg(args[0], XtNstring, &p);
+ XtGetValues(boxOptions[0].handle, args, 1);
+ snprintf(buf, MSG_SIZ, "%s%s", p, text+5); text = buf;
+ pos += strlen(p) - 5;
+ }
+ XtSetArg(args[0], XtNstring, text);
+ XtSetValues(boxOptions[0].handle, args, 1);
+ XtSetArg(args[0], XtNinsertPosition, pos);
+ XtSetValues(boxOptions[0].handle, args, 1);
+// SetFocus(boxOptions[0].handle, shells[4], NULL, False); // No idea why this does not work, and the following is needed:
+ XSetInputFocus(xDisplay, XtWindow(boxOptions[0].handle), RevertToPointerRoot, CurrentTime);
+}
+
+void InputBoxPopup()
+{
+ MarkMenu("menuView.ICS Input Box", 4);
+ if(GenericPopUp(boxOptions, _("ICS input box"), 4))
+ XtOverrideTranslations(boxOptions[0].handle, XtParseTranslationTable(ICSInputTranslations));
+}
+
void
SettingsPopUp(ChessProgramState *cps)
{