diff --git a/src/main.c b/src/main.c index cd4026b5..6c1f62be 100644 --- a/src/main.c +++ b/src/main.c @@ -200,10 +200,8 @@ void Display_syntax(void) } fputs(modes, stdout); -#if defined(WIN32) - MessageBoxA(GFX2_Get_Window_Handle(), syntax, "GrafX2", MB_OK); - MessageBoxA(GFX2_Get_Window_Handle(), modes, "GrafX2", MB_OK); -#endif + GFX2_MessageBox(syntax, "GrafX2", GFX2_MB_INFO); + GFX2_MessageBox(modes, "GrafX2", GFX2_MB_INFO); } // ---------------------------- Sortie impromptue ---------------------------- @@ -281,12 +279,10 @@ void Error_function(int error_code, const char *filename, int line_number, const if(msg != NULL) { fputs(msg, stderr); -#if defined(WIN32) -#if defined(_DEBUG) +#if defined(WIN32) && defined(_DEBUG) OutputDebugStringA(msg); #endif - MessageBoxA(GFX2_Get_Window_Handle(), msg, "GrafX2 error", MB_OK | MB_ICONERROR); -#endif + GFX2_MessageBox(msg, "GrafX2 error", GFX2_MB_ERROR); } if (error_code == ERROR_COMMAND_LINE) diff --git a/src/screen.h b/src/screen.h index 34f82c27..8b3ef9dd 100644 --- a/src/screen.h +++ b/src/screen.h @@ -94,4 +94,23 @@ void Set_mouse_position(void); */ int GFX2_GetScreenSize(int * width, int * height); +#if defined(USE_SDL2) +#define GFX2_MB_INFO SDL_MESSAGEBOX_INFORMATION +#define GFX2_MB_ERROR SDL_MESSAGEBOX_ERROR +#define GFX2_MB_WARNING SDL_MESSAGEBOX_WARNING +#elif defined(WIN32) +#define GFX2_MB_INFO MB_OK +#define GFX2_MB_ERROR (MB_OK|MB_ICONERROR) +#define GFX2_MB_WARNING (MB_OK|MB_ICONWARNING) +#else +#define GFX2_MB_INFO 1 +#define GFX2_MB_ERROR 2 +#define GFX2_MB_WARNING 3 +#endif + +/** + * Display a modal message + */ +int GFX2_MessageBox(const char * text, const char * caption, unsigned int type); + #endif // SCREEN_H_INCLUDED diff --git a/src/sdlscreen.c b/src/sdlscreen.c index e07d7c98..bf4537d0 100644 --- a/src/sdlscreen.c +++ b/src/sdlscreen.c @@ -796,3 +796,13 @@ void Set_mouse_position(void) SDL_WarpMouseInWindow(NULL, Mouse_X*Pixel_width, Mouse_Y*Pixel_height); #endif } + +int GFX2_MessageBox(const char * text, const char * caption, unsigned int type) +{ +#if defined(USE_SDL2) + return SDL_ShowSimpleMessageBox(type, caption, text, Window_SDL); +#elif defined(WIN32) + return MessageBoxA(GFX2_Get_Window_Handle(), text, caption, type); +#endif +// TODO : display for MacOS : http://blog.jorgearimany.com/2010/05/messagebox-from-windows-to-mac.html +} diff --git a/src/win32screen.c b/src/win32screen.c index bc730d48..99724ea7 100644 --- a/src/win32screen.c +++ b/src/win32screen.c @@ -704,3 +704,8 @@ int GFX2_GetScreenSize(int * width, int * height) return (*width > 0 && *height > 0); } + +int GFX2_MessageBox(const char * text, const char * caption, unsigned int type) +{ + return MessageBoxA(GFX2_Get_Window_Handle(), text, caption, type); +} diff --git a/src/x11screen.c b/src/x11screen.c index 8f21e042..2fbbcc29 100644 --- a/src/x11screen.c +++ b/src/x11screen.c @@ -342,3 +342,123 @@ void Set_mouse_position(void) 0, 0, 0, 0, Mouse_X * Pixel_width, Mouse_Y * Pixel_height); } + +int GFX2_MessageBox(const char * text, const char * caption, unsigned int type) +{ + const char * p; + const char * lf; + int line_count = 0; + int s; + Window win, parent; + GC gc; + int quit = 0; + Atom wmDelete, atoms[2]; + char * atom_name; + + if (X11_display == NULL) + X11_display = XOpenDisplay(NULL);// NULL is equivalent to getenv("DISPLAY") + if (X11_display == NULL) + { + GFX2_Log(GFX2_ERROR, "X11: cannot open display\n"); + return 0; + } + for (p = text; p != NULL; p = strchr(p, '\n')) + { + p++; + line_count++; + } + GFX2_Log(GFX2_DEBUG, "GFX2_MessageBox() text line_count = %d\n", line_count); + s = DefaultScreen(X11_display); + parent = X11_window ? X11_window : RootWindow(X11_display, s); + win = XCreateSimpleWindow(X11_display, parent, 0, 0, 480, line_count * 16, 1, + BlackPixel(X11_display, s), WhitePixel(X11_display, s)); + { + XSizeHints * hints = XAllocSizeHints(); + hints->min_width = hints->max_width = 480; + hints->min_height = hints->max_height = line_count * 16; + hints->flags = PMinSize | PMaxSize; + XSetWMNormalHints(X11_display, win, hints); + XFree(hints); + } + gc = XCreateGC(X11_display, win, 0, NULL); + XSelectInput(X11_display, win, ExposureMask | ButtonPressMask | ButtonReleaseMask | KeyPressMask | KeyReleaseMask); + wmDelete = XInternAtom(X11_display, "WM_DELETE_WINDOW", True); + XSetWMProtocols(X11_display, win, &wmDelete, 1); + atoms[0] = XInternAtom(X11_display, "_NET_WM_WINDOW_TYPE_DIALOG", False); + XChangeProperty(X11_display, win, XInternAtom(X11_display, "_NET_WM_WINDOW_TYPE", False), XA_ATOM, 32, PropModeReplace, (unsigned char *)atoms, 1); + atoms[0] = XInternAtom(X11_display, "_NET_WM_ACTION_MOVE", False); + atoms[1] = XInternAtom(X11_display, "_NET_WM_ACTION_CLOSE", False); + XChangeProperty(X11_display, win, XInternAtom(X11_display, "_NET_WM_ALLOWED_ACTIONS", False), XA_ATOM, 32, PropModeReplace, (unsigned char *)atoms, 2); + XMapWindow(X11_display, win); + XStoreName(X11_display, win, caption); + XFlush(X11_display); + + while (!quit) + { + XEvent e; + XNextEvent(X11_display, &e); + switch (e.type) + { + case KeyPress: + case ButtonPress: + break; + case KeyRelease: + { + KeySym sym; + sym = XkbKeycodeToKeysym(X11_display, e.xkey.keycode, 0, 0); + GFX2_Log(GFX2_DEBUG, "keyrelease code= %3d state=0x%08x sym = 0x%04lx %s\n", + e.xkey.keycode, e.xkey.state, sym, XKeysymToString(sym)); + if (sym == XK_Escape) + quit = 1; + } + break; + case ButtonRelease: + quit = 1; + break; + case Expose: + { + int len; + int y = 16; + // print text + for (p = text; p != NULL; p = lf) + { + int x = 0; + while (*p == '\t') + { + p++; + x += 32; + } + lf = strchr(p, '\n'); + if (lf == NULL) + len = (int)strlen(p); + else + { + len = (int)(lf - p); + lf++; + } + XDrawString(X11_display, win, gc, x, y, p, len); + y += 16; + } + } + break; + case ClientMessage: + atom_name = XGetAtomName(X11_display, e.xclient.message_type); + GFX2_Log(GFX2_DEBUG, "ClientMessage type %s\n", atom_name); + XFree(atom_name); + if (e.xclient.message_type == XInternAtom(X11_display, "WM_PROTOCOLS", False)) + { + atom_name = XGetAtomName(X11_display, (Atom)e.xclient.data.l[0]); + GFX2_Log(GFX2_DEBUG, " l[0] = %s\n", atom_name); + XFree(atom_name); + if ((Atom)e.xclient.data.l[0] == wmDelete) + quit = 1; + } + break; + default: + GFX2_Log(GFX2_DEBUG, "X11 event type %d\n", e.type); + } + } + XFreeGC(X11_display, gc); + XDestroyWindow(X11_display, win); + return 1; +}