2013-05-15 16:06:53 +00:00
/*
2013-06-15 11:37:22 +00:00
* This file is subject to the terms of the GFX License . If a copy of
2013-05-15 16:06:53 +00:00
* the license was not distributed with this file , you can obtain one at :
*
2013-07-21 20:20:37 +00:00
* http : //ugfx.org/license.html
2013-05-15 16:06:53 +00:00
*/
2015-02-20 23:23:33 +00:00
// We need to include stdio.h below. Turn off GFILE_NEED_STDIO just for this file to prevent conflicts
# define GFILE_NEED_STDIO_MUST_BE_OFF
2013-05-15 16:06:53 +00:00
# include "gfx.h"
# if GFX_USE_GDISP
2015-01-08 09:53:28 +00:00
# include <X11/Xlib.h>
# include <X11/Xutil.h>
# include <X11/Xresource.h>
# include <stdio.h>
# include <stdlib.h>
# define GDISP_DRIVER_VMT GDISPVMT_X11
2014-09-26 07:29:31 +00:00
# include "gdisp_lld_config.h"
2015-11-21 09:27:08 +00:00
# include "../../../src/gdisp/gdisp_driver.h"
2013-09-29 14:05:07 +00:00
2015-01-08 09:53:28 +00:00
// Configuration parameters for this driver
2014-09-26 07:29:31 +00:00
# ifndef GDISP_FORCE_24BIT
2018-02-27 07:44:21 +00:00
# define GDISP_FORCE_24BIT GFXOFF
2015-01-08 09:53:28 +00:00
# endif
# ifndef GDISP_SCREEN_WIDTH
# define GDISP_SCREEN_WIDTH 640
2013-05-15 16:06:53 +00:00
# endif
2013-09-29 14:05:07 +00:00
# ifndef GDISP_SCREEN_HEIGHT
2015-01-08 09:53:28 +00:00
# define GDISP_SCREEN_HEIGHT 480
2013-09-29 14:05:07 +00:00
# endif
2015-01-08 09:53:28 +00:00
# ifndef GKEYBOARD_X_NO_LAYOUT
/**
2018-02-27 07:44:21 +00:00
* Setting this to GFXON turns off the layout engine .
2015-01-08 09:53:28 +00:00
* In this situation " cooked " characters are returned but
* shift states etc are lost .
* As only a limited number of keyboard layouts are currently
* defined for X in uGFX ( currently none ) , setting this
2018-02-27 07:44:21 +00:00
* to GFXON enables the X keyboard mapping to be pass non - English
2015-01-08 09:53:28 +00:00
* characters to uGFX or to handle non - standard keyboard layouts at
* the expense of losing special function keys etc .
*/
2018-02-27 07:44:21 +00:00
// We set this to GFXON by default as currently the X layout code is not complete!
# define GKEYBOARD_X_NO_LAYOUT GFXON
2015-01-08 09:53:28 +00:00
# endif
# ifndef GKEYBOARD_X_DEFAULT_LAYOUT
# define GKEYBOARD_X_DEFAULT_LAYOUT KeyboardLayout_X_US
2013-09-29 14:05:07 +00:00
# endif
2015-01-08 09:53:28 +00:00
// Driver status flags
2013-10-12 12:38:12 +00:00
# define GDISP_FLG_READY (GDISP_FLG_DRIVER<<0)
2013-05-15 16:06:53 +00:00
# if GINPUT_NEED_MOUSE
2014-09-26 07:29:31 +00:00
// Include mouse support code
# define GMOUSE_DRIVER_VMT GMOUSEVMT_X11
2015-11-21 09:27:08 +00:00
# include "../../../src/ginput/ginput_driver_mouse.h"
2014-09-26 07:29:31 +00:00
// Forward definitions
2018-06-23 03:02:07 +00:00
static gBool XMouseInit ( GMouse * m , unsigned driverinstance ) ;
static gBool XMouseRead ( GMouse * m , GMouseReading * prd ) ;
2014-09-26 07:29:31 +00:00
const GMouseVMT const GMOUSE_DRIVER_VMT [ 1 ] = { {
{
GDRIVER_TYPE_MOUSE ,
GMOUSE_VFLG_NOPOLL | GMOUSE_VFLG_DYNAMICONLY ,
// Extra flags for testing only
//GMOUSE_VFLG_TOUCH|GMOUSE_VFLG_SELFROTATION|GMOUSE_VFLG_DEFAULTFINGER
//GMOUSE_VFLG_CALIBRATE|GMOUSE_VFLG_CAL_EXTREMES|GMOUSE_VFLG_CAL_TEST|GMOUSE_VFLG_CAL_LOADFREE
//GMOUSE_VFLG_ONLY_DOWN|GMOUSE_VFLG_POORUPDOWN
sizeof ( GMouse ) ,
_gmouseInitDriver , _gmousePostInitDriver , _gmouseDeInitDriver
} ,
1 , // z_max
0 , // z_min
1 , // z_touchon
0 , // z_touchoff
{ // pen_jitter
0 , // calibrate
0 , // click
0 // move
} ,
{ // finger_jitter
0 , // calibrate
2 , // click
2 // move
} ,
XMouseInit , // init
0 , // deinit
XMouseRead , // get
0 , // calsave
0 // calload
} } ;
2013-05-15 16:06:53 +00:00
# endif
2015-01-08 09:53:28 +00:00
# if GINPUT_NEED_KEYBOARD
// Include mouse support code
# define GKEYBOARD_DRIVER_VMT GKEYBOARDVMT_X
2015-11-21 09:27:08 +00:00
# include "../../../src/ginput/ginput_driver_keyboard.h"
2015-01-08 09:53:28 +00:00
# if !GKEYBOARD_X_NO_LAYOUT
# if GKEYBOARD_LAYOUT_OFF
2018-02-27 07:44:21 +00:00
# error "The X keyboard driver is using the layout engine. Please set GKEYBOARD_LAYOUT_OFF=GFXOFF or GKEYBOARD_X_NO_LAYOUT=GFXON."
2015-01-08 09:53:28 +00:00
# endif
// Forward definitions
extern uint8_t GKEYBOARD_X_DEFAULT_LAYOUT [ ] ;
2015-11-21 09:27:08 +00:00
# include "../../../src/ginput/ginput_keyboard_microcode.h"
2015-01-08 09:53:28 +00:00
# include <X11/keysym.h>
// This is the layout code for the English US keyboard.
// We make it public so that a user can switch to a different layout if required.
uint8_t KeyboardLayout_X_US [ ] = {
KMC_HEADERSTART , KMC_HEADER_ID1 , KMC_HEADER_ID2 , KMC_HEADER_VER_1 ,
// TODO
# error "The code to do keyboard layouts in X is not complete."
// Transient Shifters: SHIFT, CTRL, ALT, WINKEY
// Locking Shifters: CAPSLOCK, NUMLOCK and SCROLLLOCK
// Keyup, Repeat
// 0 - 9
// A - Z
// Number pad
// Symbols
// Special Keys
// Anything else
// EOF
KMC_RECORDSTART , 0
} ;
# elif !GKEYBOARD_LAYOUT_OFF
2017-06-30 09:43:51 +00:00
# if GFX_COMPILER_WARNING_TYPE == GFX_COMPILER_WARNING_DIRECT
2018-02-27 07:44:21 +00:00
# warning "The X keyboard driver is not using the layout engine. If no other keyboard is using it consider defining GKEYBOARD_LAYOUT_OFF=GFXON to save code size."
2017-06-30 09:43:51 +00:00
# elif GFX_COMPILER_WARNING_TYPE == GFX_COMPILER_WARNING_MACRO
2018-02-27 07:44:21 +00:00
COMPILER_WARNING ( " The X keyboard driver is not using the layout engine. If no other keyboard is using it consider defining GKEYBOARD_LAYOUT_OFF=GFXON to save code size. " )
2017-06-30 09:43:51 +00:00
# endif
2015-01-08 09:53:28 +00:00
# endif
// Forward definitions
2018-06-23 03:02:07 +00:00
static gBool XKeyboardInit ( GKeyboard * k , unsigned driverinstance ) ;
2015-01-08 09:53:28 +00:00
static int XKeyboardGetData ( GKeyboard * k , uint8_t * pch , int sz ) ;
const GKeyboardVMT const GKEYBOARD_DRIVER_VMT [ 1 ] = { {
{
GDRIVER_TYPE_KEYBOARD ,
GKEYBOARD_VFLG_NOPOLL , // GKEYBOARD_VFLG_DYNAMICONLY
sizeof ( GKeyboard ) ,
_gkeyboardInitDriver , _gkeyboardPostInitDriver , _gkeyboardDeInitDriver
} ,
// The default keyboard layout
# if GKEYBOARD_X_NO_LAYOUT
0 ,
# else
GKEYBOARD_X_DEFAULT_LAYOUT ,
# endif
XKeyboardInit , // init
0 , // deinit
XKeyboardGetData , // getdata
0 // putdata void (*putdata)(GKeyboard *k, char ch); Optional
} } ;
static int keypos ;
static uint8_t keybuffer [ 8 ] ;
static GKeyboard * keyboard ;
# endif
2013-05-15 16:06:53 +00:00
2018-06-23 03:02:07 +00:00
static gBool initdone ;
2013-10-12 12:38:12 +00:00
static Display * dis ;
static int scr ;
static XEvent evt ;
static Colormap cmap ;
static XVisualInfo vis ;
static XContext cxt ;
2014-09-29 06:00:17 +00:00
static Atom wmDelete ;
2013-05-15 16:06:53 +00:00
2013-10-12 12:38:12 +00:00
typedef struct xPriv {
Pixmap pix ;
GC gc ;
Window win ;
2014-09-26 07:29:31 +00:00
# if GINPUT_NEED_MOUSE
2018-07-08 00:54:19 +00:00
gCoord mousex , mousey ;
2014-09-26 07:29:31 +00:00
uint16_t buttons ;
GMouse * mouse ;
# endif
2013-10-12 12:38:12 +00:00
} xPriv ;
static void ProcessEvent ( GDisplay * g , xPriv * priv ) {
2013-05-15 16:06:53 +00:00
switch ( evt . type ) {
2013-10-12 12:38:12 +00:00
case MapNotify :
2015-01-08 09:53:28 +00:00
XSelectInput ( dis , evt . xmap . window ,
StructureNotifyMask | ExposureMask | ButtonPressMask | ButtonReleaseMask | PointerMotionMask | KeyPressMask | KeyReleaseMask | KeymapStateMask ) ;
2013-10-12 12:38:12 +00:00
g - > flags | = GDISP_FLG_READY ;
break ;
case UnmapNotify :
XCloseDisplay ( dis ) ;
exit ( 0 ) ;
break ;
2014-09-29 06:00:17 +00:00
case ClientMessage :
if ( ( Atom ) evt . xclient . data . l [ 0 ] = = wmDelete ) {
XCloseDisplay ( dis ) ;
exit ( 0 ) ;
}
break ;
2013-05-15 16:06:53 +00:00
case Expose :
2013-10-12 13:36:27 +00:00
XCopyArea ( dis , priv - > pix , evt . xexpose . window , priv - > gc ,
2013-05-15 16:06:53 +00:00
evt . xexpose . x , evt . xexpose . y ,
2014-09-26 07:29:31 +00:00
evt . xexpose . width , evt . xexpose . height ,
2013-05-15 16:06:53 +00:00
evt . xexpose . x , evt . xexpose . y ) ;
break ;
2015-01-08 09:53:28 +00:00
# if GINPUT_NEED_MOUSE
case ButtonPress :
priv - > mousex = evt . xbutton . x ;
priv - > mousey = evt . xbutton . y ;
switch ( evt . xbutton . button ) {
case 1 : priv - > buttons | = GINPUT_MOUSE_BTN_LEFT ; break ;
case 2 : priv - > buttons | = GINPUT_MOUSE_BTN_MIDDLE ; break ;
case 3 : priv - > buttons | = GINPUT_MOUSE_BTN_RIGHT ; break ;
case 4 : priv - > buttons | = GINPUT_MOUSE_BTN_4 ; break ;
}
_gmouseWakeup ( priv - > mouse ) ;
break ;
case ButtonRelease :
priv - > mousex = evt . xbutton . x ;
priv - > mousey = evt . xbutton . y ;
switch ( evt . xbutton . button ) {
case 1 : priv - > buttons & = ~ GINPUT_MOUSE_BTN_LEFT ; break ;
case 2 : priv - > buttons & = ~ GINPUT_MOUSE_BTN_MIDDLE ; break ;
case 3 : priv - > buttons & = ~ GINPUT_MOUSE_BTN_RIGHT ; break ;
case 4 : priv - > buttons & = ~ GINPUT_MOUSE_BTN_4 ; break ;
}
_gmouseWakeup ( priv - > mouse ) ;
break ;
case MotionNotify :
priv - > mousex = evt . xmotion . x ;
priv - > mousey = evt . xmotion . y ;
_gmouseWakeup ( priv - > mouse ) ;
break ;
# endif
# if GINPUT_NEED_KEYBOARD
case KeymapNotify :
XRefreshKeyboardMapping ( & evt . xmapping ) ;
break ;
case KeyPress :
# if !GKEYBOARD_X_NO_LAYOUT
// TODO
# error "The code to do keyboard layouts in X is not complete."
# endif
/* ignore these when there is no layout engine */
break ;
case KeyRelease :
# if !GKEYBOARD_X_NO_LAYOUT
// TODO
# error "The code to do keyboard layouts in X is not complete."
# endif
if ( keyboard & & ! keyboard - > pLayout & & keypos < ( int ) sizeof ( keybuffer ) ) {
int len ;
len = XLookupString ( & evt . xkey , ( char * ) ( keybuffer + keypos ) , sizeof ( keybuffer ) - keypos , /*&keysym*/ 0 , NULL ) ;
if ( len > 0 ) {
keypos + = len ;
_gkeyboardWakeup ( keyboard ) ;
}
}
break ;
# endif
2013-05-15 16:06:53 +00:00
}
}
/* this is the X11 thread which keeps track of all events */
2013-07-21 07:26:11 +00:00
static DECLARE_THREAD_STACK ( waXThread , 1024 ) ;
static DECLARE_THREAD_FUNCTION ( ThreadX , arg ) {
2013-10-12 12:38:12 +00:00
GDisplay * g ;
2013-07-21 07:26:11 +00:00
( void ) arg ;
while ( 1 ) {
gfxSleepMilliseconds ( 100 ) ;
while ( XPending ( dis ) ) {
XNextEvent ( dis , & evt ) ;
2013-10-12 13:36:27 +00:00
XFindContext ( evt . xany . display , evt . xany . window , cxt , ( XPointer * ) & g ) ;
2013-10-12 12:38:12 +00:00
ProcessEvent ( g , ( xPriv * ) g - > priv ) ;
2013-05-15 16:06:53 +00:00
}
}
2013-07-21 07:26:11 +00:00
return 0 ;
}
2014-09-26 07:29:31 +00:00
2013-05-15 16:06:53 +00:00
static int FatalXIOError ( Display * d ) {
( void ) d ;
/* The window has closed */
fprintf ( stderr , " GFX Window closed! \n " ) ;
exit ( 0 ) ;
}
2018-06-23 03:02:07 +00:00
LLDSPEC gBool gdisp_lld_init ( GDisplay * g ) {
2013-05-15 16:06:53 +00:00
XSizeHints * pSH ;
XSetWindowAttributes xa ;
XTextProperty WindowTitle ;
char * WindowTitleText ;
2013-10-12 12:38:12 +00:00
xPriv * priv ;
2013-05-15 16:06:53 +00:00
2013-10-12 12:38:12 +00:00
if ( ! initdone ) {
2018-07-08 05:40:27 +00:00
gThread hth ;
2013-05-15 16:06:53 +00:00
2018-06-23 03:02:07 +00:00
initdone = gTrue ;
2013-10-12 12:38:12 +00:00
# if GFX_USE_OS_LINUX || GFX_USE_OS_OSX
XInitThreads ( ) ;
# endif
2013-05-15 16:06:53 +00:00
2013-12-21 03:21:59 +00:00
dis = XOpenDisplay ( 0 ) ;
2013-10-12 12:38:12 +00:00
scr = DefaultScreen ( dis ) ;
cxt = XUniqueContext ( ) ;
2014-09-29 06:00:17 +00:00
wmDelete = XInternAtom ( dis , " WM_DELETE_WINDOW " , False ) ;
2013-10-12 12:38:12 +00:00
XSetIOErrorHandler ( FatalXIOError ) ;
# if GDISP_FORCE_24BIT
if ( ! XMatchVisualInfo ( dis , scr , 24 , TrueColor , & vis ) ) {
fprintf ( stderr , " Your display has no TrueColor mode \n " ) ;
XCloseDisplay ( dis ) ;
2018-06-23 03:02:07 +00:00
return gFalse ;
2013-10-12 12:38:12 +00:00
}
cmap = XCreateColormap ( dis , RootWindow ( dis , scr ) ,
vis . visual , AllocNone ) ;
# else
vis . visual = CopyFromParent ;
vis . depth = DefaultDepth ( dis , scr ) ;
cmap = DefaultColormap ( dis , scr ) ;
# endif
fprintf ( stderr , " Running GFX Window in %d bit color \n " , vis . depth ) ;
2018-07-08 05:32:26 +00:00
if ( ! ( hth = gfxThreadCreate ( waXThread , sizeof ( waXThread ) , gThreadpriorityHigh , ThreadX , 0 ) ) ) {
2013-10-12 12:38:12 +00:00
fprintf ( stderr , " Cannot start X Thread \n " ) ;
2013-05-15 16:06:53 +00:00
XCloseDisplay ( dis ) ;
2013-10-12 12:38:12 +00:00
exit ( 0 ) ;
2013-05-15 16:06:53 +00:00
}
2013-10-12 12:38:12 +00:00
# if GFX_USE_OS_LINUX || GFX_USE_OS_OSX
pthread_detach ( hth ) ;
# endif
gfxThreadClose ( hth ) ;
}
g - > priv = gfxAlloc ( sizeof ( xPriv ) ) ;
priv = ( xPriv * ) g - > priv ;
2013-10-21 05:13:10 +00:00
g - > board = 0 ; // No board interface for this driver
2013-05-15 16:06:53 +00:00
xa . colormap = cmap ;
xa . border_pixel = 0xFFFFFF ;
xa . background_pixel = 0x000000 ;
2014-09-26 07:29:31 +00:00
2013-10-12 12:38:12 +00:00
priv - > win = XCreateWindow ( dis , RootWindow ( dis , scr ) , 16 , 16 ,
2013-05-15 16:06:53 +00:00
GDISP_SCREEN_WIDTH , GDISP_SCREEN_HEIGHT ,
0 , vis . depth , InputOutput , vis . visual ,
CWBackPixel | CWColormap | CWBorderPixel , & xa ) ;
XSync ( dis , TRUE ) ;
2014-09-26 07:29:31 +00:00
2013-10-12 13:36:27 +00:00
XSaveContext ( dis , priv - > win , cxt , ( XPointer ) g ) ;
2014-09-29 06:00:17 +00:00
XSetWMProtocols ( dis , priv - > win , & wmDelete , 1 ) ;
2013-10-12 12:38:12 +00:00
{
char buf [ 132 ] ;
2013-10-19 05:36:05 +00:00
sprintf ( buf , " uGFX - %u " , g - > systemdisplay + 1 ) ;
2013-10-12 12:38:12 +00:00
WindowTitleText = buf ;
XStringListToTextProperty ( & WindowTitleText , 1 , & WindowTitle ) ;
2013-10-12 13:36:27 +00:00
XSetWMName ( dis , priv - > win , & WindowTitle ) ;
XSetWMIconName ( dis , priv - > win , & WindowTitle ) ;
2013-10-12 12:38:12 +00:00
XSync ( dis , TRUE ) ;
}
2014-09-26 07:29:31 +00:00
2013-05-15 16:06:53 +00:00
pSH = XAllocSizeHints ( ) ;
pSH - > flags = PSize | PMinSize | PMaxSize ;
pSH - > min_width = pSH - > max_width = pSH - > base_width = GDISP_SCREEN_WIDTH ;
pSH - > min_height = pSH - > max_height = pSH - > base_height = GDISP_SCREEN_HEIGHT ;
2013-10-12 13:36:27 +00:00
XSetWMNormalHints ( dis , priv - > win , pSH ) ;
2013-05-15 16:06:53 +00:00
XFree ( pSH ) ;
XSync ( dis , TRUE ) ;
2014-09-26 07:29:31 +00:00
2013-10-12 13:36:27 +00:00
priv - > pix = XCreatePixmap ( dis , priv - > win ,
2013-05-15 16:06:53 +00:00
GDISP_SCREEN_WIDTH , GDISP_SCREEN_HEIGHT , vis . depth ) ;
XSync ( dis , TRUE ) ;
2013-10-12 13:36:27 +00:00
priv - > gc = XCreateGC ( dis , priv - > win , 0 , 0 ) ;
XSetBackground ( dis , priv - > gc , BlackPixel ( dis , scr ) ) ;
2013-05-15 16:06:53 +00:00
XSync ( dis , TRUE ) ;
2014-09-29 05:59:37 +00:00
// Create the associated mouse before the map
# if GINPUT_NEED_MOUSE
priv - > mouse = ( GMouse * ) gdriverRegister ( ( const GDriverVMT const * ) GMOUSE_DRIVER_VMT , g ) ;
# endif
2013-10-12 13:36:27 +00:00
XSelectInput ( dis , priv - > win , StructureNotifyMask ) ;
XMapWindow ( dis , priv - > win ) ;
2013-05-15 16:06:53 +00:00
2013-10-12 12:38:12 +00:00
// Wait for the window creation to complete (for safety)
while ( ! ( ( ( volatile GDisplay * ) g ) - > flags & GDISP_FLG_READY ) )
gfxSleepMilliseconds ( 100 ) ;
2013-05-15 16:06:53 +00:00
2013-10-12 12:38:12 +00:00
/* Initialise the GDISP structure to match */
2018-07-08 03:51:20 +00:00
g - > g . Orientation = gOrientation0 ;
2018-07-08 01:47:36 +00:00
g - > g . Powermode = gPowerOn ;
2013-09-29 14:05:07 +00:00
g - > g . Backlight = 100 ;
g - > g . Contrast = 50 ;
g - > g . Width = GDISP_SCREEN_WIDTH ;
g - > g . Height = GDISP_SCREEN_HEIGHT ;
2014-09-26 07:29:31 +00:00
2018-06-23 03:02:07 +00:00
return gTrue ;
2013-05-15 16:06:53 +00:00
}
2013-10-12 13:36:27 +00:00
LLDSPEC void gdisp_lld_draw_pixel ( GDisplay * g )
2013-05-15 16:06:53 +00:00
{
2013-10-12 13:36:27 +00:00
xPriv * priv = ( xPriv * ) g - > priv ;
2013-05-15 16:06:53 +00:00
XColor col ;
2013-09-29 14:05:07 +00:00
col . red = RED_OF ( g - > p . color ) < < 8 ;
col . green = GREEN_OF ( g - > p . color ) < < 8 ;
col . blue = BLUE_OF ( g - > p . color ) < < 8 ;
2013-05-15 16:06:53 +00:00
XAllocColor ( dis , cmap , & col ) ;
2013-10-12 12:38:12 +00:00
XSetForeground ( dis , priv - > gc , col . pixel ) ;
XDrawPoint ( dis , priv - > pix , priv - > gc , ( int ) g - > p . x , ( int ) g - > p . y ) ;
XDrawPoint ( dis , priv - > win , priv - > gc , ( int ) g - > p . x , ( int ) g - > p . y ) ;
2013-05-15 16:06:53 +00:00
XFlush ( dis ) ;
}
2013-09-29 14:05:07 +00:00
# if GDISP_HARDWARE_FILLS
2013-10-12 13:36:27 +00:00
LLDSPEC void gdisp_lld_fill_area ( GDisplay * g ) {
xPriv * priv = ( xPriv * ) g - > priv ;
2013-09-29 14:05:07 +00:00
XColor col ;
col . red = RED_OF ( g - > p . color ) < < 8 ;
col . green = GREEN_OF ( g - > p . color ) < < 8 ;
col . blue = BLUE_OF ( g - > p . color ) < < 8 ;
XAllocColor ( dis , cmap , & col ) ;
2013-10-12 12:38:12 +00:00
XSetForeground ( dis , priv - > gc , col . pixel ) ;
XFillRectangle ( dis , priv - > pix , priv - > gc , g - > p . x , g - > p . y , g - > p . cx , g - > p . cy ) ;
XFillRectangle ( dis , priv - > win , priv - > gc , g - > p . x , g - > p . y , g - > p . cx , g - > p . cy ) ;
2013-09-29 14:05:07 +00:00
XFlush ( dis ) ;
}
# endif
#if 0 && GDISP_HARDWARE_BITFILLS
2013-10-12 13:36:27 +00:00
LLDSPEC void gdisp_lld_blit_area ( GDisplay * g ) {
2013-09-29 14:05:07 +00:00
// Start of Bitblit code
//XImage bitmap;
2018-07-08 01:08:55 +00:00
//gPixel *bits;
2013-09-29 14:05:07 +00:00
// bits = malloc(vis.depth * GDISP_SCREEN_WIDTH * GDISP_SCREEN_HEIGHT);
// bitmap = XCreateImage(dis, vis, vis.depth, ZPixmap,
// 0, bits, GDISP_SCREEN_WIDTH, GDISP_SCREEN_HEIGHT,
// 0, 0);
}
# endif
# if GDISP_HARDWARE_PIXELREAD
2018-07-08 01:19:43 +00:00
LLDSPEC gColor gdisp_lld_get_pixel_color ( GDisplay * g ) {
2013-10-12 13:36:27 +00:00
xPriv * priv = ( xPriv * ) g - > priv ;
2013-09-29 14:05:07 +00:00
XColor color ;
XImage * img ;
2013-05-15 16:06:53 +00:00
2013-10-12 12:38:12 +00:00
img = XGetImage ( dis , priv - > pix , g - > p . x , g - > p . y , 1 , 1 , AllPlanes , XYPixmap ) ;
2013-09-29 16:23:22 +00:00
color . pixel = XGetPixel ( img , 0 , 0 ) ;
2013-09-29 14:05:07 +00:00
XFree ( img ) ;
XQueryColor ( dis , cmap , & color ) ;
2013-09-29 16:23:22 +00:00
return RGB2COLOR ( color . red > > 8 , color . green > > 8 , color . blue > > 8 ) ;
2013-09-29 14:05:07 +00:00
}
# endif
# if GDISP_NEED_SCROLL && GDISP_HARDWARE_SCROLL
2013-10-12 13:36:27 +00:00
LLDSPEC void gdisp_lld_vertical_scroll ( GDisplay * g ) {
xPriv * priv = ( xPriv * ) g - > priv ;
2013-10-12 12:38:12 +00:00
2013-09-29 14:05:07 +00:00
if ( g - > p . y1 > 0 ) {
2013-10-12 12:38:12 +00:00
XCopyArea ( dis , priv - > pix , priv - > pix , priv - > gc , g - > p . x , g - > p . y + g - > p . y1 , g - > p . cx , g - > p . cy - g - > p . y1 , g - > p . x , g - > p . y ) ;
XCopyArea ( dis , priv - > pix , priv - > win , priv - > gc , g - > p . x , g - > p . y , g - > p . cx , g - > p . cy - g - > p . y1 , g - > p . x , g - > p . y ) ;
2013-09-29 14:05:07 +00:00
} else {
2013-10-12 12:38:12 +00:00
XCopyArea ( dis , priv - > pix , priv - > pix , priv - > gc , g - > p . x , g - > p . y , g - > p . cx , g - > p . cy + g - > p . y1 , g - > p . x , g - > p . y - g - > p . y1 ) ;
XCopyArea ( dis , priv - > pix , priv - > win , priv - > gc , g - > p . x , g - > p . y - g - > p . y1 , g - > p . cx , g - > p . cy + g - > p . y1 , g - > p . x , g - > p . y - g - > p . y1 ) ;
2013-09-29 14:05:07 +00:00
}
}
# endif
2013-05-15 16:06:53 +00:00
# if GINPUT_NEED_MOUSE
2018-06-23 03:02:07 +00:00
static gBool XMouseInit ( GMouse * m , unsigned driverinstance ) {
2014-09-26 07:29:31 +00:00
( void ) m ;
( void ) driverinstance ;
2018-06-23 03:02:07 +00:00
return gTrue ;
2014-09-26 07:29:31 +00:00
}
2018-06-23 03:02:07 +00:00
static gBool XMouseRead ( GMouse * m , GMouseReading * pt ) {
2014-09-26 07:29:31 +00:00
xPriv * priv ;
priv = m - > display - > priv ;
pt - > x = priv - > mousex ;
pt - > y = priv - > mousey ;
pt - > z = ( priv - > buttons & GINPUT_MOUSE_BTN_LEFT ) ? 1 : 0 ;
pt - > buttons = priv - > buttons ;
2018-06-23 03:02:07 +00:00
return gTrue ;
2013-05-15 16:06:53 +00:00
}
# endif /* GINPUT_NEED_MOUSE */
2015-01-08 09:53:28 +00:00
# if GINPUT_NEED_KEYBOARD
2018-06-23 03:02:07 +00:00
static gBool XKeyboardInit ( GKeyboard * k , unsigned driverinstance ) {
2015-01-08 09:53:28 +00:00
( void ) driverinstance ;
// Only one please
if ( keyboard )
2018-06-23 03:02:07 +00:00
return gFalse ;
2015-01-08 09:53:28 +00:00
keyboard = k ;
2018-06-23 03:02:07 +00:00
return gTrue ;
2015-01-08 09:53:28 +00:00
}
static int XKeyboardGetData ( GKeyboard * k , uint8_t * pch , int sz ) {
int i , j ;
( void ) k ;
if ( ! keypos )
return 0 ;
for ( i = 0 ; i < keypos & & i < sz ; i + + )
pch [ i ] = keybuffer [ i ] ;
keypos - = i ;
for ( j = 0 ; j < keypos ; j + + )
keybuffer [ j ] = keybuffer [ i + j ] ;
return i ;
}
# endif /* GINPUT_NEED_KEYBOARD */
2013-05-15 16:06:53 +00:00
# endif /* GFX_USE_GDISP */