]> git.cworth.org Git - apitrace/blob - glws_glx.cpp
Minor cleanup.
[apitrace] / glws_glx.cpp
1 /**************************************************************************
2  *
3  * Copyright 2011 Jose Fonseca
4  * All Rights Reserved.
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a copy
7  * of this software and associated documentation files (the "Software"), to deal
8  * in the Software without restriction, including without limitation the rights
9  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10  * copies of the Software, and to permit persons to whom the Software is
11  * furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included in
14  * all copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
22  * THE SOFTWARE.
23  *
24  **************************************************************************/
25
26 #include "glimports.hpp"
27 #include "glws.hpp"
28
29
30 namespace glws {
31
32
33 class GlxVisual : public Visual
34 {
35 public:
36     XVisualInfo *visinfo;
37
38     GlxVisual(XVisualInfo *vi) :
39         visinfo(vi)
40     {}
41
42     ~GlxVisual() {
43         XFree(visinfo);
44     }
45 };
46
47
48 class GlxDrawable : public Drawable
49 {
50 public:
51     Display *display;
52     Window window;
53
54     GlxDrawable(const Visual *vis, Display *dpy, Window win) :
55         Drawable(vis),
56         display(dpy), 
57         window(win)
58     {}
59
60     ~GlxDrawable() {
61         XDestroyWindow(display, window);
62     }
63     
64     void
65     resize(unsigned w, unsigned h) {
66         Drawable::resize(w, h);
67         XResizeWindow(display, window, w, h);
68     }
69
70     void swapBuffers(void) {
71         glXSwapBuffers(display, window);
72     }
73 };
74
75
76 class GlxContext : public Context
77 {
78 public:
79     Display *display;
80     GLXContext context;
81     
82     GlxContext(const Visual *vis, Display *dpy, GLXContext ctx) :
83         Context(vis),
84         display(dpy), 
85         context(ctx)
86     {}
87
88     ~GlxContext() {
89         glXDestroyContext(display, context);
90     }
91 };
92
93
94 class GlxWindowSystem : public WindowSystem
95 {
96 private:
97     Display *display;
98     int screen;
99
100 public:
101     GlxWindowSystem() {
102         display = XOpenDisplay(NULL);
103         screen = DefaultScreen(display);
104     }
105
106     ~GlxWindowSystem() {
107         XCloseDisplay(display);
108     }
109
110     Visual *
111     createVisual(bool doubleBuffer) {
112         int single_attribs[] = {
113             GLX_RGBA,
114             GLX_RED_SIZE, 1,
115             GLX_GREEN_SIZE, 1,
116             GLX_BLUE_SIZE, 1,
117             GLX_DEPTH_SIZE, 1,
118             None
119         };
120
121         int double_attribs[] = {
122             GLX_RGBA,
123             GLX_RED_SIZE, 1,
124             GLX_GREEN_SIZE, 1,
125             GLX_BLUE_SIZE, 1,
126             GLX_DOUBLEBUFFER,
127             GLX_DEPTH_SIZE, 1,
128             None
129         };
130
131         XVisualInfo *visinfo;
132         
133         visinfo = glXChooseVisual(display, screen, doubleBuffer ? double_attribs : single_attribs);
134
135         return new GlxVisual(visinfo);
136     }
137     
138     Drawable *
139     createDrawable(const Visual *visual)
140     {
141         XVisualInfo *visinfo = dynamic_cast<const GlxVisual *>(visual)->visinfo;
142
143         Window root = RootWindow(display, screen);
144
145         /* window attributes */
146         XSetWindowAttributes attr;
147         attr.background_pixel = 0;
148         attr.border_pixel = 0;
149         attr.colormap = XCreateColormap(display, root, visinfo->visual, AllocNone);
150         attr.event_mask = StructureNotifyMask | ExposureMask | KeyPressMask;
151         
152         unsigned long mask;
153         mask = CWBackPixel | CWBorderPixel | CWColormap | CWEventMask;
154
155         int x = 0, y = 0, width = 256, height = 256;
156
157         Window window = XCreateWindow(
158             display, root, 
159             x, y, width, height,
160             0, 
161             visinfo->depth, 
162             InputOutput,
163             visinfo->visual, 
164             mask, 
165             &attr);
166
167         XSizeHints sizehints;
168         sizehints.x = x;
169         sizehints.y = y;
170         sizehints.width  = width;
171         sizehints.height = height;
172         sizehints.flags = USSize | USPosition;
173         XSetNormalHints(display, window, &sizehints);
174         
175         const char *name = "glretrace";
176         XSetStandardProperties(
177             display, window, name, name,
178             None, (char **)NULL, 0, &sizehints);
179
180         XMapWindow(display, window);
181         
182         return new GlxDrawable(visual, display, window);
183     }
184
185     Context *
186     createContext(const Visual *visual)
187     {
188         XVisualInfo *visinfo = dynamic_cast<const GlxVisual *>(visual)->visinfo;
189         GLXContext context = glXCreateContext(display, visinfo, NULL, True);
190         return new GlxContext(visual, display, context);
191     }
192
193     bool
194     makeCurrent(Drawable *drawable, Context *context)
195     {
196         if (!drawable || !context) {
197             return glXMakeCurrent(display, NULL, NULL);
198         } else {
199             GlxDrawable *glxDrawable = dynamic_cast<GlxDrawable *>(drawable);
200             GlxContext *glxContext = dynamic_cast<GlxContext *>(context);
201
202             return glXMakeCurrent(display, glxDrawable->window, glxContext->context);
203         }
204     }
205
206     bool
207     processEvents(void) {
208         while (XPending(display) > 0) {
209             XEvent event;
210             XNextEvent(display, &event);
211             // TODO
212         }
213         return true;
214     }
215 };
216
217
218 WindowSystem *createNativeWindowSystem(void) {
219     return new GlxWindowSystem();
220 }
221
222
223 } /* namespace glretrace */