blob: af9b1bd8892969069ed3f47261c2bb445c376f1f [file] [log] [blame]
José Fonseca2403f682011-03-30 11:33:52 +01001/**************************************************************************
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/*
27 * Abstraction for GL window system specific APIs (GLX, WGL).
28 */
29
Jose Fonseca9653f952015-05-19 16:32:43 +010030#pragma once
José Fonseca2403f682011-03-30 11:33:52 +010031
32
José Fonsecae23365e2012-10-22 18:55:52 +010033#include <assert.h>
34
José Fonseca93f0e3f2011-10-09 16:16:18 +010035#include <vector>
José Fonsecad1c301f2012-10-18 15:22:41 +010036#include <string>
José Fonseca0396fa02015-01-05 16:20:08 +000037
Jose Fonseca9ed64622016-04-04 13:36:12 +010038#include "glfeatures.hpp"
José Fonseca93f0e3f2011-10-09 16:16:18 +010039
40
José Fonseca818d47d2011-04-02 20:22:17 +010041namespace glws {
José Fonseca2403f682011-03-30 11:33:52 +010042
43
Jose Fonseca9ed64622016-04-04 13:36:12 +010044using glfeatures::Profile;
José Fonseca65da8922015-01-05 14:27:14 +000045
Brian Paul974a1f22015-10-31 00:53:08 +000046class Drawable;
47
José Fonseca984010a2013-10-30 11:45:47 +000048
José Fonseca93f0e3f2011-10-09 16:16:18 +010049bool
50checkExtension(const char *extName, const char *extString);
51
Brian Paul14b02d42015-10-26 15:38:18 -060052// Extra info for creating PBuffers
53struct pbuffer_info
54{
55 int texFormat; // GL_RGB, GL_RGBA, or GL_NONE
56 int texTarget; // GL_TEXTURE_1D/2D/CUBE_MAP or GL_NONE
57 bool texMipmap; // 0 or 1 (false/true)
Brian Paul974a1f22015-10-31 00:53:08 +000058
59 Drawable *hdc_drawable; // Needed for WGL Pbuffers
Brian Paul14b02d42015-10-26 15:38:18 -060060};
61
José Fonseca93f0e3f2011-10-09 16:16:18 +010062
63template< class T >
64class Attributes {
65protected:
66 std::vector<T> attribs;
67
68public:
69 void add(T param) {
70 attribs.push_back(param);
71 }
72
73 void add(T pname, T pvalue) {
74 add(pname);
75 add(pvalue);
76 }
77
Chia-I Wuba226032011-11-07 14:45:20 -070078 void end(T terminator = 0) {
79 add(terminator);
José Fonseca93f0e3f2011-10-09 16:16:18 +010080 }
81
82 operator T * (void) {
83 return &attribs[0];
84 }
85
86 operator const T * (void) const {
87 return &attribs[0];
88 }
89};
90
91
José Fonseca30228ce2011-04-02 20:12:33 +010092class Visual
José Fonseca2403f682011-03-30 11:33:52 +010093{
José Fonseca30228ce2011-04-02 20:12:33 +010094public:
José Fonseca0d3dd0b2013-10-29 19:22:04 +000095 Profile profile;
96
97 /* TODO */
98#if 0
José Fonseca2403f682011-03-30 11:33:52 +010099 unsigned long redMask;
100 unsigned long greenMask;
101 unsigned long blueMask;
102 unsigned long alphaMask;
José Fonseca0d3dd0b2013-10-29 19:22:04 +0000103#endif
José Fonseca2403f682011-03-30 11:33:52 +0100104 bool doubleBuffer;
José Fonseca30228ce2011-04-02 20:12:33 +0100105
José Fonseca0d3dd0b2013-10-29 19:22:04 +0000106 Visual(Profile prof) :
107 profile(prof)
108 {}
109
José Fonseca30228ce2011-04-02 20:12:33 +0100110 virtual ~Visual() {}
José Fonseca2403f682011-03-30 11:33:52 +0100111};
112
113
José Fonseca30228ce2011-04-02 20:12:33 +0100114class Drawable
José Fonseca2403f682011-03-30 11:33:52 +0100115{
José Fonseca30228ce2011-04-02 20:12:33 +0100116public:
José Fonseca2403f682011-03-30 11:33:52 +0100117 const Visual *visual;
José Fonseca7497c132011-05-06 20:43:48 +0100118 int width;
119 int height;
José Fonsecae23365e2012-10-22 18:55:52 +0100120 bool pbuffer;
José Fonsecad3a6f152011-05-20 23:54:13 +0100121 bool visible;
José Fonseca30228ce2011-04-02 20:12:33 +0100122
Brian Paul14b02d42015-10-26 15:38:18 -0600123 // For WGL_ARB_render_texture
124 glws::pbuffer_info pbInfo;
125 int mipmapLevel, cubeFace;
126
José Fonsecae23365e2012-10-22 18:55:52 +0100127 Drawable(const Visual *vis, int w, int h, bool pb) :
José Fonseca7497c132011-05-06 20:43:48 +0100128 visual(vis),
129 width(w),
José Fonsecad3a6f152011-05-20 23:54:13 +0100130 height(h),
José Fonsecae23365e2012-10-22 18:55:52 +0100131 pbuffer(pb),
Brian Paul90b13792015-12-02 16:28:32 -0700132 visible(false),
133 mipmapLevel(0),
134 cubeFace(0)
José Fonseca30228ce2011-04-02 20:12:33 +0100135 {}
136
137 virtual ~Drawable() {}
138
139 virtual void
José Fonseca7497c132011-05-06 20:43:48 +0100140 resize(int w, int h) {
José Fonseca30228ce2011-04-02 20:12:33 +0100141 width = w;
142 height = h;
143 }
144
José Fonsecad3a6f152011-05-20 23:54:13 +0100145 virtual void
146 show(void) {
José Fonsecae23365e2012-10-22 18:55:52 +0100147 assert(!pbuffer);
José Fonsecad3a6f152011-05-20 23:54:13 +0100148 visible = true;
149 }
150
Alex Smith4b02e352016-10-25 10:31:16 +0100151 virtual void setName(const char *name) {}
152
José Fonseca3e899d72013-10-29 14:40:57 +0000153 virtual void copySubBuffer(int x, int y, int width, int height);
Carl Worth4dc3f3b2013-10-17 14:52:21 -0700154
José Fonseca30228ce2011-04-02 20:12:33 +0100155 virtual void swapBuffers(void) = 0;
156};
157
158
159class Context
160{
161public:
162 const Visual *visual;
Jose Fonseca6d7ddcc2015-08-25 22:05:36 +0100163
164 // Requested profile
José Fonsecae4d895b2011-11-28 21:48:58 +0000165 Profile profile;
Jose Fonseca6d7ddcc2015-08-25 22:05:36 +0100166
167 // Created profile
168 Profile actualProfile;
Jose Fonseca9ed64622016-04-04 13:36:12 +0100169 glfeatures::Extensions actualExtensions;
Jose Fonseca8d6653a2016-04-04 15:42:25 +0100170 glfeatures::Features actualFeatures;
José Fonsecad1c301f2012-10-18 15:22:41 +0100171
José Fonseca0d3dd0b2013-10-29 19:22:04 +0000172 Context(const Visual *vis) :
José Fonsecae4d895b2011-11-28 21:48:58 +0000173 visual(vis),
Jose Fonsecac87689f2015-06-27 12:49:02 +0100174 profile(vis->profile),
Jose Fonseca6d7ddcc2015-08-25 22:05:36 +0100175 actualProfile(profile),
Jose Fonsecac87689f2015-06-27 12:49:02 +0100176 initialized(false)
José Fonseca30228ce2011-04-02 20:12:33 +0100177 {}
178
179 virtual ~Context() {}
José Fonsecad1c301f2012-10-18 15:22:41 +0100180
Jose Fonsecac87689f2015-06-27 12:49:02 +0100181 // Context must have been made current once
182 inline bool
183 hasExtension(const char *extension) const {
184 assert(initialized);
Jose Fonseca6d7ddcc2015-08-25 22:05:36 +0100185 return actualExtensions.has(extension);
Jose Fonsecac87689f2015-06-27 12:49:02 +0100186 }
187
188private:
189 bool initialized;
190 void initialize(void);
191
192 friend bool makeCurrent(Drawable *, Context *);
Brian Paul57cb4c32016-10-06 10:56:40 -0600193 friend bool makeCurrent(Drawable *, Drawable *, Context *);
José Fonseca2403f682011-03-30 11:33:52 +0100194};
195
196
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100197void
198init(void);
José Fonseca2403f682011-03-30 11:33:52 +0100199
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100200void
201cleanup(void);
José Fonseca2403f682011-03-30 11:33:52 +0100202
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100203Visual *
José Fonsecaa04c50d2015-01-05 15:16:11 +0000204createVisual(bool doubleBuffer, unsigned samples, Profile profile);
José Fonseca2403f682011-03-30 11:33:52 +0100205
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100206Drawable *
Brian Paul14b02d42015-10-26 15:38:18 -0600207createDrawable(const Visual *visual, int width, int height,
208 const glws::pbuffer_info *pbInfo = NULL);
José Fonseca2403f682011-03-30 11:33:52 +0100209
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100210Context *
José Fonseca0d3dd0b2013-10-29 19:22:04 +0000211createContext(const Visual *visual, Context *shareContext = 0, bool debug = false);
José Fonseca2403f682011-03-30 11:33:52 +0100212
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100213bool
Brian Paul57cb4c32016-10-06 10:56:40 -0600214makeCurrentInternal(Drawable *drawable, Drawable *readable, Context *context);
Jose Fonsecac87689f2015-06-27 12:49:02 +0100215
216inline bool
Brian Paul57cb4c32016-10-06 10:56:40 -0600217makeCurrent(Drawable *drawable, Drawable *readable, Context *context)
Jose Fonsecac87689f2015-06-27 12:49:02 +0100218{
Brian Paul57cb4c32016-10-06 10:56:40 -0600219 bool success = makeCurrentInternal(drawable, readable, context);
Jose Fonsecac87689f2015-06-27 12:49:02 +0100220 if (success && context && !context->initialized) {
221 context->initialize();
222 }
223 return success;
224}
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100225
Brian Paul57cb4c32016-10-06 10:56:40 -0600226inline bool
227makeCurrent(Drawable *drawable, Context *context)
228{
229 return makeCurrent(drawable, drawable, context);
230}
231
José Fonseca9a0ed9c2011-10-09 10:36:44 +0100232bool
233processEvents(void);
José Fonseca2403f682011-03-30 11:33:52 +0100234
Brian Pauld01ec382015-10-26 15:45:29 -0600235// iBuffer is one of GL_FRONT/BACK_LEFT/RIGHT, GL_AUX0...
236bool
237bindTexImage(Drawable *pBuffer, int iBuffer);
238
239// iBuffer is one of GL_FRONT/BACK_LEFT/RIGHT, GL_AUX0...
240bool
241releaseTexImage(Drawable *pBuffer, int iBuffer);
242
243bool
244setPbufferAttrib(Drawable *pBuffer, const int *attribList);
245
José Fonseca2403f682011-03-30 11:33:52 +0100246
José Fonseca818d47d2011-04-02 20:22:17 +0100247} /* namespace glws */