# endif
#endif
+
+# if HAVE_LIBREADLINE /* add gnu-readline support */
+#include <readline/readline.h>
+#include <readline/history.h>
+# endif
+
#include <X11/Intrinsic.h>
#include <X11/StringDefs.h>
#include <X11/Shell.h>
void CreateGCs P((void));
void CreateXIMPieces P((void));
void CreateXPMPieces P((void));
+void CreateXPMBoard P((char *s, int n));
void CreatePieces P((void));
void CreatePieceMenus P((void));
Widget CreateMenuBar P((Menu *mb));
void update_ics_width P(());
int get_term_width P(());
int CopyMemoProc P(());
+
+# if HAVE_LIBREADLINE /* add gnu-readline support */
+static void ReadlineCompleteHandler P((char *));
+# endif
+
/*
* XBoard depends on Xt R4 or higher
*/
char *fileOpenMode;
char installDir[] = "."; // [HGM] UCI: needed for UCI; probably needs run-time initializtion
+# if HAVE_LIBREADLINE /* gnu readline support */
+static char* readline_buffer;
+static int readline_complete=0;
+extern int sending_ICS_login;
+extern int sending_ICS_password;
+#endif
+
Position commentX = -1, commentY = -1;
Dimension commentW, commentH;
typedef unsigned int BoardSize;
Pixmap xpmPieceBitmap[4][(int)BlackPawn]; /* LL, LD, DL, DD actually used*/
Pixmap xpmPieceBitmap2[4][(int)BlackPawn+4]; /* LL, LD, DL, DD set to select from */
Pixmap xpmLightSquare, xpmDarkSquare, xpmJailSquare;
-int useImages, useImageSqs;
+Pixmap xpmBoardBitmap[2];
+int useImages, useImageSqs, useTexture, textureW[2], textureH[2];
XImage *ximPieceBitmap[4][(int)BlackPawn+4]; /* LL, LD, DL, DD */
Pixmap ximMaskPm[(int)BlackPawn]; /* clipmasks, used for XIM pieces */
Pixmap ximMaskPm2[(int)BlackPawn+4]; /* clipmasks, used for XIM pieces */
\"Send to second chess program:\",,2) \n";
char boardTranslations[] =
- "<Btn1Down>: HandleUserMove() \n \
- <Btn1Up>: HandleUserMove() \n \
+ "<Btn1Down>: HandleUserMove(0) \n \
+ Shift<Btn1Up>: HandleUserMove(1) \n \
+ <Btn1Up>: HandleUserMove(0) \n \
<Btn1Motion>: AnimateUserMove() \n \
<Btn3Motion>: HandlePV() \n \
<Btn3Up>: PieceMenuPopup(menuB) \n \
PopUpStartupDialog()
{ // start menu not implemented in XBoard
}
+
char *
ConvertToLine(int argc, char **argv)
{
int i;
line[0] = NULLCHAR;
- for(i=1; i<argc; i++) {
- if( (strchr(argv[i], ' ') || strchr(argv[i], '\n') ||strchr(argv[i], '\t') )
- && argv[i][0] != '{' )
- snprintf(buf, sizeof(buf)/sizeof(buf[0]), "{%s} ", argv[i]);
- else
- snprintf(buf, sizeof(buf)/sizeof(buf[0]), "%s ", argv[i]);
- strcat(line, buf);
- }
- line[strlen(line)-1] = NULLCHAR;
+ for(i=1; i<argc; i++)
+ {
+ if( (strchr(argv[i], ' ') || strchr(argv[i], '\n') ||strchr(argv[i], '\t') )
+ && argv[i][0] != '{' )
+ snprintf(buf, sizeof(buf)/sizeof(buf[0]), "{%s} ", argv[i]);
+ else
+ snprintf(buf, sizeof(buf)/sizeof(buf[0]), "%s ", argv[i]);
+ strncat(line, buf, 128*1024 - strlen(line) - 1 );
+ }
+
+ line[strlen(line)-1] = NULLCHAR;
return line;
}
setbuf(stdout, NULL);
setbuf(stderr, NULL);
debugFP = stderr;
+
+# if HAVE_LIBREADLINE
+ /* install gnu-readline handler */
+ rl_callback_handler_install("> ", ReadlineCompleteHandler);
+ rl_readline_name="XBoard";
+# endif
if(argc > 1 && (!strcmp(argv[1], "-v" ) || !strcmp(argv[1], "--version" ))) {
printf("%s version %s\n", PACKAGE_NAME, PACKAGE_VERSION);
fprintf(stderr, _("Closest %s size: %d\n"), IMAGE_EXT, squareSize);
}
}
+ if(appData.overrideLineGap >= 0) lineGap = appData.overrideLineGap;
/* [HR] height treated separately (hacked) */
boardWidth = lineGap + BOARD_WIDTH * (squareSize + lineGap);
CreatePieces();
} else {
CreateXPMPieces();
+ CreateXPMBoard(appData.liteBackTextureFile, 1);
+ CreateXPMBoard(appData.darkBackTextureFile, 0);
}
#else
CreateXIMPieces();
if (saveSettingsOnExit) SaveSettings(settingsFileName);
unlink(gameCopyFilename);
unlink(gamePasteFilename);
+
+# if HAVE_LIBREADLINE
+ /* remove gnu-readline handler. */
+ rl_callback_handler_remove();
+#endif
+
+ return;
}
RETSIGTYPE TermSizeSigHandler(int sig)
void
ICSInitScript()
{
- FILE *f;
- char buf[MSG_SIZ];
- char *p;
+ /* try to open the icsLogon script, either in the location given
+ * or in the users HOME directory
+ */
+
+ FILE *f;
+ char buf[MSG_SIZ];
+ char *homedir;
- f = fopen(appData.icsLogon, "r");
- if (f == NULL) {
- p = getenv("HOME");
- if (p != NULL) {
- safeStrCpy(buf, p, sizeof(buf)/sizeof(buf[0]) );
- strcat(buf, "/");
- strcat(buf, appData.icsLogon);
+ f = fopen(appData.icsLogon, "r");
+ if (f == NULL)
+ {
+ homedir = getenv("HOME");
+ if (homedir != NULL)
+ {
+ safeStrCpy(buf, homedir, sizeof(buf)/sizeof(buf[0]) );
+ strncat(buf, "/", MSG_SIZ - strlen(buf) - 1);
+ strncat(buf, appData.icsLogon, MSG_SIZ - strlen(buf) - 1);
f = fopen(buf, "r");
}
}
- if (f != NULL)
- ProcessICSInitScript(f);
+
+ if (f != NULL)
+ ProcessICSInitScript(f);
+ else
+ printf("Warning: Couldn't open icsLogon file (checked %s and %s).\n", appData.icsLogon, buf);
+
+ return;
}
void
}
#if HAVE_LIBXPM
+void CreateXPMBoard(char *s, int kind)
+{
+ XpmAttributes attr;
+ attr.valuemask = 0;
+ if(s == NULL || *s == 0 || *s == '*') return;
+ if (XpmReadFileToPixmap(xDisplay, xBoardWindow, s, &(xpmBoardBitmap[kind]), NULL, &attr) == 0) {
+ useTexture |= kind + 1; textureW[kind] = attr.width; textureH[kind] = attr.height;
+ }
+}
+
void CreateXPMPieces()
{
int piece, kind, r;
if (*appData.bitmapDirectory != NULLCHAR) {
safeStrCpy(fullname, appData.bitmapDirectory, sizeof(fullname)/sizeof(fullname[0]) );
- strcat(fullname, "/");
- strcat(fullname, name);
- errcode = XReadBitmapFile(xDisplay, xBoardWindow, fullname,
- &w, &h, pm, &x_hot, &y_hot);
- fprintf(stderr, "load %s\n", name);
+ strncat(fullname, "/", MSG_SIZ - strlen(fullname) - 1);
+ strncat(fullname, name, MSG_SIZ - strlen(fullname) - 1);
+ errcode = XReadBitmapFile(xDisplay, xBoardWindow, fullname,
+ &w, &h, pm, &x_hot, &y_hot);
+ fprintf(stderr, "load %s\n", name);
if (errcode != BitmapSuccess) {
switch (errcode) {
case BitmapOpenFailed:
while (mb->name != NULL) {
safeStrCpy(menuName, "menu", sizeof(menuName)/sizeof(menuName[0]) );
- strcat(menuName, mb->name);
+ strncat(menuName, mb->name, MSG_SIZ - strlen(menuName) - 1);
j = 0;
XtSetArg(args[j], XtNmenuName, XtNewString(menuName)); j++;
if (tinyLayout) {
SetPremoveHighlights(-1, -1, -1, -1);
}
-static void BlankSquare(x, y, color, piece, dest)
- int x, y, color;
+static int CutOutSquare(x, y, x0, y0, kind)
+ int x, y, *x0, *y0, kind;
+{
+ int W = BOARD_WIDTH, H = BOARD_HEIGHT;
+ int nx = x/(squareSize + lineGap), ny = y/(squareSize + lineGap);
+ *x0 = 0; *y0 = 0;
+ if(textureW[kind] < squareSize || textureH[kind] < squareSize) return 0;
+ if(textureW[kind] < W*squareSize)
+ *x0 = (textureW[kind] - squareSize) * nx/(W-1);
+ else
+ *x0 = textureW[kind]*nx / W + (textureW[kind] - W*squareSize) / (2*W);
+ if(textureH[kind] < H*squareSize)
+ *y0 = (textureH[kind] - squareSize) * ny/(H-1);
+ else
+ *y0 = textureH[kind]*ny / H + (textureH[kind] - H*squareSize) / (2*H);
+ return 1;
+}
+
+static void BlankSquare(x, y, color, piece, dest, fac)
+ int x, y, color, fac;
ChessSquare piece;
Drawable dest;
-{
+{ // [HGM] extra param 'fac' for forcing destination to (0,0) for copying to animation buffer
+ int x0, y0;
+ if (useImages && color != 2 && (useTexture & color+1) && CutOutSquare(x, y, &x0, &y0, color)) {
+ XCopyArea(xDisplay, xpmBoardBitmap[color], dest, wlPieceGC, x0, y0,
+ squareSize, squareSize, x*fac, y*fac);
+ } else
if (useImages && useImageSqs) {
Pixmap pm;
switch (color) {
break;
}
XCopyArea(xDisplay, pm, dest, wlPieceGC, 0, 0,
- squareSize, squareSize, x, y);
+ squareSize, squareSize, x*fac, y*fac);
} else {
GC gc;
switch (color) {
gc = jailSquareGC;
break;
}
- XFillRectangle(xDisplay, dest, gc, x, y, squareSize, squareSize);
+ XFillRectangle(xDisplay, dest, gc, x*fac, y*fac, squareSize, squareSize);
}
}
int square_color, x, y;
Drawable dest;
{
- int kind;
+ int kind, p = piece;
switch (square_color) {
case 1: /* light */
}
break;
}
+ if(appData.upsideDown && flipView) kind ^= 2; // swap white and black pieces
+ if(useTexture & square_color+1) {
+ BlankSquare(x, y, square_color, piece, dest, 1); // erase previous contents with background
+ XSetClipMask(xDisplay, wlPieceGC, xpmMask[p]);
+ XSetClipOrigin(xDisplay, wlPieceGC, x, y);
+ XCopyArea(xDisplay, xpmPieceBitmap[kind][piece], dest, wlPieceGC, 0, 0, squareSize, squareSize, x, y);
+ XSetClipMask(xDisplay, wlPieceGC, None);
+ XSetClipOrigin(xDisplay, wlPieceGC, 0, 0);
+ } else
XCopyArea(xDisplay, xpmPieceBitmap[kind][piece],
dest, wlPieceGC, 0, 0,
squareSize, squareSize, x, y);
column == BOARD_LEFT-1 || column == BOARD_RGHT
|| (column == BOARD_LEFT-2 && row < BOARD_HEIGHT-gameInfo.holdingsSize)
|| (column == BOARD_RGHT+1 && row >= gameInfo.holdingsSize) ) {
- BlankSquare(x, y, 2, EmptySquare, xBoardWindow);
+ BlankSquare(x, y, 2, EmptySquare, xBoardWindow, 1);
// [HGM] print piece counts next to holdings
string[1] = NULLCHAR;
}
} else {
if (piece == EmptySquare || appData.blindfold) {
- BlankSquare(x, y, square_color, piece, xBoardWindow);
+ BlankSquare(x, y, square_color, piece, xBoardWindow, 1);
} else {
drawfunc = ChooseDrawFunc();
if (do_flash && appData.flashCount > 0) {
XSync(xDisplay, False);
do_flash_delay(flash_delay);
- BlankSquare(x, y, square_color, piece, xBoardWindow);
+ BlankSquare(x, y, square_color, piece, xBoardWindow, 1);
XSync(xDisplay, False);
do_flash_delay(flash_delay);
}
if(DrawSeekGraph()) return; // [HGM] seekgraph: suppress any drawing if seek graph up
if (board == NULL) {
- if (!lastBoardValid) return;
+ if (!lastBoardValid[nr]) return;
board = lastBoard[nr];
}
if (!lastBoardValid[nr] || (nr == 0 && lastFlipView != flipView)) {
Cardinal *nprms;
{
if (w != boardWidget || errorExitStatus != -1) return;
+ if(nprms) shiftKey = !strcmp(prms[0], "1");
if (promotionUp) {
if (event->type == ButtonPress) {
reply = XawDialogGetValueString(w = XtParent(w));
safeStrCpy(buf, pendingReplyPrefix, sizeof(buf)/sizeof(buf[0]) );
- if (*buf) strcat(buf, " ");
- strcat(buf, reply);
- strcat(buf, "\n");
+ if (*buf) strncat(buf, " ", MSG_SIZ - strlen(buf) - 1);
+ strncat(buf, reply, MSG_SIZ - strlen(buf) - 1);
+ strncat(buf, "\n", MSG_SIZ - strlen(buf) - 1);
OutputToProcess(pendingReplyPR, buf, strlen(buf), &err);
AskQuestionPopDown();
}
q = is->buf;
while (p < is->unused) {
- *q++ = *p++;
+ *q++ = *p++;
}
is->unused = q;
} else {
- count = read(is->fd, is->buf, INPUT_SOURCE_BUF_SIZE);
- if (count == -1)
- error = errno;
- else
- error = 0;
- (is->func)(is, is->closure, is->buf, count, error);
+# if HAVE_LIBREADLINE
+ /* check if input is from stdin, if yes, use gnu-readline */
+ if( is->fd==fileno(stdin) )
+ {
+ /* to clear the line */
+ printf("\r \r");
+
+ /* read from stdin */
+ rl_callback_read_char();
+
+ /* redisplay the current line, check special case for login and password */
+ if(sending_ICS_password)
+ {
+ int i; char buf[MSG_SIZ];
+
+ bzero(buf,MSG_SIZ);
+
+ /* blank the password */
+ count = strlen(rl_line_buffer);
+ if(count>MSG_SIZ-1)
+ {
+ printf("PROBLEM with readline\n");
+ count=MSG_SIZ;
+ }
+ for(i=0;i<count;i++)
+ buf[i]='*';
+ i++;
+ buf[i]='\0';
+ printf("\rpassword: %s",buf);
+ }
+ else if (sending_ICS_login)
+ {
+ /* show login prompt */
+ count = strlen(rl_line_buffer);
+ printf("\rlogin: %s",rl_line_buffer);
+ }
+ else
+ rl_reset_line_state();
+
+ if(readline_complete)
+ {
+ /* copy into XBoards buffer */
+ count = strlen(readline_buffer);
+ if (count>INPUT_SOURCE_BUF_SIZE-1)
+ {
+ printf("PROBLEM with readline\n");
+ count = INPUT_SOURCE_BUF_SIZE;
+ };
+ strncpy(is->buf,readline_buffer,count);
+ is->buf[count]='\n';count++;
+
+ /* reset gnu-readline state */
+ free(readline_buffer);
+ readline_buffer=NULL;
+ readline_complete=0;
+
+ if (count == -1)
+ error = errno;
+ else
+ error = 0;
+ (is->func)(is, is->closure, is->buf, count, error);
+
+ /* are we done with the password? */
+ if(sending_ICS_password)
+ sending_ICS_password=0;
+ if(sending_ICS_login)
+ sending_ICS_login=0;
+ }
+ }
+ else
+ {
+ /* input not from stdin, use default method */
+ count = read(is->fd, is->buf, INPUT_SOURCE_BUF_SIZE);
+ if (count == -1)
+ error = errno;
+ else
+ error = 0;
+ (is->func)(is, is->closure, is->buf, count, error);
+ };
+#else /* no readline support */
+ count = read(is->fd, is->buf, INPUT_SOURCE_BUF_SIZE);
+ if (count == -1)
+ error = errno;
+ else
+ error = 0;
+ (is->func)(is, is->closure, is->buf, count, error);
+#endif
+
}
}
ChildProc *cp = (ChildProc *) pr;
int outCount;
+
if (pr == NoProc)
{
- if (appData.noJoin || !appData.useInternalWrap)
- outCount = fwrite(message, 1, count, stdout);
- else
+ if (appData.noJoin || !appData.useInternalWrap)
+ outCount = fwrite(message, 1, count, stdout);
+ else
{
- int width = get_term_width();
- int len = wrap(NULL, message, count, width, &line);
- char *msg = malloc(len);
- int dbgchk;
-
- if (!msg)
- outCount = fwrite(message, 1, count, stdout);
- else
+ int width = get_term_width();
+ int len = wrap(NULL, message, count, width, &line);
+ char *msg = malloc(len);
+ int dbgchk;
+
+ if (!msg)
+ outCount = fwrite(message, 1, count, stdout);
+ else
{
- dbgchk = wrap(msg, message, count, width, &line);
- if (dbgchk != len && appData.debugMode)
- fprintf(debugFP, "wrap(): dbgchk(%d) != len(%d)\n", dbgchk, len);
- outCount = fwrite(msg, 1, dbgchk, stdout);
- free(msg);
+ dbgchk = wrap(msg, message, count, width, &line);
+ if (dbgchk != len && appData.debugMode)
+ fprintf(debugFP, "wrap(): dbgchk(%d) != len(%d)\n", dbgchk, len);
+ outCount = fwrite(msg, 1, dbgchk, stdout);
+ free(msg);
}
}
+
+# if HAVE_LIBREADLINE
+ /* readline support */
+ if(strlen(rl_line_buffer))
+ printf("\n> %s",rl_line_buffer);
+#endif
+
}
else
outCount = write(cp->fdTo, message, count);
kind = 0;
else
kind = 2;
+ if(appData.upsideDown && flipView) kind ^= 2;
XCopyArea(xDisplay, xpmPieceBitmap[kind][piece],
dest, clip,
0, 0, squareSize, squareSize,
Pixmap mask;
/* The old buffer is initialised with the start square (empty) */
- BlankSquare(0, 0, startColor, EmptySquare, anim->saveBuf);
+ BlankSquare(start->x, start->y, startColor, EmptySquare, anim->saveBuf, 0);
anim->prevFrame = *start;
/* The piece will be drawn using its own bitmap as a matte */
it's being dragged around the board. So we erase the square
that the piece is on and draw it at the last known drag point. */
BlankSquare(player.startSquare.x, player.startSquare.y,
- player.startColor, EmptySquare, xBoardWindow);
+ player.startColor, EmptySquare, xBoardWindow, 1);
AnimationFrame(&player, &player.prevFrame, player.dragPiece);
damage[0][player.startBoardY][player.startBoardX] = TRUE;
}
{
update_ics_width();
}
+
+# if HAVE_LIBREADLINE
+static void
+ReadlineCompleteHandler(char* ptr)
+{
+ /* make gnu-readline keep the history */
+ readline_buffer = ptr;
+ readline_complete = 1;
+
+ if (ptr && *ptr && !sending_ICS_password && !sending_ICS_login)
+ add_history(ptr);
+
+ return;
+}
+#endif