Merge remote branch 'origin/master' into pipe-video
[mesa.git] / src / gallium / targets / graw-xlib / graw_xlib.c
1 #include "pipe/p_compiler.h"
2 #include "pipe/p_context.h"
3 #include "pipe/p_screen.h"
4 #include "util/u_debug.h"
5 #include "util/u_memory.h"
6 #include "target-helpers/wrap_screen.h"
7 #include "target-helpers/inline_sw_helper.h"
8 #include "state_tracker/xlib_sw_winsys.h"
9 #include "state_tracker/graw.h"
10
11 #include <X11/Xlib.h>
12 #include <X11/Xlibint.h>
13 #include <X11/Xutil.h>
14 #include <stdio.h>
15
16 static struct {
17 Display *display;
18 void (*draw)(void);
19 } graw;
20
21
22 static struct pipe_screen *
23 graw_create_screen( void )
24 {
25 struct pipe_screen *screen = NULL;
26 struct sw_winsys *winsys = NULL;
27
28 /* Create the underlying winsys, which performs presents to Xlib
29 * drawables:
30 */
31 winsys = xlib_create_sw_winsys( graw.display );
32 if (winsys == NULL)
33 return NULL;
34
35 screen = sw_screen_create( winsys );
36
37 /* Inject any wrapping layers we want to here:
38 */
39 return gallium_wrap_screen( screen );
40 }
41
42
43 struct pipe_screen *
44 graw_create_window_and_screen( int x,
45 int y,
46 unsigned width,
47 unsigned height,
48 enum pipe_format format,
49 void **handle)
50 {
51 struct pipe_screen *screen = NULL;
52 struct xlib_drawable *xlib_handle = NULL;
53 XSetWindowAttributes attr;
54 Window root;
55 Window win = 0;
56 XVisualInfo templat, *visinfo = NULL;
57 unsigned mask;
58 int n;
59 int scrnum;
60
61 graw.display = XOpenDisplay(NULL);
62 if (graw.display == NULL)
63 return NULL;
64
65 scrnum = DefaultScreen( graw.display );
66 root = RootWindow( graw.display, scrnum );
67
68
69 if (format != PIPE_FORMAT_R8G8B8A8_UNORM)
70 goto fail;
71
72 if (graw.display == NULL)
73 goto fail;
74
75 xlib_handle = CALLOC_STRUCT(xlib_drawable);
76 if (xlib_handle == NULL)
77 goto fail;
78
79
80 mask = VisualScreenMask | VisualDepthMask | VisualClassMask;
81 templat.screen = DefaultScreen(graw.display);
82 templat.depth = 32;
83 templat.class = TrueColor;
84
85 visinfo = XGetVisualInfo(graw.display, mask, &templat, &n);
86 if (!visinfo) {
87 printf("Error: couldn't get an RGB, Double-buffered visual\n");
88 exit(1);
89 }
90
91 /* window attributes */
92 attr.background_pixel = 0;
93 attr.border_pixel = 0;
94 attr.colormap = XCreateColormap( graw.display, root, visinfo->visual, AllocNone);
95 attr.event_mask = StructureNotifyMask | ExposureMask | KeyPressMask;
96 /* XXX this is a bad way to get a borderless window! */
97 mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
98
99 win = XCreateWindow( graw.display, root, x, y, width, height,
100 0, visinfo->depth, InputOutput,
101 visinfo->visual, mask, &attr );
102
103
104 /* set hints and properties */
105 {
106 char *name = NULL;
107 XSizeHints sizehints;
108 sizehints.x = x;
109 sizehints.y = y;
110 sizehints.width = width;
111 sizehints.height = height;
112 sizehints.flags = USSize | USPosition;
113 XSetNormalHints(graw.display, win, &sizehints);
114 XSetStandardProperties(graw.display, win, name, name,
115 None, (char **)NULL, 0, &sizehints);
116 }
117
118 XMapWindow(graw.display, win);
119 while (1) {
120 XEvent e;
121 XNextEvent( graw.display, &e );
122 if (e.type == MapNotify && e.xmap.window == win) {
123 break;
124 }
125 }
126
127 xlib_handle->visual = visinfo->visual;
128 xlib_handle->drawable = (Drawable)win;
129 xlib_handle->depth = visinfo->depth;
130 *handle = (void *)xlib_handle;
131
132 screen = graw_create_screen();
133 if (screen == NULL)
134 goto fail;
135
136 XFree(visinfo);
137 return screen;
138
139 fail:
140 if (screen)
141 screen->destroy(screen);
142
143 if (xlib_handle)
144 FREE(xlib_handle);
145
146 if (visinfo)
147 XFree(visinfo);
148
149 if (win)
150 XDestroyWindow(graw.display, win);
151
152 return NULL;
153 }
154
155
156 void
157 graw_set_display_func( void (*draw)( void ) )
158 {
159 graw.draw = draw;
160 }
161
162 void
163 graw_main_loop( void )
164 {
165 int i;
166 for (i = 0; i < 10; i++) {
167 graw.draw();
168 sleep(1);
169 }
170 }
171