#include #include #include #include #include #include #include #include #include struct image { XImage *ximage; int width; int height; }; struct image Image; RwTexDictionary *TexDict; Display *display; Widget da; int TexIndex; int ShowAlpha; void LoadTex(void); void alpha_toggle_cb(Widget w, XtPointer client_data, XtPointer call_data); void file_cb(Widget w, XtPointer client_data, XtPointer call_data); void help_cb(Widget w, XtPointer client_data, XtPointer call_data); void list_cb(Widget w, XtPointer client_data, XtPointer call_data); void redraw(Widget w, XtPointer client_data, XtPointer call_data); void quit_app(Widget w, XtPointer client_data, XtPointer call_data); void make_form(Widget toplevel); XImage *CreateTrueColorImage(Display *dpy, Visual *vis, unsigned char *image, int width, int height); int main(int argc, char *argv[]) { Widget toplevel; XtAppContext app; RwStream *txds; XtSetLanguageProc(NULL, NULL, NULL); toplevel = XtVaOpenApplication(&app, "Draw_Image", NULL, 0, &argc, argv, NULL, sessionShellWidgetClass, NULL); if (argc < 2) { fprintf(stderr, "Not enough arguments\n"); exit(1); } txds = RwStreamOpen(rwSTREAMFILENAME, rwSTREAMREAD, argv[1]); if (!txds) { fprintf(stderr, "Couldn't open file\n"); exit(1); } TexDict = RwTexDictionaryStreamRead2(txds, 0); RwStreamClose(txds, NULL); make_form(toplevel); Image.ximage = NULL; Image.width = 0; Image.height = 0; TexIndex = 0; ShowAlpha = 0; LoadTex(); XtAppMainLoop(app); return 0; } char *ConvertData(RwTexture *tex) { int i, j; char *data, *p; data = (char *) malloc(tex->width*tex->height*4); p = data; j = 0; if (tex->reversed) for (i = 0; i < tex->height*tex->width*4; i+=4) { *p++ = tex->Data_a[i+0]; *p++ = tex->Data_a[i+1]; *p++ = tex->Data_a[i+2]; *p++ = tex->Data_a[i+3]; } else if (ShowAlpha) for (i = 0; i < tex->height*tex->width*4; i+=4) { *p++ = tex->Data_a[i+3]; *p++ = tex->Data_a[i+3]; *p++ = tex->Data_a[i+3]; *p++ = tex->Data_a[i+3]; } else for (i = 0; i < tex->height*tex->width*4; i+=4) { *p++ = tex->Data_a[i+2]; *p++ = tex->Data_a[i+1]; *p++ = tex->Data_a[i+0]; *p++ = tex->Data_a[i+3]; } return data; } void LoadTex() { RwTexture *tex; Visual *vis; char *data; vis = DefaultVisual(display, 0); tex = &TexDict->texture[TexIndex]; // printf("%d\n", TexIndex); // if (Image.ximage != NULL) { // printf("Destroying image\n"); // XDestroyImage(Image.ximage); // Image.ximage = NULL; // } else { // printf("No image\n"); // } if (tex->depth == 32) { data = ConvertData(tex); Image.ximage = XCreateImage(display, vis, 24, ZPixmap, 0, data, tex->width, tex->height, 32, 0); Image.width = tex->width; Image.height = tex->height; free(data); } else { Image.ximage = XCreateImage(display, vis, 24, ZPixmap, 0, NULL, 0, 0, 32, 0); } XtUnmanageChild(da); XtManageChild(da); } XImage *CreateTrueColorImage(Display *dpy, Visual *vis, unsigned char *image, int width, int height) { int i, j; char *image32, *p; image32 = (char *) malloc(width*height*4); p = image32; for (i = 0; i < width; i++) { for (j = 0; j < height; j++) { if ((i<256) && (j<256)) { *p++=rand() % 256; *p++=rand() % 256; *p++=rand() % 256; } else { *p++ = i % 256; *p++ = j % 256; if (i < 256) *p++ = i % 256; else if (j < 256) *p++ = j % 256; else *p++ = (256-j) % 256; } p++; } } return XCreateImage(dpy, vis, 24, ZPixmap, 0, image32, width, height, 32, 0); } void make_form(Widget toplevel) { Widget mainw, widget; Widget form, menubar, menu, list, check; XmString file, help, close, quit; Visual *vis; XmStringTable str_tbl; int i; display = XtDisplay(toplevel); vis = DefaultVisual(display, 0); if (vis->class != TrueColor) { fprintf(stderr, "No true color possible\n"); exit(1); } mainw = XmCreateMainWindow(toplevel, "mainw", NULL, 0); XtManageChild(mainw); /* Menu */ file = XmStringCreateLocalized("File"); help = XmStringCreateLocalized("Help"); menubar = XmVaCreateSimpleMenuBar(mainw, "menubar", XmVaCASCADEBUTTON, file, 'F', XmVaCASCADEBUTTON, help, 'H', NULL); XmStringFree(file); XtManageChild(menubar); if ((widget = XtNameToWidget(menubar, "button_1"))) XtVaSetValues(menubar, XmNmenuHelpWidget, widget, NULL); close = XmStringCreateLocalized("Close"); quit = XmStringCreateLocalized("Quit"); menu = XmVaCreateSimplePulldownMenu(menubar, "file_menu", 0, file_cb, XmVaPUSHBUTTON, close, 'C', NULL, NULL, XmVaSEPARATOR, XmVaPUSHBUTTON, quit, 'Q', NULL, NULL, NULL); XmStringFree(close); XmStringFree(quit); menu = XmVaCreateSimplePulldownMenu(menubar, "help_menu", 1, help_cb, XmVaPUSHBUTTON, help, 'H', NULL, NULL, NULL); XmStringFree(help); /* Form */ form = XmCreateForm(mainw, "form", NULL, 0); XtVaSetValues(form, XmNverticalSpacing, 3, XmNhorizontalSpacing, 3, NULL); XtManageChild(form); /* Check box */ check = XmCreateToggleButton(form, "Alpha", NULL, 0); XtVaSetValues(check, XmNbottomAttachment, XmATTACH_FORM, XmNleftAttachment, XmATTACH_FORM, NULL); XtAddCallback(check, XmNvalueChangedCallback, alpha_toggle_cb, NULL); XtManageChild(check); /* List */ str_tbl = (XmStringTable) XtMalloc(TexDict->numTextures * sizeof(XmString)); for (i = 0; i < TexDict->numTextures; i++) str_tbl[i] = XmStringCreateLocalized(TexDict->texture[i].Name); list = XtVaCreateWidget("list", xmListWidgetClass, form, XmNvisibleItemCount, 8, XmNitemCount, TexDict->numTextures, XmNitems, str_tbl, XmNtopAttachment, XmATTACH_FORM, // XmNbottomAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_WIDGET, XmNbottomWidget, check, XmNleftAttachment, XmATTACH_FORM, NULL); for (i = 0; i < TexDict->numTextures; i++) XmStringFree(str_tbl[i]); XtFree((char *) str_tbl); XtManageChild(list); XtAddCallback(list, XmNbrowseSelectionCallback, list_cb, NULL); /* Image */ Image.width = 512; Image.height = 512; Image.ximage = CreateTrueColorImage(display, vis, 0, Image.width, Image.height); da = XmCreateDrawingArea(form, "da", NULL, 0); XtVaSetValues(da, XmNwidth, 256, XmNheight, 256, XmNtopAttachment, XmATTACH_FORM, XmNbottomAttachment, XmATTACH_FORM, XmNleftAttachment, XmATTACH_WIDGET, XmNleftWidget, list, XmNrightAttachment, XmATTACH_FORM, NULL); XtAddCallback(da, XmNexposeCallback, redraw, &Image); XtManageChild(da); XtVaSetValues(mainw, XmNworkWindow, form, NULL); XtRealizeWidget(toplevel); } void alpha_toggle_cb(Widget w, XtPointer client_data, XtPointer call_data) { XmToggleButtonCallbackStruct *cbs = (XmToggleButtonCallbackStruct *) call_data; if (cbs->set) ShowAlpha = 1; else ShowAlpha = 0; XtUnmanageChild(da); XtManageChild(da); LoadTex(); } void list_cb(Widget w, XtPointer client_data, XtPointer call_data) { XmListCallbackStruct *cbs = (XmListCallbackStruct *) call_data; TexIndex = cbs->item_position - 1; LoadTex(); } void file_cb(Widget w, XtPointer client_data, XtPointer call_data) { int item_no = (int) client_data; if (item_no == 0) printf("No close\n"); else if (item_no == 1) exit(0); } void help_cb(Widget w, XtPointer client_data, XtPointer call_data) { int item_no = (int) client_data; if (item_no == 0) { printf("No help\n"); } } void redraw(Widget w, XtPointer client_data, XtPointer call_data) { struct image *img = (struct image *) client_data; XmDrawingAreaCallbackStruct *cbs = (XmDrawingAreaCallbackStruct *) call_data; XEvent *event = cbs->event; Display *dpy = event->xany.display; XPutImage(dpy, XtWindow(w), DefaultGC(dpy, 0), img->ximage, 0, 0, 0, 0, img->width, img->height); } void quit_app(Widget w, XtPointer client_data, XtPointer call_data) { exit((int)client_data); }