JOGL v2.6.0-rc-20250706
JOGL, High-Performance Graphics Binding for Java™ (public API).
GLContextDrawableSwitchBase0.java
Go to the documentation of this file.
1/**
2 * Copyright 2013 JogAmp Community. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without modification, are
5 * permitted provided that the following conditions are met:
6 *
7 * 1. Redistributions of source code must retain the above copyright notice, this list of
8 * conditions and the following disclaimer.
9 *
10 * 2. Redistributions in binary form must reproduce the above copyright notice, this list
11 * of conditions and the following disclaimer in the documentation and/or other materials
12 * provided with the distribution.
13 *
14 * THIS SOFTWARE IS PROVIDED BY JogAmp Community ``AS IS'' AND ANY EXPRESS OR IMPLIED
15 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND
16 * FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL JogAmp Community OR
17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
18 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
19 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
20 * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
21 * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
22 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
23 *
24 * The views and conclusions contained in the software and documentation are those of the
25 * authors and should not be interpreted as representing official policies, either expressed
26 * or implied, of JogAmp Community.
27 */
28
29package com.jogamp.opengl.test.junit.jogl.acore.glels;
30
31import java.lang.reflect.InvocationTargetException;
32
33import com.jogamp.opengl.GLAutoDrawable;
34import com.jogamp.opengl.GLCapabilities;
35import com.jogamp.opengl.GLCapabilitiesImmutable;
36import com.jogamp.opengl.GLProfile;
37import com.jogamp.opengl.Threading;
38
39import com.jogamp.opengl.util.Animator;
40import com.jogamp.opengl.util.GLDrawableUtil;
41import com.jogamp.opengl.test.junit.jogl.demos.es2.GearsES2;
42import com.jogamp.opengl.test.junit.util.QuitAdapter;
43import com.jogamp.opengl.test.junit.util.UITestCase;
44
45import org.junit.BeforeClass;
46import org.junit.Test;
47import org.junit.FixMethodOrder;
48import org.junit.runners.MethodSorters;
49
50/**
51 * Test re-association (switching) of GLWindow /GLDrawables,
52 * from GLWindow/GLOffscreenAutoDrawable to an GLOffscreenAutoDrawable and back.
53 */
54@FixMethodOrder(MethodSorters.NAME_ASCENDING)
55public abstract class GLContextDrawableSwitchBase0 extends UITestCase {
56 static int width, height;
57 static boolean testEvenUnsafeSwapGLContext = false;
58
59 static GLCapabilities getCaps(final String profile) {
60 if( !GLProfile.isAvailable(profile) ) {
61 System.err.println("Profile "+profile+" n/a");
62 return null;
63 }
64 return new GLCapabilities(GLProfile.get(profile));
65 }
66
67 @BeforeClass
68 public static void initClass() {
69 width = 256;
70 height = 256;
71 }
72
73 public abstract GLAutoDrawable createGLAutoDrawable(final QuitAdapter quitAdapter, final GLCapabilitiesImmutable caps, final int width, final int height) throws InterruptedException, InvocationTargetException;
74 public abstract void destroyGLAutoDrawable(final GLAutoDrawable glad) throws InterruptedException, InvocationTargetException;
75
76 @Test(timeout=30000)
77 public void test01aSwitch2Onscreen2OnscreenGL2ES2_Def() throws InterruptedException, InvocationTargetException {
78 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
79 if(null == reqGLCaps) return;
80 testImpl(reqGLCaps, true);
81 }
82
83 @Test(timeout=30000)
84 public void test01bSwitch2Onscreen2OffscreenGL2ES2_Def() throws InterruptedException, InvocationTargetException {
85 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
86 if(null == reqGLCaps) return;
87 testImpl(reqGLCaps, false);
88 }
89
90 @Test(timeout=30000)
91 public void test01cSwitch2Offscreen2OffscreenGL2ES2_Def() throws InterruptedException, InvocationTargetException {
92 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
93 if(null == reqGLCaps) return;
94 reqGLCaps.setOnscreen(false);
95 testImpl(reqGLCaps, false);
96 }
97
98 @Test(timeout=30000)
99 public void test01dSwitch2Offscreen2OnscreenGL2ES2_Def() throws InterruptedException, InvocationTargetException {
100 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
101 if(null == reqGLCaps) return;
102 reqGLCaps.setOnscreen(false);
103 testImpl(reqGLCaps, true);
104 }
105
106 @Test(timeout=30000)
107 public void test02aSwitch2Onscreen2OnscreenGL2ES2_MSAA() throws InterruptedException, InvocationTargetException {
108 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
109 if(null == reqGLCaps) return;
110 reqGLCaps.setNumSamples(4);
111 reqGLCaps.setSampleBuffers(true);
112 testImpl(reqGLCaps, true);
113 }
114
115 @Test(timeout=30000)
116 public void test02bSwitch2Onscreen2OffscreenGL2ES2_MSAA() throws InterruptedException, InvocationTargetException {
117 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
118 if(null == reqGLCaps) return;
119 reqGLCaps.setNumSamples(4);
120 reqGLCaps.setSampleBuffers(true);
121 testImpl(reqGLCaps, false);
122 }
123
124 @Test(timeout=30000)
125 public void test02cSwitch2Offscreen2OffscreenGL2ES2_MSAA() throws InterruptedException, InvocationTargetException {
126 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
127 if(null == reqGLCaps) return;
128 reqGLCaps.setOnscreen(false);
129 reqGLCaps.setNumSamples(4);
130 reqGLCaps.setSampleBuffers(true);
131 testImpl(reqGLCaps, false);
132 }
133
134 @Test(timeout=30000)
135 public void test02dSwitch2Offscreen2OnscreenGL2ES2_MSAA() throws InterruptedException, InvocationTargetException {
136 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
137 if(null == reqGLCaps) return;
138 reqGLCaps.setOnscreen(false);
139 reqGLCaps.setNumSamples(4);
140 reqGLCaps.setSampleBuffers(true);
141 testImpl(reqGLCaps, true);
142 }
143
144 @Test(timeout=30000)
145 public void test03aSwitch2Onscreen2OnscreenGL2ES2_Accu() throws InterruptedException, InvocationTargetException {
146 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
147 if(null == reqGLCaps) return;
148 reqGLCaps.setAccumRedBits(1);
149 reqGLCaps.setAccumGreenBits(1);
150 reqGLCaps.setAccumBlueBits(1);
151 testImpl(reqGLCaps, true);
152 }
153
154 @Test(timeout=30000)
155 public void test03bSwitch2Onscreen2OffscreenGL2ES2_Accu() throws InterruptedException, InvocationTargetException {
156 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
157 if(null == reqGLCaps) return;
158 reqGLCaps.setAccumRedBits(1);
159 reqGLCaps.setAccumGreenBits(1);
160 reqGLCaps.setAccumBlueBits(1);
161 testImpl(reqGLCaps, false);
162 }
163
164 @Test(timeout=30000)
165 public void test03cSwitch2Offscreen2OffscreenGL2ES2_Accu() throws InterruptedException, InvocationTargetException {
166 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
167 if(null == reqGLCaps) return;
168 reqGLCaps.setOnscreen(false);
169 reqGLCaps.setAccumRedBits(1);
170 reqGLCaps.setAccumGreenBits(1);
171 reqGLCaps.setAccumBlueBits(1);
172 testImpl(reqGLCaps, false);
173 }
174
175 @Test(timeout=30000)
176 public void test03dSwitch2Offscreen2OnscreenGL2ES2_Accu() throws InterruptedException, InvocationTargetException {
177 final GLCapabilities reqGLCaps = getCaps(GLProfile.GL2ES2);
178 if(null == reqGLCaps) return;
179 reqGLCaps.setOnscreen(false);
180 reqGLCaps.setAccumRedBits(1);
181 reqGLCaps.setAccumGreenBits(1);
182 reqGLCaps.setAccumBlueBits(1);
183 testImpl(reqGLCaps, true);
184 }
185
186 private void testImpl(final GLCapabilitiesImmutable srcCapsRequested, final boolean dstOnscreen) throws InterruptedException, InvocationTargetException {
187 final QuitAdapter quitAdapter = new QuitAdapter();
188 final GLAutoDrawable gladSource = createGLAutoDrawable(quitAdapter, srcCapsRequested, width, height);
189
190 final GLCapabilitiesImmutable srcCapsChosen = gladSource.getChosenGLCapabilities();
191
192 final GLCapabilities dstCaps = (GLCapabilities) srcCapsChosen.cloneMutable();
193 dstCaps.setOnscreen(dstOnscreen);
194
195 final boolean isSwapGLContextSafe = GLDrawableUtil.isSwapGLContextSafe(srcCapsRequested, srcCapsChosen, dstCaps);
196 System.err.println("Source Caps Requested: "+srcCapsRequested);
197 System.err.println("Source Caps Chosen : "+srcCapsChosen);
198 System.err.println("Dest Caps Requested: "+dstCaps);
199 System.err.println("Is SwapGLContext safe: "+isSwapGLContextSafe);
200
201 if( !isSwapGLContextSafe && !testEvenUnsafeSwapGLContext ) {
202 System.err.println("Supressing unsafe tests ...");
203 destroyGLAutoDrawable(gladSource);
204 return;
205 }
206
207 final SnapshotGLEventListener snapshotGLEventListener = new SnapshotGLEventListener();
208 final GearsES2 gears = new GearsES2(1);
209 gears.setVerbose(false);
210 gladSource.addGLEventListener(gears);
211 gladSource.addGLEventListener(snapshotGLEventListener);
212 snapshotGLEventListener.setMakeSnapshot();
213
214 final Animator animator = new Animator();
215 animator.add(gladSource);
216 animator.start();
217
218 int s = 0;
219 final long t0 = System.currentTimeMillis();
220 long t1 = t0;
221
222 final GLAutoDrawable gladDest = createGLAutoDrawable(quitAdapter, dstCaps, width, height);
223 RuntimeException caught = null;
224 try {
225 while( !quitAdapter.shouldQuit() && ( t1 - t0 ) < duration ) {
226 if( ( t1 - t0 ) / period > s) {
227 s++;
228 System.err.println(s+" - switch - START "+ ( t1 - t0 ));
229
230 final Runnable switchAction = new Runnable() {
231 public void run() {
233 } };
234
235 // switch context _and_ the demo synchronously
236 if( gladSource.isThreadGLCapable() && gladDest.isThreadGLCapable() ) {
237 switchAction.run();
238 } else {
239 Threading.invokeOnOpenGLThread(true, switchAction);
240 }
241 snapshotGLEventListener.setMakeSnapshot();
242
243 System.err.println(s+" - switch - END "+ ( t1 - t0 ));
244 }
245 Thread.sleep(100);
246 t1 = System.currentTimeMillis();
247 }
248 } catch (final RuntimeException t) {
249 caught = t;
250 }
251
252 animator.stop();
253 destroyGLAutoDrawable(gladDest);
254 destroyGLAutoDrawable(gladSource);
255
256 if( null != caught ) {
257 throw caught;
258 }
259 }
260
261 // default timing for 2 switches
262 static long duration = 2900; // ms
263 static long period = 1000; // ms
264}
void setOnscreen(final boolean onscreen)
Sets whether the surface shall be on- or offscreen.
Specifies a set of OpenGL capabilities.
void setAccumRedBits(final int accumRedBits)
Sets the number of bits requested for the accumulation buffer's red component.
void setAccumGreenBits(final int accumGreenBits)
Sets the number of bits requested for the accumulation buffer's green component.
void setNumSamples(final int numSamples)
If sample buffers are enabled, indicates the number of buffers to be allocated.
void setAccumBlueBits(final int accumBlueBits)
Sets the number of bits requested for the accumulation buffer's blue component.
void setSampleBuffers(final boolean enable)
Defaults to false.
Specifies the the OpenGL profile.
Definition: GLProfile.java:77
static boolean isAvailable(final AbstractGraphicsDevice device, final String profile)
Returns the availability of a profile on a device.
Definition: GLProfile.java:305
static final String GL2ES2
The intersection of the desktop GL3, GL2 and embedded ES2 profile.
Definition: GLProfile.java:594
static GLProfile get(final AbstractGraphicsDevice device, String profile)
Returns a GLProfile object.
This API provides access to the threading model for the implementation of the classes in this package...
Definition: Threading.java:119
static final void invokeOnOpenGLThread(final boolean wait, final Runnable r)
Executes the passed Runnable on the single thread used for all OpenGL work in this com....
Definition: Threading.java:201
Test re-association (switching) of GLWindow /GLDrawables, from GLWindow/GLOffscreenAutoDrawable to an...
abstract GLAutoDrawable createGLAutoDrawable(final QuitAdapter quitAdapter, final GLCapabilitiesImmutable caps, final int width, final int height)
final synchronized void add(final GLAutoDrawable drawable)
Adds a drawable to this animator's list of rendering drawables.
final synchronized boolean start()
Starts this animator, if not running.
Definition: Animator.java:344
final synchronized boolean stop()
Stops this animator.
Definition: Animator.java:368
Providing utility functions dealing w/ GLDrawables, GLAutoDrawable and their GLEventListener.
static final void swapGLContextAndAllGLEventListener(final GLAutoDrawable a, final GLAutoDrawable b)
Swaps the GLContext and all GLEventListener between GLAutoDrawable a and b, while preserving it's ini...
static boolean isSwapGLContextSafe(final GLCapabilitiesImmutable requestedCaps, final GLCapabilitiesImmutable chosenCapsA, final GLCapabilitiesImmutable chosenCapsB)
Return a heuristic value whether switching the GLContext is safe between GLAutoDrawables,...
A higher-level abstraction than GLDrawable which supplies an event based mechanism (GLEventListener) ...
boolean isThreadGLCapable()
Indicates whether the current thread is capable of performing OpenGL-related work.
void addGLEventListener(GLEventListener listener)
Adds the given listener to the end of this drawable queue.
Specifies an immutable set of OpenGL capabilities.
GLCapabilitiesImmutable getChosenGLCapabilities()
Fetches the GLCapabilitiesImmutable corresponding to the chosen OpenGL capabilities (pixel format / v...