/*
 * Copyright 1995 TriloBYTE Software Solutions.
 *
 * Author: Amen Zwa, TriloBYTE.
 */



static char* sccsid = "%W%\t%G%\tAmen Zwa, TriloBYTE.";



// main.c: OpenGL/GLX-based image server



#include <new.h>
#include <sys/resource.h>

#include "imagewnd.h"
#include "menu.h"
#include "etc.h"



// fallback resources
static String fallback_rsrc[] = {
    "imgsvr*background: gray75",
    "imgsvr*foreground: black",
    "imgsvr*topShadowColor: gray95",
    "imgsvr*bottomShadowColor: gray25",
    "imgsvr*selectColor: black",
    "imgsvr*XmForm*background: gray75",
    "imgsvr*XmCascadeButton*fontList: \
        -adobe-helvetica-bold-r-*-*-12-*-*-*-*-*-*-*",
    "imgsvr*XmPushButton*fontList: \
        -adobe-helvetica-bold-r-*-*-12-*-*-*-*-*-*-*",
    "imgsvr*XmPushButton*shadowThickness: 2",
    "imgsvr*XmToggleButton*fontList: 6x13",
    "imgsvr*XmToggleButton*shadowThickness: 2",
    "imgsvr*XmLabel*fontList: 6x13",
    "imgsvr*XmList*fontList: 6x13",
    "imgsvr*XmText*fontList: 6x13",
    "imgsvr*WMenu*background: SteelBlue1",
    "imgsvr*WMenu*topShadowColor: CadetBlue1",
    "imgsvr*WMenu*bottomShadowColor: SteelBlue4",
    "imgsvr*WMenu*fontList: \
        -adobe-helvetica-bold-r-*-*-12-*-*-*-*-*-*-*",
    "imgsvr*XmMessageBox*fontList: 6x13",
    0
};



void out_of_mem()
{
    error_dialog("Out of memory.");
}



#if defined(BSD43)
void sigint_handler(int, ...)
#elif defined(SVR4)
#if defined(sun)
void sigint_handler(int)
#elif defined(__sgi)
void sigint_handler(...)
#endif	// sun, __sgi
#endif	// BSD43, SVR4
{
#if defined(TEST)
    error("SIGINT");
#endif
    cleanup();
    exit(0);
}



#if defined(BSD43)
void sigbus_handler(int, ...)
#elif defined(SVR4)
#if defined(sun)
void sigbus_handler(int)
#elif defined(__sgi)
void sigbus_handler(...)
#endif	// sun, __sgi
#endif	// BSD43, SVR4
{
#if defined(TEST)
    error("SIGBUS");
    abort();
#endif
}



#if defined(BSD43)
void sigsegv_handler(int, ...)
#elif defined(SVR4)
#if defined(sun)
void sigsegv_handler(int)
#elif defined(__sgi)
void sigsegv_handler(...)
#endif	// sun, __sgi
#endif	// BSD43, SVR4
{
#if defined(TEST)
    error("SIGSEGV");
    abort();
#endif
}



int main(int argc, char** argv)
{
    set_new_handler(&out_of_mem);
    signal(SIGINT, sigint_handler);
    signal(SIGBUS, sigbus_handler);
    signal(SIGSEGV, sigsegv_handler);
#if !defined(TEST)
    struct rlimit rlim = { 0, 0 };
    setrlimit(RLIMIT_CORE, &rlim);
#endif
    appname = strnew(argv[0]);
    int c, svrport = I_SvrPort;
    char rgbfname[STRLEN];
    rgbfname[0] = '\0';
    while ((c = getopt(argc, argv, "c:p:h")) != EOF)
	switch (c) {
	case 'c':
	    strcpy(rgbfname, optarg);
	    break;
	case 'p':
	    svrport = atoi(optarg);
	    break;
	case 'h':
	case '?':
	    error("Usage: imgsvr [-c rgbfile] [-p svrport]");
	    exit(1);
	    break;
	}
    XtAppContext xtctx;
    WAppShell* appshl = new WAppShell("Image Server", argc, argv,
	xtctx, fallback_rsrc);
    context = new WContext(appshl, xtctx);
    if (!display) {
	error("Cannot connect to X server.");
	exit(1);
    }
    XStandardColormap* stdcmap = 0;
    if (rgbfname[0] == '\0') {
	Atom cmap = (colorpln == 8) ? XA_RGB_DEFAULT_MAP : XA_RGB_BEST_MAP;
	int numcmap;
	Status stat = XGetRGBColormaps(display, root_wnd,
				       &stdcmap, &numcmap, cmap);
#if defined(TEST)
	if (stat) {
	    cout << "standard colormap:\n"
		<< "\tdepth = " << colorpln << '\n'
		<< "\tnum cmap = " << numcmap << '\n'
		<< "\tcolormap = " << long(stdcmap->colormap) << '\n'
		<< "\trgb max = "
		<< stdcmap->red_max << ','
		<< stdcmap->green_max << ','
		<< stdcmap->blue_max << '\n'
		<< "\trgb mul = "
		<< stdcmap->red_mult << ','
		<< stdcmap->green_mult << ','
		<< stdcmap->blue_mult << endl;
	}
#endif
	if (!stat) {
	    if (colorpln == 8)
	      error("XA_RGB_DEFAULT_MAP standard colormap not allocated.");
	    else if (colorpln == 24)
	      error("XA_RGB_BEST_MAP standard colormap not allocated.");
	    exit(1);
	}
    }
    imagewnd = new ImageWnd(stdcmap);
    if (rgbfname[0] != '\0') imagewnd->set_rgbfile(rgbfname);
    imagewnd->show();
    imagewnd->start_server(svrport);
    context->run();
    return 0;
}
