#include <stdio.h>
#include <sys/time.h>
#include <X11/Xlib.h>
#include <X11/Xutil.h>

#include "ztypes.h"
#include "xio.h"

#define LEFTMARGIN 4
#define TOPMARGIN 3
#define TIMEOUT (3) /* in seconds. preference? */

static int messwin_x, messwin_y, messwin_w, messwin_h;
static char *message;
static int messagelen, message_size;
static int messagesticky;
static struct timeval messagetime;

#ifdef __STDC__
void xmess_init()
#else
void xmess_init()
#endif
{
    message_size = 80;
    message = (char *)malloc(message_size * sizeof(char));
    messagelen = 0;
    strcpy(message, "");
    messagesticky = TRUE;
}

#ifdef __STDC__
void xmess_resize(int xpos, int ypos, int width, int height)
#else
void xmess_resize(xpos, ypos, width, height)
int xpos;
int ypos;
int width;
int height;
#endif
{
    messwin_x = xpos;
    messwin_y = ypos;
    messwin_w = width;
    messwin_h = height;

    xmess_redraw();
}

#ifdef __STDC__
void xmess_redraw()
#else
void xmess_redraw()
#endif
{
    XDrawLine(xiodpy, xiowin, gcblack, messwin_x, messwin_y, messwin_x+messwin_w, messwin_y);
    if (messagelen)
	XDrawString(xiodpy, xiowin, gcfont[0], messwin_x+LEFTMARGIN, messwin_y+TOPMARGIN+lineheightoff, message, messagelen);
}

#ifdef __STDC__
void xmess_set_message(char *str, int sticky)
#else
void xmess_set_message(str, sticky)
char *str;
int sticky;
#endif
{
    struct timezone tz;

    if (!str)
	str = "";
    messagelen = strlen(str);
    if (messagelen >= message_size) {
	while (messagelen >= message_size)
	    message_size *= 2;
	message = (char *)realloc(message, message_size * sizeof(char));
    }
    strcpy(message, str);
    XClearArea(xiodpy, xiowin, messwin_x, messwin_y+1, messwin_w, messwin_h-1, FALSE);
    if (messagelen)
	XDrawString(xiodpy, xiowin, gcfont[0], messwin_x+LEFTMARGIN, messwin_y+TOPMARGIN+lineheightoff, message, messagelen);

    messagesticky = sticky;
    gettimeofday(&messagetime, &tz);
    messagetime.tv_sec += TIMEOUT;
}

#ifdef __STDC__
void xmess_check_timeout()
#else
void xmess_check_timeout()
#endif
{
    struct timezone tz;
    struct timeval tv;

    if (messagesticky)
	return;

    gettimeofday(&tv, &tz);
    if (tv.tv_sec > messagetime.tv_sec
	|| (tv.tv_sec == messagetime.tv_sec && tv.tv_usec > messagetime.tv_usec)) {
	xmess_set_message(NULL, TRUE);
    }
}
