Added support for OpenGL 3.0 functionality

Added support for OpenGL 3.0 context creation (MAJOR/MINOR versions, DEBUG mode, FORWARD_COMBATIBLE mode)
Added support for OpenGL 3.0 context sharing
Added support for OpenGL 3.0 extension detection
Improved support for floating point PixelFormats (ARB_color_buffer_float)
Added support for packed floating point PixelFormats (EXT_packed_float)
Added support for sRGB PixelFormats (ARB_framebuffer_sRGB)
Added support for pseudo-FORWARD_COMBATIBLE mode (deprecated functions not loaded)
Added support for EXT_direct_state_access
This commit is contained in:
Ioannis Tsakpinis 2008-08-19 16:46:03 +00:00
parent 0deaed34a5
commit d7ee23f9b2
73 changed files with 4235 additions and 817 deletions

View file

@ -56,11 +56,6 @@ public class BufferChecks {
private BufferChecks() {
}
/**
* Default buffer size for most buffer checks.
*/
private static final int DEFAULT_BUFFER_SIZE = 4;
/**
* Helper methods to ensure a function pointer is not-null (0)
*/
@ -129,7 +124,7 @@ public class BufferChecks {
private static void throwBufferSizeException(Buffer buf, int size) {
throw new IllegalArgumentException("Number of remaining buffer elements is " + buf.remaining() + ", must be at least " + size);
}
/**
* Helper method to ensure a buffer is big enough to receive data from a
* glGet* operation.

View file

@ -52,7 +52,7 @@ public final class NondirectBufferWrapper {
private final static int INITIAL_BUFFER_SIZE = 1;
private final static ThreadLocal thread_buffer = new ThreadLocal() {
protected final Object initialValue() {
protected Object initialValue() {
return new CachedBuffers(INITIAL_BUFFER_SIZE);
}
};

View file

@ -31,33 +31,29 @@
*/
package org.lwjgl.opengl;
import java.awt.Canvas;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Point;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
import org.lwjgl.Sys;
import java.awt.*;
import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;
import java.awt.event.HierarchyEvent;
import java.awt.event.HierarchyListener;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
import org.lwjgl.Sys;
/**
* <p>
* <p/>
* An AWT rendering context.
* <p>
* @version $Revision$
* <p/>
*
* @author $Author$
* $Id$
* $Id$
* @version $Revision$
*/
public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener, HierarchyListener {
private static final long serialVersionUID = 1L;
private final static AWTCanvasImplementation implementation;
private boolean update_context;
private Object SYNC_LOCK = new Object();
@ -67,7 +63,10 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
/** The drawable to share context with */
private final Drawable drawable;
/** The ContextAttribs to use when creating the context */
private final ContextAttribs attribs;
/** Context handle */
private PeerInfo peer_info;
private Context context;
@ -87,7 +86,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
}
static AWTCanvasImplementation createImplementation() {
switch (LWJGLUtil.getPlatform()) {
switch ( LWJGLUtil.getPlatform() ) {
case LWJGLUtil.PLATFORM_LINUX:
return new LinuxCanvasImplementation();
case LWJGLUtil.PLATFORM_WINDOWS:
@ -100,25 +99,21 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
}
private void setUpdate() {
synchronized(SYNC_LOCK) {
synchronized ( SYNC_LOCK ) {
update_context = true;
}
}
/**
* This method should only be called internally.
*/
/** This method should only be called internally. */
public Context getContext() {
return context;
}
/**
* Constructor using the default PixelFormat.
*/
/** Constructor using the default PixelFormat. */
public AWTGLCanvas() throws LWJGLException {
this(new PixelFormat());
}
/**
* Create an AWTGLCanvas with the requested PixelFormat on the default GraphicsDevice.
*
@ -131,7 +126,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
/**
* Create an AWTGLCanvas with the requested PixelFormat on the default GraphicsDevice.
*
* @param device the device to create the canvas on.
* @param device the device to create the canvas on.
* @param pixel_format The desired pixel format. May not be null
*/
public AWTGLCanvas(GraphicsDevice device, PixelFormat pixel_format) throws LWJGLException {
@ -141,94 +136,99 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
/**
* Create an AWTGLCanvas with the requested PixelFormat on the specified GraphicsDevice.
*
* @param device the device to create the canvas on.
* @param device the device to create the canvas on.
* @param pixel_format The desired pixel format. May not be null
* @param drawable The Drawable to share context with
* @param drawable The Drawable to share context with
*/
public AWTGLCanvas(GraphicsDevice device, PixelFormat pixel_format, Drawable drawable) throws LWJGLException {
this(device, pixel_format, drawable, null);
}
/**
* Create an AWTGLCanvas with the requested PixelFormat on the specified GraphicsDevice.
*
* @param device the device to create the canvas on.
* @param pixel_format The desired pixel format. May not be null
* @param drawable The Drawable to share context with
* @param attribs The ContextAttribs to use when creating the context. (optional, may be null)
*/
public AWTGLCanvas(GraphicsDevice device, PixelFormat pixel_format, Drawable drawable, ContextAttribs attribs) throws LWJGLException {
super(implementation.findConfiguration(device, pixel_format));
if (pixel_format == null)
if ( pixel_format == null )
throw new NullPointerException("Pixel format must be non-null");
addHierarchyListener(this);
addComponentListener(this);
this.drawable = drawable;
this.pixel_format = pixel_format;
this.attribs = attribs;
}
/* (non-Javadoc)
* @see java.awt.Canvas#addNotify()
*/
* @see java.awt.Canvas#addNotify()
*/
public void addNotify() {
super.addNotify();
}
/* (non-Javadoc)
* @see java.awt.Component#removeNotify()
*/
* @see java.awt.Component#removeNotify()
*/
public void removeNotify() {
synchronized (SYNC_LOCK) {
synchronized ( SYNC_LOCK ) {
destroyContext();
super.removeNotify();
}
}
/**
* Set swap interval.
*/
}
/** Set swap interval. */
public void setSwapInterval(int swap_interval) {
synchronized(SYNC_LOCK) {
if (context == null)
synchronized ( SYNC_LOCK ) {
if ( context == null )
throw new IllegalStateException("Canvas not yet displayable");
Context.setSwapInterval(swap_interval);
}
}
/**
* Enable vsync
*/
/** Enable vsync */
public void setVSyncEnabled(boolean enabled) {
setSwapInterval(enabled ? 1 : 0);
}
/**
* Swap the canvas' buffer
*/
/** Swap the canvas' buffer */
public void swapBuffers() throws LWJGLException {
synchronized(SYNC_LOCK) {
if (context == null)
synchronized ( SYNC_LOCK ) {
if ( context == null )
throw new IllegalStateException("Canvas not yet displayable");
Context.swapBuffers();
}
}
public void releaseContext() throws LWJGLException {
synchronized(SYNC_LOCK) {
if (context == null)
synchronized ( SYNC_LOCK ) {
if ( context == null )
throw new IllegalStateException("Canvas not yet displayable");
if (context.isCurrent())
if ( context.isCurrent() )
Context.releaseCurrentContext();
}
}
/**
* Make the canvas' context current. It is highly recommended that the context
* is only made current inside the AWT thread (for example in an overridden paintGL()).
*/
public void makeCurrent() throws LWJGLException {
synchronized(SYNC_LOCK) {
if (context == null)
synchronized ( SYNC_LOCK ) {
if ( context == null )
throw new IllegalStateException("Canvas not yet displayable");
context.makeCurrent();
}
}
/**
* Destroy the OpenGL context. This happens when the component becomes undisplayable
*/
/** Destroy the OpenGL context. This happens when the component becomes undisplayable */
private void destroyContext() {
synchronized(SYNC_LOCK) {
synchronized ( SYNC_LOCK ) {
try {
if (context != null) {
if ( context != null ) {
context.forceDestroy();
context = null;
reentry_count = 0;
@ -243,15 +243,13 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
/**
* Override this to do initialising of the context.
* It will be called once from paint(), immediately after
* It will be called once from paint(), immediately after
* the context is created and made current.
*/
protected void initGL() {
}
/**
* Override this to do painting
*/
/** Override this to do painting */
protected void paintGL() {
}
@ -261,36 +259,36 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
*/
public final void paint(Graphics g) {
LWJGLException exception = null;
synchronized (SYNC_LOCK) {
if (!isDisplayable())
synchronized ( SYNC_LOCK ) {
if ( !isDisplayable() )
return;
try {
if (peer_info == null) {
if ( peer_info == null ) {
this.peer_info = implementation.createPeerInfo(this, pixel_format);
}
peer_info.lockAndGetHandle();
try {
if (context == null) {
this.context = new Context(peer_info, drawable != null ? drawable.getContext() : null);
if ( context == null ) {
this.context = new Context(peer_info, attribs, drawable != null ? drawable.getContext() : null);
first_run = true;
}
if (reentry_count == 0)
if ( reentry_count == 0 )
context.makeCurrent();
reentry_count++;
try {
if (update_context) {
if ( update_context ) {
context.update();
update_context = false;
}
if (first_run) {
if ( first_run ) {
first_run = false;
initGL();
}
paintGL();
} finally {
reentry_count--;
if (reentry_count == 0)
if ( reentry_count == 0 )
Context.releaseCurrentContext();
}
} finally {
@ -300,7 +298,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
exception = e;
}
}
if (exception != null)
if ( exception != null )
exceptionOccurred(exception);
}
@ -314,9 +312,7 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
LWJGLUtil.log("Unhandled exception occurred, skipping paint(): " + exception);
}
/**
* override update to avoid clearing
*/
/** override update to avoid clearing */
public void update(Graphics g) {
paint(g);
}
@ -363,4 +359,5 @@ public class AWTGLCanvas extends Canvas implements Drawable, ComponentListener,
public void hierarchyChanged(HierarchyEvent e) {
setUpdate();
}
}
}

View file

@ -54,7 +54,7 @@ final class AWTSurfaceLock {
private boolean firstLockSucceeded = false;
public AWTSurfaceLock() {
AWTSurfaceLock() {
lock_buffer = createHandle();
}
@ -98,7 +98,7 @@ final class AWTSurfaceLock {
private static native boolean lockAndInitHandle(ByteBuffer lock_buffer, Canvas component) throws LWJGLException;
protected void unlock() throws LWJGLException {
void unlock() throws LWJGLException {
nUnlock(lock_buffer);
}

View file

@ -113,7 +113,7 @@ final class AWTUtil {
final GraphicsConfiguration config = component.getGraphicsConfiguration();
if (config != null) {
PointerInfo pointer_info = (PointerInfo)AccessController.doPrivileged(new PrivilegedExceptionAction() {
public final Object run() throws Exception {
public Object run() throws Exception {
return MouseInfo.getPointerInfo();
}
});

View file

@ -31,43 +31,44 @@
*/
package org.lwjgl.opengl;
import java.nio.ByteBuffer;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
import org.lwjgl.Sys;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
/**
* <p/>
* Context encapsulates an OpenGL context.
* <p/>
*
* <p/>
* This class is thread-safe.
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
final class Context {
/**
* The platform specific implementation of context methods
*/
/** The platform specific implementation of context methods */
private final static ContextImplementation implementation;
/** The current Context */
private final static ThreadLocal current_context_local = new ThreadLocal();
/**
* Handle to the native GL rendering context
*/
/** Handle to the native GL rendering context */
private final ByteBuffer handle;
private final PeerInfo peer_info;
private final IntBuffer attribList;
private final boolean forwardCombatible;
/** Whether the context has been destroyed */
private boolean destroyed;
private boolean destroy_requested;
/** The thread that has this context current, or null. */
private Thread thread;
@ -77,7 +78,7 @@ final class Context {
}
private static ContextImplementation createImplementation() {
switch (LWJGLUtil.getPlatform()) {
switch ( LWJGLUtil.getPlatform() ) {
case LWJGLUtil.PLATFORM_LINUX:
return new LinuxContextImplementation();
case LWJGLUtil.PLATFORM_WINDOWS:
@ -97,20 +98,26 @@ final class Context {
return (Context)current_context_local.get();
}
/**
* Create a context with the specified peer info and shared context
*/
public Context(PeerInfo peer_info, Context shared_context) throws LWJGLException {
/** Create a context with the specified peer info and shared context */
Context(PeerInfo peer_info, ContextAttribs attribs, Context shared_context) throws LWJGLException {
Context context_lock = shared_context != null ? shared_context : this;
// If shared_context is not null, synchronize on it to make sure it is not deleted
// If shared_context is not null, synchronize on it to make sure it is not deleted
// while this context is created. Otherwise, simply synchronize on ourself to avoid NPE
synchronized (context_lock) {
if (shared_context != null && shared_context.destroyed)
synchronized ( context_lock ) {
if ( shared_context != null && shared_context.destroyed )
throw new IllegalArgumentException("Shared context is destroyed");
GLContext.loadOpenGLLibrary();
try {
this.peer_info = peer_info;
this.handle = implementation.create(peer_info, shared_context != null ? shared_context.handle : null);
if ( attribs != null ) {
attribList = attribs.getAttribList();
forwardCombatible = attribs.isForwardCombatible();
} else {
attribList = null;
forwardCombatible = false;
}
this.handle = implementation.create(peer_info, attribList, shared_context != null ? shared_context.handle : null);
} catch (LWJGLException e) {
GLContext.unloadOpenGLLibrary();
throw e;
@ -118,16 +125,14 @@ final class Context {
}
}
/**
* Release the current context (if any). After this call, no context is current.
*/
/** Release the current context (if any). After this call, no context is current. */
public static void releaseCurrentContext() throws LWJGLException {
Context current_context = getCurrentContext();
if (current_context != null) {
if ( current_context != null ) {
implementation.releaseCurrentContext();
GLContext.useContext(null);
current_context_local.set(null);
synchronized (current_context) {
synchronized ( current_context ) {
current_context.thread = null;
current_context.checkDestroy();
}
@ -141,64 +146,56 @@ final class Context {
* on every releaseCurrentContext results in artifacts.
*/
public synchronized void releaseDrawable() throws LWJGLException {
if (destroyed)
if ( destroyed )
throw new IllegalStateException("Context is destroyed");
implementation.releaseDrawable(getHandle());
}
/**
* Update the context. Should be called whenever it's drawable is moved or resized
*/
/** Update the context. Should be called whenever it's drawable is moved or resized */
public synchronized void update() {
if (destroyed)
if ( destroyed )
throw new IllegalStateException("Context is destroyed");
implementation.update(getHandle());
}
/**
* Swap the buffers on the current context. Only valid for double-buffered contexts
*/
/** Swap the buffers on the current context. Only valid for double-buffered contexts */
public static void swapBuffers() throws LWJGLException {
implementation.swapBuffers();
}
private boolean canAccess() {
return thread == null || Thread.currentThread() == thread;
}
private void checkAccess() {
if (!canAccess())
if ( !canAccess() )
throw new IllegalStateException("From thread " + Thread.currentThread() + ": " + thread + " already has the context current");
}
/**
* Make the context current
*/
/** Make the context current */
public synchronized void makeCurrent() throws LWJGLException {
checkAccess();
if (destroyed)
if ( destroyed )
throw new IllegalStateException("Context is destroyed");
thread = Thread.currentThread();
current_context_local.set(this);
implementation.makeCurrent(peer_info, handle);
GLContext.useContext(this);
GLContext.useContext(this, forwardCombatible);
}
ByteBuffer getHandle() {
return handle;
}
/**
* Query whether the context is current
*/
/** Query whether the context is current */
public synchronized boolean isCurrent() throws LWJGLException {
if (destroyed)
if ( destroyed )
throw new IllegalStateException("Context is destroyed");
return implementation.isCurrent(handle);
}
private void checkDestroy() {
if (!destroyed && destroy_requested) {
if ( !destroyed && destroy_requested ) {
try {
releaseDrawable();
implementation.destroy(peer_info, handle);
@ -215,16 +212,13 @@ final class Context {
* Set the buffer swap interval. This call is a best-attempt at changing
* the monitor swap interval, which is the minimum periodicity of color buffer swaps,
* measured in video frame periods, and is not guaranteed to be successful.
*
* <p/>
* A video frame period is the time required to display a full frame of video data.
*
* @param sync true to synchronize; false to ignore synchronization
*/
public static void setSwapInterval(int value) {
implementation.setSwapInterval(value);
}
/**
* Destroy the context. This method behaves the same as destroy() with the extra
* requirement that the context must be either current to the current thread or not
@ -234,24 +228,25 @@ final class Context {
checkAccess();
destroy();
}
/**
* Request destruction of the Context. If the context is current, no context will be current after this call.
* The context is destroyed when no thread has it current.
*/
public synchronized void destroy() throws LWJGLException {
if (destroyed)
if ( destroyed )
return;
destroy_requested = true;
boolean was_current = isCurrent();
int error = GL11.GL_NO_ERROR;
if (was_current) {
if (GLContext.getCapabilities() != null && GLContext.getCapabilities().OpenGL11)
if ( was_current ) {
if ( GLContext.getCapabilities() != null && GLContext.getCapabilities().OpenGL11 )
error = GL11.glGetError();
releaseCurrentContext();
}
checkDestroy();
if (was_current && error != GL11.GL_NO_ERROR)
if ( was_current && error != GL11.GL_NO_ERROR )
throw new OpenGLException(error);
}
}
}

View file

@ -0,0 +1,213 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.opengl;
import org.lwjgl.BufferUtils;
import org.lwjgl.LWJGLUtil;
import java.nio.IntBuffer;
/**
* This class represents the context attributes passed to CreateContextAttribs of the XGL_create_context extension.
* These attributes can be used to indicate at context creation which OpenGL interface will be used. This includes the
* OpenGL version, the layer plane on which rendering takes place and also optional debug and forward combatibility modes.
* (read the XGL_create_context spec for details)
* <p/>
* Use of this class is optional. If an OpenGL context is created without passing an instance of this class
* (or XGL_create_context is not supported), the old context creation code will be used. Use of ContextAttribs is required
* to create an OpenGL 3.0 or newer context. Support for debug and forward compatible mobes is not guaranteed by the OpenGL
* implementation. Developers may encounter debug contexts being the same as non-debug contexts or forward combatible
* contexts having support for deprecated functionality.
* <p/>
* Warning: This functionality is currently available on the Windows platform only. However, if the forwardCombatible
* attribute is used, LWJGL will not load the deprecated functionality (as defined in the OpenGL 3.0 specification). This
* means that developers can start working on cleaning up their applications without an OpenGL 3.0 complaint driver.
*
* @author spasi <spasi@users.sourceforge.net>
*/
public abstract class ContextAttribs {
private int majorVersion;
private int minorVersion;
private int layerPlane;
private boolean debug;
private boolean forwardCombatible;
protected ContextAttribs(final int majorVersion, final int minorVersion) {
if ( majorVersion < 0 ||
3 < majorVersion ||
minorVersion < 0 ||
(majorVersion == 3 && 0 < minorVersion) ||
(majorVersion == 2 && 1 < minorVersion) ||
(majorVersion == 1 && 5 < minorVersion) )
throw new IllegalArgumentException("Invalid OpenGL version specified: " + majorVersion + '.' + minorVersion);
this.majorVersion = majorVersion;
this.minorVersion = minorVersion;
this.layerPlane = 0;
this.debug = false;
this.forwardCombatible = false;
}
protected ContextAttribs(final ContextAttribs attribs) {
this.majorVersion = attribs.majorVersion;
this.minorVersion = attribs.minorVersion;
this.layerPlane = attribs.layerPlane;
this.debug = attribs.debug;
this.forwardCombatible = attribs.forwardCombatible;
}
public static ContextAttribs create() {
return create(1, 0);
}
public static ContextAttribs create(final int majorVersion, final int minorVersion) {
switch ( LWJGLUtil.getPlatform() ) {
case LWJGLUtil.PLATFORM_LINUX:
return new LinuxContextAttribs(majorVersion, minorVersion);
case LWJGLUtil.PLATFORM_WINDOWS:
return new WindowsContextAttribs(majorVersion, minorVersion);
case LWJGLUtil.PLATFORM_MACOSX:
return new MacOSXContextAttribs(majorVersion, minorVersion);
default:
throw new IllegalStateException("Unsupported platform");
}
}
private static ContextAttribs create(final ContextAttribs attribs) {
switch ( LWJGLUtil.getPlatform() ) {
case LWJGLUtil.PLATFORM_LINUX:
return new LinuxContextAttribs(attribs);
case LWJGLUtil.PLATFORM_WINDOWS:
return new WindowsContextAttribs(attribs);
case LWJGLUtil.PLATFORM_MACOSX:
return new MacOSXContextAttribs(attribs);
default:
throw new IllegalStateException("Unsupported platform");
}
}
public final int getMajorVersion() {
return majorVersion;
}
public final int getMinorVersion() {
return minorVersion;
}
public final int getLayerPlane() {
return layerPlane;
}
public final boolean isDebug() {
return debug;
}
public final boolean isForwardCombatible() {
return forwardCombatible;
}
public final ContextAttribs withLayer(final int layerPlane) {
if ( layerPlane < 0 )
throw new IllegalArgumentException("Invalid layer plane specified: " + layerPlane);
final ContextAttribs attribs = create(this);
attribs.layerPlane = layerPlane;
return attribs;
}
public final ContextAttribs withDebug(final boolean debug) {
final ContextAttribs attribs = create(this);
attribs.debug = debug;
return attribs;
}
public final ContextAttribs withForwardCombatible(final boolean forwardCombatible) {
final ContextAttribs attribs = create(this);
attribs.forwardCombatible = forwardCombatible;
return attribs;
}
protected abstract int getMajorVersionAttrib();
protected abstract int getMinorVersionAttrib();
protected abstract int getLayerPlaneAttrib();
protected abstract int getFlagsAttrib();
protected abstract int getDebugBit();
protected abstract int getForwardCombatibleBit();
final IntBuffer getAttribList() {
int attribCount = 0;
if ( !(majorVersion == 1 && minorVersion == 0) )
attribCount += 2;
if ( 0 < layerPlane )
attribCount++;
int flags = 0;
if ( debug )
flags |= getDebugBit();
if ( forwardCombatible )
flags |= getForwardCombatibleBit();
if ( 0 < flags )
attribCount++;
if ( attribCount == 0 )
return null;
final IntBuffer attribs = BufferUtils.createIntBuffer((attribCount * 2) + 1);
if ( !(majorVersion == 1 && minorVersion == 0) ) {
attribs.put(getMajorVersionAttrib()).put(majorVersion);
attribs.put(getMinorVersionAttrib()).put(minorVersion);
}
if ( 0 < layerPlane )
attribs.put(getLayerPlaneAttrib()).put(layerPlane);
if ( 0 < flags )
attribs.put(getFlagsAttrib()).put(flags);
attribs.put(0);
attribs.rewind();
return attribs;
}
}

View file

@ -32,6 +32,7 @@
package org.lwjgl.opengl;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
import org.lwjgl.LWJGLException;
@ -48,42 +49,42 @@ interface ContextImplementation {
/**
* Create a context.
*/
public ByteBuffer create(PeerInfo peer_info, ByteBuffer shared_context_handle) throws LWJGLException;
ByteBuffer create(PeerInfo peer_info, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException;
/**
* Swap the buffers of the current context. Only valid for double-buffered contexts.
*/
public void swapBuffers() throws LWJGLException;
void swapBuffers() throws LWJGLException;
/**
* Release the context from its drawable, if any.
*/
public void releaseDrawable(ByteBuffer context_handle) throws LWJGLException;
void releaseDrawable(ByteBuffer context_handle) throws LWJGLException;
/**
* Release the current context (if any). After this call, no context is current.
*/
public void releaseCurrentContext() throws LWJGLException;
void releaseCurrentContext() throws LWJGLException;
/**
* Update the context. Should be called whenever it's drawable is moved or resized
*/
public void update(ByteBuffer context_handle);
void update(ByteBuffer context_handle);
/**
* Query whether the context is current
*/
public void makeCurrent(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException;
void makeCurrent(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException;
/**
* Query whether the context is current
*/
public boolean isCurrent(ByteBuffer handle) throws LWJGLException;
boolean isCurrent(ByteBuffer handle) throws LWJGLException;
public void setSwapInterval(int value);
void setSwapInterval(int value);
/**
* Destroys the Context.
*/
public void destroy(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException;
void destroy(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException;
}

View file

@ -43,17 +43,6 @@ package org.lwjgl.opengl;
* @author foo
*/
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.util.Arrays;
import java.util.HashSet;
import java.awt.Canvas;
import java.awt.event.ComponentListener;
import java.awt.event.ComponentAdapter;
import java.awt.event.ComponentEvent;
import org.lwjgl.BufferUtils;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
@ -62,12 +51,24 @@ import org.lwjgl.input.Controllers;
import org.lwjgl.input.Keyboard;
import org.lwjgl.input.Mouse;
import java.awt.*;
import java.awt.event.ComponentAdapter;
import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.util.Arrays;
import java.util.HashSet;
public final class Display {
private static final Thread shutdown_hook = new Thread() {
public void run() {
reset();
}
};
public void run() {
reset();
}
};
/** The display implementor */
private static final DisplayImplementation display_impl;
@ -86,7 +87,7 @@ public final class Display {
/** X coordinate of the window */
private static int x = -1;
/** Cached window icons, for when Display is recreated */
private static ByteBuffer[] cached_icons;
@ -117,8 +118,8 @@ public final class Display {
private static boolean parent_resized;
private static ComponentListener component_listener = new ComponentAdapter() {
public final void componentResized(ComponentEvent e) {
synchronized (GlobalLock.lock) {
public void componentResized(ComponentEvent e) {
synchronized ( GlobalLock.lock ) {
parent_resized = true;
}
}
@ -135,7 +136,7 @@ public final class Display {
}
drawable = new Drawable() {
public Context getContext() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return isCreated() ? context : null;
}
}
@ -152,7 +153,7 @@ public final class Display {
}
private static DisplayImplementation createDisplayImplementation() {
switch (LWJGLUtil.getPlatform()) {
switch ( LWJGLUtil.getPlatform() ) {
case LWJGLUtil.PLATFORM_LINUX:
return new LinuxDisplay();
case LWJGLUtil.PLATFORM_WINDOWS:
@ -164,9 +165,7 @@ public final class Display {
}
}
/**
* Only constructed by ourselves
*/
/** Only constructed by ourselves */
private Display() {
}
@ -176,7 +175,7 @@ public final class Display {
* given mode is not guaranteed to be available nor is it guaranteed to be within the
* current monitor specs (this is especially a problem with the frequency parameter).
* Furthermore, it is not guaranteed that create() will detect an illegal display mode.
*
* <p/>
* The only certain way to check
* is to call create() and make sure it works.
* Only non-palette-indexed modes are returned (ie. bpp will be 16, 24, or 32).
@ -186,10 +185,10 @@ public final class Display {
* @return an array of all display modes the system reckons it can handle.
*/
public static DisplayMode[] getAvailableDisplayModes() throws LWJGLException {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
DisplayMode[] unfilteredModes = display_impl.getAvailableDisplayModes();
if (unfilteredModes == null) {
if ( unfilteredModes == null ) {
return new DisplayMode[0];
}
@ -208,10 +207,11 @@ public final class Display {
/**
* Return the current display mode, as set by setDisplayMode().
*
* @return The current display mode
*/
public static DisplayMode getDisplayMode() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return current_mode;
}
}
@ -224,20 +224,21 @@ public final class Display {
* is also reset.
*
* @param mode The new display mode to set
*
* @throws LWJGLException if the display mode could not be set
*/
public static void setDisplayMode(DisplayMode mode) throws LWJGLException {
synchronized (GlobalLock.lock) {
if (mode == null)
synchronized ( GlobalLock.lock ) {
if ( mode == null )
throw new NullPointerException("mode must be non-null");
current_mode = mode;
if (isCreated()) {
if ( isCreated() ) {
destroyWindow();
// If mode is not fullscreen capable, make sure we are in windowed mode
if (!mode.isFullscreen())
if ( !mode.isFullscreen() )
resetFullscreen();
try {
if (fullscreen)
if ( fullscreen )
switchDisplayMode();
createWindow();
makeCurrentAndSetSwapInterval();
@ -256,9 +257,9 @@ public final class Display {
}
private static int getWindowX() {
if (!fullscreen && parent == null) {
if ( !fullscreen && parent == null ) {
// if no display location set, center window
if (x == -1) {
if ( x == -1 ) {
return Math.max(0, (initial_mode.getWidth() - current_mode.getWidth()) / 2);
} else {
return x;
@ -269,9 +270,9 @@ public final class Display {
}
private static int getWindowY() {
if (!fullscreen && parent == null) {
if ( !fullscreen && parent == null ) {
// if no display location set, center window
if (y == -1) {
if ( y == -1 ) {
return Math.max(0, (initial_mode.getHeight() - current_mode.getHeight()) / 2);
} else {
return y;
@ -286,24 +287,24 @@ public final class Display {
* A native context must exist, and it will be attached to the window.
*/
private static void createWindow() throws LWJGLException {
if (window_created) {
if ( window_created ) {
return;
}
Canvas tmp_parent = fullscreen ? null : parent;
if (tmp_parent != null && !tmp_parent.isDisplayable()) // Only a best effort check, since the parent can turn undisplayable hereafter
if ( tmp_parent != null && !tmp_parent.isDisplayable() ) // Only a best effort check, since the parent can turn undisplayable hereafter
throw new LWJGLException("Parent.isDisplayable() must be true");
if (tmp_parent != null) {
if ( tmp_parent != null ) {
tmp_parent.addComponentListener(component_listener);
}
DisplayMode mode = getEffectiveMode();
display_impl.createWindow(mode, fullscreen, tmp_parent, getWindowX(), getWindowY());
window_created = true;
setTitle(title);
initControls();
// set cached window icon if exists
if(cached_icons != null) {
if ( cached_icons != null ) {
setIcon(cached_icons);
} else {
setIcon(new ByteBuffer[] { LWJGLUtil.LWJGLIcon32x32, LWJGLUtil.LWJGLIcon16x16 });
@ -312,7 +313,7 @@ public final class Display {
private static void releaseDrawable() {
try {
if (context != null && context.isCurrent()) {
if ( context != null && context.isCurrent() ) {
Context.releaseCurrentContext();
context.releaseDrawable();
}
@ -322,19 +323,19 @@ public final class Display {
}
private static void destroyWindow() {
if (!window_created) {
if ( !window_created ) {
return;
}
if (parent != null) {
if ( parent != null ) {
parent.removeComponentListener(component_listener);
}
releaseDrawable();
// Automatically destroy keyboard & mouse
if (Mouse.isCreated()) {
if ( Mouse.isCreated() ) {
Mouse.destroy();
}
if (Keyboard.isCreated()) {
if ( Keyboard.isCreated() ) {
Keyboard.destroy();
}
display_impl.destroyWindow();
@ -342,7 +343,7 @@ public final class Display {
}
private static void switchDisplayMode() throws LWJGLException {
if (!current_mode.isFullscreen()) {
if ( !current_mode.isFullscreen() ) {
throw new IllegalStateException("Only modes acquired from getAvailableDisplayModes() can be used for fullscreen display");
}
display_impl.switchDisplayMode(current_mode);
@ -352,36 +353,36 @@ public final class Display {
* Set the display configuration to the specified gamma, brightness and contrast.
* The configuration changes will be reset when destroy() is called.
*
* @param gamma The gamma value
* @param gamma The gamma value
* @param brightness The brightness value between -1.0 and 1.0, inclusive
* @param contrast The contrast, larger than 0.0.
* @param contrast The contrast, larger than 0.0.
*/
public static void setDisplayConfiguration(float gamma, float brightness, float contrast) throws LWJGLException {
synchronized (GlobalLock.lock) {
if (!isCreated()) {
synchronized ( GlobalLock.lock ) {
if ( !isCreated() ) {
throw new LWJGLException("Display not yet created.");
}
if (brightness < -1.0f || brightness > 1.0f)
if ( brightness < -1.0f || brightness > 1.0f )
throw new IllegalArgumentException("Invalid brightness value");
if (contrast < 0.0f)
if ( contrast < 0.0f )
throw new IllegalArgumentException("Invalid contrast value");
int rampSize = display_impl.getGammaRampLength();
if (rampSize == 0) {
if ( rampSize == 0 ) {
throw new LWJGLException("Display configuration not supported");
}
FloatBuffer gammaRamp = BufferUtils.createFloatBuffer(rampSize);
for (int i = 0; i < rampSize; i++) {
float intensity = (float)i/(rampSize - 1);
for ( int i = 0; i < rampSize; i++ ) {
float intensity = (float)i / (rampSize - 1);
// apply gamma
float rampEntry = (float)java.lang.Math.pow(intensity, gamma);
// apply brightness
rampEntry += brightness;
// apply contrast
rampEntry = (rampEntry - 0.5f)*contrast + 0.5f;
rampEntry = (rampEntry - 0.5f) * contrast + 0.5f;
// Clamp entry to [0, 1]
if (rampEntry > 1.0f)
if ( rampEntry > 1.0f )
rampEntry = 1.0f;
else if (rampEntry < 0.0f)
else if ( rampEntry < 0.0f )
rampEntry = 0.0f;
gammaRamp.put(i, rampEntry);
}
@ -401,13 +402,13 @@ public final class Display {
long timeNow;
long gapTo;
long savedTimeLate;
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
gapTo = Sys.getTimerResolution() / fps + timeThen;
timeNow = Sys.getTime();
savedTimeLate = timeLate;
}
while (gapTo > timeNow + savedTimeLate) {
while ( gapTo > timeNow + savedTimeLate ) {
try {
Thread.sleep(1);
} catch (InterruptedException e) {
@ -415,8 +416,8 @@ public final class Display {
timeNow = Sys.getTime();
}
synchronized (GlobalLock.lock) {
if (gapTo < timeNow)
synchronized ( GlobalLock.lock ) {
if ( gapTo < timeNow )
timeLate = timeNow - gapTo;
else
timeLate = 0;
@ -425,29 +426,25 @@ public final class Display {
}
}
/**
* @return the title of the window
*/
/** @return the title of the window */
public static String getTitle() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return title;
}
}
private static void resetFullscreen() {
synchronized (GlobalLock.lock) {
if (Display.fullscreen) {
synchronized ( GlobalLock.lock ) {
if ( Display.fullscreen ) {
Display.fullscreen = false;
display_impl.resetDisplayMode();
}
}
}
/**
* Return the last parent set with setParent().
*/
/** Return the last parent set with setParent(). */
public static Canvas getParent() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return parent;
}
}
@ -461,17 +458,16 @@ public final class Display {
* and it is difficult to predict which AWT thread will process any given AWT event.<p>
* While the Display is in fullscreen mode, the current parent will be ignored. Additionally, when a non null parent is specified,
* the Dispaly will inherit the size of the parent, disregarding the currently set display mode.<p>
*
*/
public static void setParent(Canvas parent) throws LWJGLException {
synchronized (GlobalLock.lock) {
if (Display.parent != parent) {
synchronized ( GlobalLock.lock ) {
if ( Display.parent != parent ) {
Display.parent = parent;
if (!isCreated())
if ( !isCreated() )
return;
destroyWindow();
try {
if (fullscreen) {
if ( fullscreen ) {
switchDisplayMode();
} else {
display_impl.resetDisplayMode();
@ -496,18 +492,19 @@ public final class Display {
* mode returned by getDisplayMode(). The native cursor position is also reset.
*
* @param fullscreen Specify the fullscreen mode of the context.
*
* @throws LWJGLException If fullscreen is true, and the current DisplayMode instance is not
* from getAvailableDisplayModes() or if the mode switch fails.
* from getAvailableDisplayModes() or if the mode switch fails.
*/
public static void setFullscreen(boolean fullscreen) throws LWJGLException {
synchronized (GlobalLock.lock) {
if (Display.fullscreen != fullscreen) {
synchronized ( GlobalLock.lock ) {
if ( Display.fullscreen != fullscreen ) {
Display.fullscreen = fullscreen;
if (!isCreated())
if ( !isCreated() )
return;
destroyWindow();
try {
if (fullscreen) {
if ( fullscreen ) {
switchDisplayMode();
} else {
display_impl.resetDisplayMode();
@ -524,58 +521,51 @@ public final class Display {
}
}
/**
* @return whether the Display is in fullscreen mode
*/
/** @return whether the Display is in fullscreen mode */
public static boolean isFullscreen() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return fullscreen;
}
}
/**
* Set the title of the window. This may be ignored by the underlying OS.
*
* @param newTitle The new window title
*/
public static void setTitle(String newTitle) {
synchronized (GlobalLock.lock) {
if (newTitle == null) {
synchronized ( GlobalLock.lock ) {
if ( newTitle == null ) {
newTitle = "";
}
title = newTitle;
if (isCreated())
if ( isCreated() )
display_impl.setTitle(title);
}
}
/**
* @return true if the user or operating system has asked the window to close
*/
/** @return true if the user or operating system has asked the window to close */
public static boolean isCloseRequested() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Cannot determine close requested state of uncreated window");
return display_impl.isCloseRequested();
}
}
/**
* @return true if the window is visible, false if not
*/
/** @return true if the window is visible, false if not */
public static boolean isVisible() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Cannot determine minimized state of uncreated window");
return display_impl.isVisible();
}
}
/**
* @return true if window is active, that is, the foreground display of the operating system.
*/
/** @return true if window is active, that is, the foreground display of the operating system. */
public static boolean isActive() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Cannot determine focused state of uncreated window");
return display_impl.isActive();
}
@ -589,11 +579,11 @@ public final class Display {
* redraw when it returns true. The flag is cleared when update() or isDirty() is called.
*
* @return true if the window has been damaged by external changes
* and needs to repaint itself
* and needs to repaint itself
*/
public static boolean isDirty() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Cannot determine dirty state of uncreated window");
return display_impl.isDirty();
}
@ -605,8 +595,8 @@ public final class Display {
* this method if update() is called periodically.
*/
public static void processMessages() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Display not created");
display_impl.update();
@ -616,11 +606,12 @@ public final class Display {
/**
* Swap the display buffers. This method is called from update(), and should normally not be called by
* the application.
*
* @throws OpenGLException if an OpenGL error has occured since the last call to GL11.glGetError()
*/
public static void swapBuffers() throws LWJGLException {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Display not created");
Util.checkGLError();
@ -631,16 +622,17 @@ public final class Display {
/**
* Update the window. This calls processMessages(), and if the window is visible
* clears the dirty flag and calls swapBuffers() and finally polls the input devices.
*
* @throws OpenGLException if an OpenGL error has occured since the last call to GL11.glGetError()
*/
public static void update() {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Display not created");
processMessages();
// We paint only when the window is visible or dirty
if (display_impl.isVisible() || display_impl.isDirty()) {
if ( display_impl.isVisible() || display_impl.isDirty() ) {
try {
swapBuffers();
} catch (LWJGLException e) {
@ -649,7 +641,7 @@ public final class Display {
}
pollDevices();
if (parent_resized) {
if ( parent_resized ) {
reshape();
parent_resized = false;
}
@ -658,16 +650,16 @@ public final class Display {
static void pollDevices() {
// Poll the input devices while we're here
if (Mouse.isCreated()) {
if ( Mouse.isCreated() ) {
Mouse.poll();
Mouse.updateCursor();
}
if (Keyboard.isCreated()) {
if ( Keyboard.isCreated() ) {
Keyboard.poll();
}
if(Controllers.isCreated()) {
if ( Controllers.isCreated() ) {
Controllers.poll();
}
}
@ -678,62 +670,27 @@ public final class Display {
* @throws LWJGLException If the context could not be released
*/
public static void releaseContext() throws LWJGLException {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Display is not created");
if (context.isCurrent())
if ( context.isCurrent() )
Context.releaseCurrentContext();
}
}
/**
* Make the Display the current rendering context for GL calls.
*
* @throws LWJGLException If the context could not be made current
*/
public static void makeCurrent() throws LWJGLException {
synchronized (GlobalLock.lock) {
if (!isCreated())
synchronized ( GlobalLock.lock ) {
if ( !isCreated() )
throw new IllegalStateException("Display is not created");
context.makeCurrent();
}
}
/**
* Create the OpenGL context. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
*
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @throws LWJGLException
*/
public static void create() throws LWJGLException {
synchronized (GlobalLock.lock) {
create(new PixelFormat());
}
}
/**
* Create the OpenGL context with the given minimum parameters. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
*
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @param pixel_format Describes the minimum specifications the context must fulfill.
* @throws LWJGLException
*/
public static void create(PixelFormat pixel_format) throws LWJGLException {
synchronized (GlobalLock.lock) {
create(pixel_format, null);
}
}
private static void removeShutdownHook() {
AccessController.doPrivileged(new PrivilegedAction() {
public Object run() {
@ -752,35 +709,113 @@ public final class Display {
});
}
/**
* Create the OpenGL context. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
* <p/>
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @throws LWJGLException
*/
public static void create() throws LWJGLException {
synchronized ( GlobalLock.lock ) {
create(new PixelFormat());
}
}
/**
* Create the OpenGL context with the given minimum parameters. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
*
* <p/>
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @param pixel_format Describes the minimum specifications the context must fulfill.
* @param shared_drawable The Drawable to share context with or null.
*
* @throws LWJGLException
*/
public static void create(PixelFormat pixel_format) throws LWJGLException {
synchronized ( GlobalLock.lock ) {
create(pixel_format, null, null);
}
}
/**
* Create the OpenGL context with the given minimum parameters. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
* <p/>
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @param pixel_format Describes the minimum specifications the context must fulfill.
* @param shared_drawable The Drawable to share context with. (optional, may be null)
*
* @throws LWJGLException
*/
public static void create(PixelFormat pixel_format, Drawable shared_drawable) throws LWJGLException {
synchronized (GlobalLock.lock) {
if (isCreated())
synchronized ( GlobalLock.lock ) {
create(pixel_format, shared_drawable, null);
}
}
/**
* Create the OpenGL context with the given minimum parameters. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
* <p/>
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @param pixel_format Describes the minimum specifications the context must fulfill.
* @param attribs The ContextAttribs to use when creating the context. (optional, may be null)
*
* @throws LWJGLException
*/
public static void create(PixelFormat pixel_format, ContextAttribs attribs) throws LWJGLException {
synchronized ( GlobalLock.lock ) {
create(pixel_format, null, attribs);
}
}
/**
* Create the OpenGL context with the given minimum parameters. If isFullscreen() is true or if windowed
* context are not supported on the platform, the display mode will be switched to the mode returned by
* getDisplayMode(), and a fullscreen context will be created. If isFullscreen() is false, a windowed context
* will be created with the dimensions given in the mode returned by getDisplayMode(). If a context can't be
* created with the given parameters, a LWJGLException will be thrown.
* <p/>
* <p>The window created will be set up in orthographic 2D projection, with 1:1 pixel ratio with GL coordinates.
*
* @param pixel_format Describes the minimum specifications the context must fulfill.
* @param shared_drawable The Drawable to share context with. (optional, may be null)
* @param attribs The ContextAttribs to use when creating the context. (optional, may be null)
*
* @throws LWJGLException
*/
public static void create(PixelFormat pixel_format, Drawable shared_drawable, ContextAttribs attribs) throws LWJGLException {
synchronized ( GlobalLock.lock ) {
if ( isCreated() )
throw new IllegalStateException("Only one LWJGL context may be instantiated at any one time.");
if (pixel_format == null)
if ( pixel_format == null )
throw new NullPointerException("pixel_format cannot be null");
removeShutdownHook();
registerShutdownHook();
if (fullscreen)
if ( fullscreen )
switchDisplayMode();
try {
peer_info = display_impl.createPeerInfo(pixel_format);
try {
createWindow();
try {
context = new Context(peer_info, shared_drawable != null ? shared_drawable.getContext() : null);
context = new Context(peer_info, attribs, shared_drawable != null ? shared_drawable.getContext() : null);
try {
makeCurrentAndSetSwapInterval();
initContext();
@ -819,40 +854,38 @@ public final class Display {
return display_impl;
}
/**
* Gets a boolean property as a privileged action.
*/
/** Gets a boolean property as a privileged action. */
static boolean getPrivilegedBoolean(final String property_name) {
Boolean value = (Boolean)AccessController.doPrivileged(new PrivilegedAction() {
public Object run() {
public Object run() {
return new Boolean(Boolean.getBoolean(property_name));
}
});
return value.booleanValue();
}
private static void initControls() {
// Automatically create mouse, keyboard and controller
if (!getPrivilegedBoolean("org.lwjgl.opengl.Display.noinput")) {
if (!Mouse.isCreated() && !getPrivilegedBoolean("org.lwjgl.opengl.Display.nomouse")) {
if ( !getPrivilegedBoolean("org.lwjgl.opengl.Display.noinput") ) {
if ( !Mouse.isCreated() && !getPrivilegedBoolean("org.lwjgl.opengl.Display.nomouse") ) {
try {
Mouse.create();
} catch (LWJGLException e) {
if (LWJGLUtil.DEBUG) {
if ( LWJGLUtil.DEBUG ) {
e.printStackTrace(System.err);
} else {
LWJGLUtil.log("Failed to create Mouse: "+e);
LWJGLUtil.log("Failed to create Mouse: " + e);
}
}
}
if (!Keyboard.isCreated() && !getPrivilegedBoolean("org.lwjgl.opengl.Display.nokeyboard")) {
if ( !Keyboard.isCreated() && !getPrivilegedBoolean("org.lwjgl.opengl.Display.nokeyboard") ) {
try {
Keyboard.create();
} catch (LWJGLException e) {
if (LWJGLUtil.DEBUG) {
if ( LWJGLUtil.DEBUG ) {
e.printStackTrace(System.err);
} else {
LWJGLUtil.log("Failed to create Keyboard: "+e);
LWJGLUtil.log("Failed to create Keyboard: " + e);
}
}
}
@ -864,8 +897,8 @@ public final class Display {
* regardless of whether the Display was the current rendering context.
*/
public static void destroy() {
synchronized (GlobalLock.lock) {
if (!isCreated()) {
synchronized ( GlobalLock.lock ) {
if ( !isCreated() ) {
return;
}
@ -904,11 +937,9 @@ public final class Display {
current_mode = initial_mode;
}
/**
* @return true if the window's native peer has been created
*/
/** @return true if the window's native peer has been created */
public static boolean isCreated() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return window_created;
}
}
@ -917,27 +948,27 @@ public final class Display {
* Set the buffer swap interval. This call is a best-attempt at changing
* the monitor swap interval, which is the minimum periodicity of color buffer swaps,
* measured in video frame periods, and is not guaranteed to be successful.
*
* <p/>
* A video frame period is the time required to display a full frame of video data.
*
* @param value The swap interval in frames, 0 to disable
*/
public static void setSwapInterval(int value) {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
swap_interval = value;
if (isCreated())
if ( isCreated() )
Context.setSwapInterval(swap_interval);
}
}
/**
* Enable or disable vertical monitor synchronization. This call is a best-attempt at changing
* the vertical refresh synchronization of the monitor, and is not guaranteed to be successful.
*
* @param sync true to synchronize; false to ignore synchronization
*/
public static void setVSyncEnabled(boolean sync) {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
setSwapInterval(sync ? 1 : 0);
}
}
@ -948,12 +979,13 @@ public final class Display {
* to position the window such that it would extend off the screen, the window
* is simply placed as close to the edge as possible.
* <br><b>note</b>If no location has been specified (or x == y == -1) the window will be centered
*
* @param new_x The new window location on the x axis
* @param new_y The new window location on the y axis
*/
public static void setLocation(int new_x, int new_y) {
synchronized (GlobalLock.lock) {
if (fullscreen) {
synchronized ( GlobalLock.lock ) {
if ( fullscreen ) {
return;
}
@ -962,7 +994,7 @@ public final class Display {
y = new_y;
// offset if already created
if(isCreated()) {
if ( isCreated() ) {
reshape();
}
}
@ -976,10 +1008,11 @@ public final class Display {
/**
* Get the driver adapter string. This is a unique string describing the actual card's hardware, eg. "Geforce2", "PS2",
* "Radeon9700". If the adapter cannot be determined, this function returns null.
*
* @return a String
*/
public static String getAdapter() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return display_impl.getAdapter();
}
}
@ -987,14 +1020,14 @@ public final class Display {
/**
* Get the driver version. This is a vendor/adapter specific version string. If the version cannot be determined,
* this function returns null.
*
* @return a String
*/
public static String getVersion() {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
return display_impl.getVersion();
}
}
/**
* Sets one or more icons for the Display.
@ -1004,21 +1037,22 @@ public final class Display {
* <li>Mac OS X should be supplied one 128x128 icon</li>
* </ul>
* The implementation will use the supplied ByteBuffers with image data in RGBA and perform any conversions nescesarry for the specific platform.
* <p>
* <p/>
* <b>NOTE:</b> The display will make a deep copy of the supplied byte buffer array, for the purpose
* of recreating the icons when you go back and forth fullscreen mode. You therefore only need to
* of recreating the icons when you go back and forth fullscreen mode. You therefore only need to
* set the icon once per instance.
*
* @param icons Array of icons in RGBA mode. Pass the icons in order of preference.
*
* @return number of icons used, or 0 if display hasn't been created
*/
public static int setIcon(ByteBuffer[] icons) {
synchronized (GlobalLock.lock) {
synchronized ( GlobalLock.lock ) {
// make deep copy so we dont rely on the supplied buffers later on
// don't recache!
if(cached_icons != icons) {
if ( cached_icons != icons ) {
cached_icons = new ByteBuffer[icons.length];
for(int i=0;i<icons.length; i++) {
for ( int i = 0; i < icons.length; i++ ) {
cached_icons[i] = BufferUtils.createByteBuffer(icons[i].capacity());
int old_position = icons[i].position();
cached_icons[i].put(icons[i]);
@ -1027,7 +1061,7 @@ public final class Display {
}
}
if (Display.isCreated() && parent == null) {
if ( Display.isCreated() && parent == null ) {
return display_impl.setIcon(cached_icons);
} else {
return 0;

View file

@ -131,21 +131,21 @@ interface DisplayImplementation extends InputImplementation {
/**
* Method to test for buffer integrity
*/
public boolean isBufferLost(PeerInfo handle);
boolean isBufferLost(PeerInfo handle);
/**
* Method to create a Pbuffer
*/
public PeerInfo createPbuffer(int width, int height, PixelFormat pixel_format,
PeerInfo createPbuffer(int width, int height, PixelFormat pixel_format,
IntBuffer pixelFormatCaps,
IntBuffer pBufferAttribs) throws LWJGLException;
public void setPbufferAttrib(PeerInfo handle, int attrib, int value);
void setPbufferAttrib(PeerInfo handle, int attrib, int value);
public void bindTexImageToPbuffer(PeerInfo handle, int buffer);
void bindTexImageToPbuffer(PeerInfo handle, int buffer);
void releaseTexImageFromPbuffer(PeerInfo handle, int buffer);
public void releaseTexImageFromPbuffer(PeerInfo handle, int buffer);
/**
* Sets one or more icons for the Display.
* <ul>
@ -158,5 +158,5 @@ interface DisplayImplementation extends InputImplementation {
* @param icons Array of icons in RGBA mode
* @return number of icons used.
*/
public int setIcon(ByteBuffer[] icons);
int setIcon(ByteBuffer[] icons);
}

View file

@ -71,13 +71,19 @@ class GLChecks {
return scratch_buffer.get(0);
}
static int getNamedBufferObjectSize(ContextCapabilities caps, int buffer) {
IntBuffer scratch_buffer = caps.scratch_int_buffer;
EXTDirectStateAccess.glGetNamedBufferParameterEXT(buffer, GL15.GL_BUFFER_SIZE, scratch_buffer);
return scratch_buffer.get(0);
}
private static boolean checkBufferObject(ContextCapabilities caps, int buffer_enum, boolean state) {
IntBuffer scratch_buffer = caps.scratch_int_buffer;
GL11.glGetInteger(buffer_enum, scratch_buffer);
boolean is_enabled = scratch_buffer.get(0) != 0;
return state == is_enabled;
}
/** Helper method to ensure that array buffer objects are disabled. If they are enabled, we'll throw an OpenGLException */
static void ensureArrayVBOdisabled(ContextCapabilities caps) {
if(StateTracker.getReferencesStack(caps).getReferences().arrayBuffer != 0)

View file

@ -31,38 +31,35 @@
*/
package org.lwjgl.opengl;
import java.lang.reflect.Method;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.security.PrivilegedExceptionAction;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;
import java.util.StringTokenizer;
import java.util.WeakHashMap;
import org.lwjgl.BufferUtils;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
import org.lwjgl.Sys;
import java.lang.reflect.Method;
import java.nio.IntBuffer;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.security.PrivilegedExceptionAction;
import java.util.*;
/**
* <p/>
* Manages GL contexts. Before any rendering is done by a LWJGL system, a call should be made to GLContext.useContext() with a
* context. This will ensure that GLContext has an accurate reflection of the current context's capabilities and function
* pointers.
*
* <p/>
* This class is thread-safe in the sense that multiple threads can safely call all public methods. The class is also
* thread-aware in the sense that it tracks a per-thread current context (including capabilities and function pointers).
* That way, multiple threads can have multiple contexts current and render to them concurrently.
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
public final class GLContext {
/**
* Maps threads to their current context's ContextCapabilities, if any
*/
/** Maps threads to their current context's ContextCapabilities, if any */
private final static ThreadLocal current_capabilities = new ThreadLocal();
/**
@ -71,18 +68,18 @@ public final class GLContext {
* for the function pointers of gl functions. However, the 'current_capabilities' ThreadLocal
* is (relatively) expensive to look up, and since most OpenGL applications use are single threaded
* rendering, the following two is an optimization for this case.
*
* <p/>
* ThreadLocals can be thought of as a mapping between threads and values, so the idea
* is to use a lock-less cache of mappings between threads and the current ContextCapabilities. The cache
* could be any size, but in our case, we want a single sized cache for optimal performance
* in the single threaded case.
*
* <p/>
* 'fast_path_cache' is the most recent ContextCapabilities (potentially null) and its owner. By
* recent I mean the last thread setting the value in setCapabilities(). When getCapabilities()
* is called, a check to see if the current is the owner of the ContextCapabilities instance in
* fast_path_cache. If so, the instance is returned, if not, some thread has since taken ownership
* of the cache entry and the slower current_capabilities ThreadLocal is queried instead.
*
* <p/>
* No locks are needed in get/setCapabilities, because even though fast_path_cache can be accessed
* from multiple threads at once, we are guaranteed by the JVM spec that its value is always valid.
* Furthermore, if the ownership test in getCapabilities() succeeds, the cache entry can only contain
@ -120,7 +117,7 @@ public final class GLContext {
public static ContextCapabilities getCapabilities() {
CapabilitiesCacheEntry recent_cache_entry = fast_path_cache;
// Check owner of cache entry
if (recent_cache_entry.owner == Thread.currentThread()) {
if ( recent_cache_entry.owner == Thread.currentThread() ) {
/* The owner ship test succeeded, so the cache must contain the current ContextCapabilities instance
* assert recent_cache_entry.capabilities == getThreadLocalCapabilities();
*/
@ -143,7 +140,7 @@ public final class GLContext {
current_capabilities.set(capabilities);
CapabilitiesCacheEntry thread_cache_entry = (CapabilitiesCacheEntry)thread_cache_entries.get();
if (thread_cache_entry == null) {
if ( thread_cache_entry == null ) {
thread_cache_entry = new CapabilitiesCacheEntry();
thread_cache_entries.set(thread_cache_entry);
}
@ -163,8 +160,8 @@ public final class GLContext {
return System.getProperty("os.name");
}
});
for (int i = 0; i < os_prefixes.length; i++)
if (os_name.startsWith(os_prefixes[i])) {
for ( int i = 0; i < os_prefixes.length; i++ )
if ( os_name.startsWith(os_prefixes[i]) ) {
String platform_function_name = function.replaceFirst(function_prefix, os_function_prefixes[i]);
long address = getFunctionAddress(platform_function_name);
return address;
@ -172,9 +169,7 @@ public final class GLContext {
return 0;
}
/**
* Helper method to get a pointer to a named function in the OpenGL library
*/
/** Helper method to get a pointer to a named function in the OpenGL library */
static native long getFunctionAddress(String name);
/**
@ -183,21 +178,17 @@ public final class GLContext {
* @return A Set containing all available extension strings.
*/
static Set getSupportedExtensions() {
Set supported_extensions = new HashSet();
String extensions_string = GL11.glGetString(GL11.GL_EXTENSIONS);
if (extensions_string == null)
throw new IllegalStateException("glGetString(GL_EXTENSIONS) returned null - is there a context current?");
StringTokenizer tokenizer = new StringTokenizer(extensions_string);
while ( tokenizer.hasMoreTokens() ) {
String extension_string = tokenizer.nextToken();
supported_extensions.add(extension_string);
}
String version = GL11.glGetString(GL11.GL_VERSION);
if (version == null)
final Set supported_extensions = new HashSet();
// Detect OpenGL version first
final String version = GL11.glGetString(GL11.GL_VERSION);
if ( version == null )
throw new IllegalStateException("glGetString(GL_VERSION) returned null - possibly caused by missing current context.");
StringTokenizer version_tokenizer = new StringTokenizer(version, ". ");
String major_string = version_tokenizer.nextToken();
String minor_string = version_tokenizer.nextToken();
final StringTokenizer version_tokenizer = new StringTokenizer(version, ". ");
final String major_string = version_tokenizer.nextToken();
final String minor_string = version_tokenizer.nextToken();
int majorVersion = 0;
int minorVersion = 0;
@ -208,39 +199,47 @@ public final class GLContext {
LWJGLUtil.log("The major and/or minor OpenGL version is malformed: " + e.getMessage());
}
if (majorVersion >= 2) {
// ----------------------[ 2.X ]----------------------
switch (minorVersion) {
case 1:
supported_extensions.add("OpenGL21");
// Intentional fall through
case 0:
supported_extensions.add("OpenGL20");
}
// ----------------------[ 1.X ]----------------------
supported_extensions.add("OpenGL11");
supported_extensions.add("OpenGL12");
supported_extensions.add("OpenGL13");
supported_extensions.add("OpenGL14");
// ----------------------[ 3.X ]----------------------
if ( 3 <= majorVersion )
supported_extensions.add("OpenGL30");
// ----------------------[ 2.X ]----------------------
if ( 2 < majorVersion || (2 == majorVersion && 1 <= minorVersion) )
supported_extensions.add("OpenGL21");
if ( 2 <= majorVersion )
supported_extensions.add("OpenGL20");
// ----------------------[ 1.X ]----------------------
if ( 1 < majorVersion || 5 <= minorVersion )
supported_extensions.add("OpenGL15");
} else if (majorVersion == 1) {
switch (minorVersion) {
case 5:
supported_extensions.add("OpenGL15");
// Intentional fall through
case 4:
supported_extensions.add("OpenGL14");
// Intentional fall through
case 3:
supported_extensions.add("OpenGL13");
// Intentional fall through
case 2:
supported_extensions.add("OpenGL12");
// Intentional fall through
case 1:
supported_extensions.add("OpenGL11");
}
if ( 1 < majorVersion || 4 <= minorVersion )
supported_extensions.add("OpenGL14");
if ( 1 < majorVersion || 3 <= minorVersion )
supported_extensions.add("OpenGL13");
if ( 1 < majorVersion || 2 <= minorVersion )
supported_extensions.add("OpenGL12");
if ( 1 < majorVersion || 1 <= minorVersion )
supported_extensions.add("OpenGL11");
if ( majorVersion < 3 ) {
// Parse EXTENSIONS string
final String extensions_string = GL11.glGetString(GL11.GL_EXTENSIONS);
if ( extensions_string == null )
throw new IllegalStateException("glGetString(GL_EXTENSIONS) returned null - is there a context current?");
final StringTokenizer tokenizer = new StringTokenizer(extensions_string);
while ( tokenizer.hasMoreTokens() )
supported_extensions.add(tokenizer.nextToken());
} else {
// Use forward compatible indexed EXTENSIONS
final IntBuffer buffer = BufferUtils.createIntBuffer(16);
GL11.glGetInteger(GL30.GL_NUM_EXTENSIONS, buffer);
final int extensionCount = buffer.get(0);
for ( int i = 0; i < extensionCount; i++ )
supported_extensions.add(GL30.glGetStringi(GL11.GL_EXTENSIONS, i));
}
return supported_extensions;
}
@ -250,7 +249,7 @@ public final class GLContext {
*/
static void initNativeStubs(final Class extension_class, Set supported_extensions, String ext_name) {
resetNativeStubs(extension_class);
if (supported_extensions.contains(ext_name)) {
if ( supported_extensions.contains(ext_name) ) {
try {
AccessController.doPrivileged(new PrivilegedExceptionAction() {
public Object run() throws Exception {
@ -281,32 +280,53 @@ public final class GLContext {
* @throws LWJGLException if context non-null, and the gl library can't be loaded or the basic GL11 functions can't be loaded
*/
public static synchronized void useContext(Object context) throws LWJGLException {
if (context == null) {
useContext(context, false);
}
/**
* Makes a GL context the current LWJGL context by loading GL function pointers. The context must be current before a call to
* this method! Instead it simply ensures that the current context is reflected accurately by GLContext's extension caps and
* function pointers. Use useContext(null) when no context is active. <p>If the context is the same as last time, then this is
* a no-op. <p>If the context has not been encountered before it will be fully initialized from scratch. Otherwise a cached set
* of caps and function pointers will be used. <p>The reference to the context is held in a weak reference; therefore if no
* strong reference exists to the GL context it will automatically be forgotten by the VM at an indeterminate point in the
* future, freeing up a little RAM.
* <p>If forwardCombatible is true, function pointers of deprecated GL11-GL21 functionality will not be loaded. Calling a deprecated
* function using the specified context will result in an <code>IllegalStateException</code>.
*
* @param context The context object, which uniquely identifies a GL context. If context is null, the native stubs are
* unloaded.
* @param forwardCombatible If the context is a forward combatible context (does not expose deprecated functionality, see XGL_ARB_create_context)
*
* @throws LWJGLException if context non-null, and the gl library can't be loaded or the basic GL11 functions can't be loaded
*/
public static synchronized void useContext(Object context, boolean forwardCombatible) throws LWJGLException {
if ( context == null ) {
ContextCapabilities.unloadAllStubs();
setCapabilities(null);
if (did_auto_load)
if ( did_auto_load )
unloadOpenGLLibrary();
return;
}
if (gl_ref_count == 0) {
if ( gl_ref_count == 0 ) {
loadOpenGLLibrary();
did_auto_load = true;
}
try {
ContextCapabilities capabilities = (ContextCapabilities)capability_cache.get(context);
if (capabilities == null) {
if ( capabilities == null ) {
/*
* The capabilities object registers itself as current. This behaviour is caused
* by a chicken-and-egg situation where the constructor needs to call GL functions
* as part of its capability discovery, but GL functions cannot be called before
* a capabilities object has been set.
*/
new ContextCapabilities();
new ContextCapabilities(forwardCombatible);
capability_cache.put(context, getCapabilities());
} else
setCapabilities(capabilities);
} catch (LWJGLException e) {
if (did_auto_load)
if ( did_auto_load )
unloadOpenGLLibrary();
throw e;
}
@ -314,7 +334,7 @@ public final class GLContext {
/** If the OpenGL reference count is 0, the library is loaded. The reference count is then incremented. */
public static synchronized void loadOpenGLLibrary() throws LWJGLException {
if (gl_ref_count == 0)
if ( gl_ref_count == 0 )
nLoadOpenGLLibrary();
gl_ref_count++;
}
@ -328,7 +348,7 @@ public final class GLContext {
* Unload the native OpenGL library unless we're on linux, since
* some drivers (NVIDIA proprietary) crash on exit when unloading the library.
*/
if (gl_ref_count == 0 && LWJGLUtil.getPlatform() != LWJGLUtil.PLATFORM_LINUX)
if ( gl_ref_count == 0 && LWJGLUtil.getPlatform() != LWJGLUtil.PLATFORM_LINUX )
nUnloadOpenGLLibrary();
}
@ -338,6 +358,7 @@ public final class GLContext {
static native void resetNativeStubs(Class clazz);
private final static class CapabilitiesCacheEntry {
Thread owner;
ContextCapabilities capabilities;
}

View file

@ -247,7 +247,7 @@ final class KeyboardEventQueue extends EventQueue implements KeyListener {
KEY_MAP[KeyEvent.VK_Z] = Keyboard.KEY_Z;
}
public KeyboardEventQueue(Component component) {
KeyboardEventQueue(Component component) {
super(Keyboard.EVENT_SIZE);
this.component = component;
}

View file

@ -48,10 +48,10 @@ final class LinuxAWTGLCanvasPeerInfo extends LinuxPeerInfo {
private final AWTSurfaceLock awt_surface = new AWTSurfaceLock();
private int screen = -1;
public LinuxAWTGLCanvasPeerInfo(Canvas component) {
LinuxAWTGLCanvasPeerInfo(Canvas component) {
this.component = component;
}
protected void doLockAndInitHandle() throws LWJGLException {
ByteBuffer surface_handle = awt_surface.lockAndGetHandle(component);
if (screen == -1) {

View file

@ -0,0 +1,83 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.opengl;
/**
* An implementation of ContextAttribs using GLX_create_context.
* <p/><p/>
* ---- WIP - GLX_create_context has not been defined yet ----
*
* @author spasi <spasi@users.sourceforge.net>
*/
final class LinuxContextAttribs extends ContextAttribs {
private static final int GLX_CONTEXT_MAJOR_VERSION_ARB = 0x2091;
private static final int GLX_CONTEXT_MINOR_VERSION_ARB = 0x2092;
private static final int GLX_CONTEXT_LAYER_PLANE_ARB = 0x2093;
private static final int GLX_CONTEXT_FLAGS_ARB = 0x2094;
private static final int GLX_CONTEXT_DEBUG_BIT_ARB = 0x0001;
private static final int GLX_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB = 0x0002;
LinuxContextAttribs(final int majorVersion, final int minorVersion) {
super(majorVersion, minorVersion);
}
LinuxContextAttribs(final ContextAttribs attribs) {
super(attribs);
}
protected int getMajorVersionAttrib() {
return GLX_CONTEXT_MAJOR_VERSION_ARB;
}
protected int getMinorVersionAttrib() {
return GLX_CONTEXT_MINOR_VERSION_ARB;
}
protected int getLayerPlaneAttrib() {
return GLX_CONTEXT_LAYER_PLANE_ARB;
}
protected int getFlagsAttrib() {
return GLX_CONTEXT_FLAGS_ARB;
}
protected int getDebugBit() {
return GLX_CONTEXT_DEBUG_BIT_ARB;
}
protected int getForwardCombatibleBit() {
return GLX_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB;
}
}

View file

@ -31,23 +31,24 @@
*/
package org.lwjgl.opengl;
import java.nio.ByteBuffer;
import org.lwjgl.LWJGLException;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
/**
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
final class LinuxContextImplementation implements ContextImplementation {
public ByteBuffer create(PeerInfo peer_info, ByteBuffer shared_context_handle) throws LWJGLException {
public ByteBuffer create(PeerInfo peer_info, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException {
LinuxDisplay.lockAWT();
try {
ByteBuffer peer_handle = peer_info.lockAndGetHandle();
try {
return nCreate(peer_handle, shared_context_handle);
return nCreate(peer_handle, attribs, shared_context_handle);
} finally {
peer_info.unlock();
}
@ -56,16 +57,16 @@ final class LinuxContextImplementation implements ContextImplementation {
}
}
private static native ByteBuffer nCreate(ByteBuffer peer_handle, ByteBuffer shared_context_handle) throws LWJGLException;
private static native ByteBuffer nCreate(ByteBuffer peer_handle, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException;
public void releaseDrawable(ByteBuffer context_handle) throws LWJGLException {
}
public void swapBuffers() throws LWJGLException {
Context current_context = Context.getCurrentContext();
if (current_context == null)
if ( current_context == null )
throw new IllegalStateException("No context is current");
synchronized (current_context) {
synchronized ( current_context ) {
PeerInfo current_peer_info = current_context.getPeerInfo();
LinuxDisplay.lockAWT();
try {
@ -80,13 +81,14 @@ final class LinuxContextImplementation implements ContextImplementation {
}
}
}
private static native void nSwapBuffers(ByteBuffer peer_info_handle) throws LWJGLException;
public void releaseCurrentContext() throws LWJGLException {
Context current_context = Context.getCurrentContext();
if (current_context == null)
if ( current_context == null )
throw new IllegalStateException("No context is current");
synchronized (current_context) {
synchronized ( current_context ) {
PeerInfo current_peer_info = current_context.getPeerInfo();
LinuxDisplay.lockAWT();
try {
@ -101,6 +103,7 @@ final class LinuxContextImplementation implements ContextImplementation {
}
}
}
private static native void nReleaseCurrentContext(ByteBuffer peer_info_handle) throws LWJGLException;
public void update(ByteBuffer context_handle) {
@ -119,8 +122,9 @@ final class LinuxContextImplementation implements ContextImplementation {
LinuxDisplay.unlockAWT();
}
}
private static native void nMakeCurrent(ByteBuffer peer_handle, ByteBuffer context_handle) throws LWJGLException;
public boolean isCurrent(ByteBuffer handle) throws LWJGLException {
LinuxDisplay.lockAWT();
try {
@ -130,18 +134,20 @@ final class LinuxContextImplementation implements ContextImplementation {
LinuxDisplay.unlockAWT();
}
}
private static native boolean nIsCurrent(ByteBuffer context_handle) throws LWJGLException;
public void setSwapInterval(int value) {
Context current_context = Context.getCurrentContext();
if (current_context == null)
if ( current_context == null )
throw new IllegalStateException("No context is current");
synchronized (current_context) {
synchronized ( current_context ) {
LinuxDisplay.lockAWT();
nSetSwapInterval(current_context.getHandle(), value);
LinuxDisplay.unlockAWT();
}
}
private static native void nSetSwapInterval(ByteBuffer context_handle, int value);
public void destroy(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException {
@ -157,5 +163,6 @@ final class LinuxContextImplementation implements ContextImplementation {
LinuxDisplay.unlockAWT();
}
}
private static native void nDestroy(ByteBuffer peer_handle, ByteBuffer context_handle) throws LWJGLException;
}

View file

@ -81,7 +81,7 @@ final class LinuxDisplay implements DisplayImplementation {
/** Current window mode */
private static int current_window_mode = WINDOWED;
/** Display mode switching API */
private static final int XRANDR = 10;
private static final int XF86VIDMODE = 11;
@ -91,7 +91,7 @@ final class LinuxDisplay implements DisplayImplementation {
private static long display;
private static long current_window;
private static long saved_error_handler;
private static int display_connection_usage_count = 0;
/** Event buffer */
@ -136,13 +136,13 @@ final class LinuxDisplay implements DisplayImplementation {
private LinuxMouse mouse;
private final FocusListener focus_listener = new FocusListener() {
public final void focusGained(FocusEvent e) {
public void focusGained(FocusEvent e) {
synchronized (GlobalLock.lock) {
parent_focused = true;
parent_focus_changed = true;
}
}
public final void focusLost(FocusEvent e) {
public void focusLost(FocusEvent e) {
synchronized (GlobalLock.lock) {
parent_focused = false;
parent_focus_changed = true;
@ -167,7 +167,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
private static native ByteBuffer nGetCurrentGammaRamp(long display, int screen) throws LWJGLException;
private static int getBestDisplayModeExtension() {
int result;
if (isXrandrSupported()) {
@ -182,7 +182,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
return result;
}
private static boolean isXrandrSupported() {
if (Display.getPrivilegedBoolean("LWJGL_DISABLE_XRANDR"))
return false;
@ -240,7 +240,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
private static native boolean nIsNetWMFullscreenSupported(long display, int screen) throws LWJGLException;
/* Since Xlib is not guaranteed to be thread safe, we need a way to synchronize LWJGL
* Xlib calls with AWT Xlib calls. Fortunately, JAWT implements Lock()/Unlock() to
* do just that.
@ -253,7 +253,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
private static native void nLockAWT() throws LWJGLException;
static void unlockAWT() {
try {
nUnlockAWT();
@ -303,7 +303,7 @@ final class LinuxDisplay implements DisplayImplementation {
closeDisplay(display);
resetErrorHandler(saved_error_handler);
display = 0;
GLContext.unloadOpenGLLibrary();
GLContext.unloadOpenGLLibrary();
}*/
}
@ -322,7 +322,7 @@ final class LinuxDisplay implements DisplayImplementation {
} else
return WINDOWED;
}
static long getDisplay() {
if (display_connection_usage_count <= 0)
throw new InternalError("display_connection_usage_count = " + display_connection_usage_count);
@ -345,7 +345,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
static native int nUngrabKeyboard(long display);
private void grabKeyboard() {
if (!keyboard_grabbed) {
int res = nGrabKeyboard(getDisplay(), getWindow());
@ -354,7 +354,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
static native int nGrabKeyboard(long display, long window);
private void grabPointer() {
if (!pointer_grabbed) {
int result = nGrabPointer(getDisplay(), getWindow(), None);
@ -394,7 +394,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
updateCursor();
}
private void updateCursor() {
long cursor;
if (shouldGrab()) {
@ -405,7 +405,7 @@ final class LinuxDisplay implements DisplayImplementation {
nDefineCursor(getDisplay(), getWindow(), cursor);
}
private static native void nDefineCursor(long display, long window, long cursor_handle);
private boolean isLegacyFullscreen() {
return current_window_mode == FULLSCREEN_LEGACY;
}
@ -484,7 +484,7 @@ final class LinuxDisplay implements DisplayImplementation {
ByteBuffer parent_peer_info_handle = parent_peer_info.lockAndGetHandle();
try {
return parent_peer_info.getDrawable();
} finally {
} finally {
parent_peer_info.unlock();
}
}
@ -548,8 +548,7 @@ final class LinuxDisplay implements DisplayImplementation {
public void resetDisplayMode() {
lockAWT();
try {
if(current_mode != saved_mode)
switchDisplayMode(saved_mode);
switchDisplayMode(saved_mode);
if (isXF86VidModeSupported())
doSetGamma(saved_gamma);
} catch (LWJGLException e) {
@ -646,7 +645,7 @@ final class LinuxDisplay implements DisplayImplementation {
current_mode = saved_mode;
saved_gamma = getCurrentGammaRamp();
current_gamma = saved_gamma;
return current_mode;
return saved_mode;
} finally {
unlockAWT();
}
@ -665,7 +664,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
/** Assumes extension == XRANDR */
private static native DisplayMode nGetCurrentXRandrMode(long display, int screen) throws LWJGLException;
@ -703,7 +702,7 @@ final class LinuxDisplay implements DisplayImplementation {
peer_info = new LinuxDisplayPeerInfo(pixel_format);
return peer_info;
}
static native void setInputFocus(long display, long window, long time);
private void relayEventToParent(LinuxEvent event_buffer, int event_mask) {
@ -828,7 +827,7 @@ final class LinuxDisplay implements DisplayImplementation {
mouse = null;
updateInputGrab();
}
public void pollMouse(IntBuffer coord_buffer, ByteBuffer buttons) {
lockAWT();
try {
@ -837,7 +836,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
public void readMouse(ByteBuffer buffer) {
lockAWT();
try {
@ -846,7 +845,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
public void setCursorPosition(int x, int y) {
lockAWT();
try {
@ -949,7 +948,7 @@ final class LinuxDisplay implements DisplayImplementation {
private boolean shouldWarpPointer() {
return pointer_grabbed && shouldGrab();
}
public int getNativeCursorCapabilities() {
lockAWT();
try {
@ -976,7 +975,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
public int getMinCursorSize() {
lockAWT();
try {
@ -1012,7 +1011,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
private static native int nGetMaxCursorSize(long display, long window);
/* Keyboard */
public void createKeyboard() throws LWJGLException {
lockAWT();
@ -1022,7 +1021,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
public void destroyKeyboard() {
lockAWT();
try {
@ -1032,7 +1031,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
public void pollKeyboard(ByteBuffer keyDownBuffer) {
lockAWT();
try {
@ -1050,7 +1049,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
private static native long nCreateCursor(long display, int width, int height, int xHotspot, int yHotspot, int numImages, IntBuffer images, int images_offset, IntBuffer delays, int delays_offset) throws LWJGLException;
private static long createBlankCursor() {
@ -1088,7 +1087,7 @@ final class LinuxDisplay implements DisplayImplementation {
}
}
static native void nDestroyCursor(long display, long cursorHandle);
public int getPbufferCapabilities() {
lockAWT();
try {
@ -1128,7 +1127,7 @@ final class LinuxDisplay implements DisplayImplementation {
public void releaseTexImageFromPbuffer(PeerInfo handle, int buffer) {
throw new UnsupportedOperationException();
}
private static ByteBuffer convertIcon(ByteBuffer icon, int width, int height) {
ByteBuffer icon_rgb = BufferUtils.createByteBuffer(icon.capacity());
int x;
@ -1212,7 +1211,7 @@ final class LinuxDisplay implements DisplayImplementation {
unlockAWT();
}
}
private static native void nSetWindowIcon(long display, long window, ByteBuffer icon_rgb, int icon_rgb_size, ByteBuffer icon_mask, int icon_mask_size, int width, int height);
public int getWidth() {

View file

@ -42,7 +42,7 @@ import org.lwjgl.LWJGLException;
* $Id$
*/
final class LinuxDisplayPeerInfo extends LinuxPeerInfo {
public LinuxDisplayPeerInfo(PixelFormat pixel_format) throws LWJGLException {
LinuxDisplayPeerInfo(PixelFormat pixel_format) throws LWJGLException {
LinuxDisplay.lockAWT();
try {
GLContext.loadOpenGLLibrary();
@ -63,7 +63,7 @@ final class LinuxDisplayPeerInfo extends LinuxPeerInfo {
}
}
private static native void initDefaultPeerInfo(long display, int screen, ByteBuffer peer_info_handle, PixelFormat pixel_format) throws LWJGLException;
protected void doLockAndInitHandle() throws LWJGLException {
LinuxDisplay.lockAWT();
try {
@ -73,7 +73,7 @@ final class LinuxDisplayPeerInfo extends LinuxPeerInfo {
}
}
private static native void initDrawable(long window, ByteBuffer peer_info_handle);
protected void doUnlock() throws LWJGLException {
// NO-OP
}

View file

@ -55,12 +55,12 @@ final class LinuxEvent {
private final ByteBuffer event_buffer;
public LinuxEvent() {
LinuxEvent() {
this.event_buffer = createEventBuffer();
}
private static native ByteBuffer createEventBuffer();
public final void copyFrom(LinuxEvent event) {
public void copyFrom(LinuxEvent event) {
int pos = event_buffer.position();
int event_pos = event.event_buffer.position();
event_buffer.put(event.event_buffer);
@ -68,137 +68,137 @@ final class LinuxEvent {
event.event_buffer.position(event_pos);
}
public final static native int getPending(long display);
public static native int getPending(long display);
public final void sendEvent(long display, long window, boolean propagate, long event_mask) {
public void sendEvent(long display, long window, boolean propagate, long event_mask) {
nSendEvent(event_buffer, display, window, propagate, event_mask);
}
private static native void nSendEvent(ByteBuffer event_buffer, long display, long window, boolean propagate, long event_mask);
public final boolean filterEvent(long window) {
public boolean filterEvent(long window) {
return nFilterEvent(event_buffer, window);
}
private static native boolean nFilterEvent(ByteBuffer event_buffer, long window);
public final void nextEvent(long display) {
public void nextEvent(long display) {
nNextEvent(display, event_buffer);
}
private static native void nNextEvent(long display, ByteBuffer event_buffer);
public final int getType() {
public int getType() {
return nGetType(event_buffer);
}
private static native int nGetType(ByteBuffer event_buffer);
public final long getWindow() {
public long getWindow() {
return nGetWindow(event_buffer);
}
private static native long nGetWindow(ByteBuffer event_buffer);
public final void setWindow(long window) {
public void setWindow(long window) {
nSetWindow(event_buffer, window);
}
private static native void nSetWindow(ByteBuffer event_buffer, long window);
/* Focus methods */
public final int getFocusMode() {
public int getFocusMode() {
return nGetFocusMode(event_buffer);
}
private static native int nGetFocusMode(ByteBuffer event_buffer);
public final int getFocusDetail() {
public int getFocusDetail() {
return nGetFocusDetail(event_buffer);
}
private static native int nGetFocusDetail(ByteBuffer event_buffer);
/* ClientMessage methods */
public final long getClientMessageType() {
public long getClientMessageType() {
return nGetClientMessageType(event_buffer);
}
private static native long nGetClientMessageType(ByteBuffer event_buffer);
public final int getClientData(int index) {
public int getClientData(int index) {
return nGetClientData(event_buffer, index);
}
private static native int nGetClientData(ByteBuffer event_buffer, int index);
public final int getClientFormat() {
public int getClientFormat() {
return nGetClientFormat(event_buffer);
}
private static native int nGetClientFormat(ByteBuffer event_buffer);
/* Button methods */
public final long getButtonTime() {
public long getButtonTime() {
return nGetButtonTime(event_buffer);
}
private static native long nGetButtonTime(ByteBuffer event_buffer);
public final int getButtonState() {
public int getButtonState() {
return nGetButtonState(event_buffer);
}
private static native int nGetButtonState(ByteBuffer event_buffer);
public final int getButtonType() {
public int getButtonType() {
return nGetButtonType(event_buffer);
}
private static native int nGetButtonType(ByteBuffer event_buffer);
public final int getButtonButton() {
public int getButtonButton() {
return nGetButtonButton(event_buffer);
}
private static native int nGetButtonButton(ByteBuffer event_buffer);
public final long getButtonRoot() {
public long getButtonRoot() {
return nGetButtonRoot(event_buffer);
}
private static native long nGetButtonRoot(ByteBuffer event_buffer);
public final int getButtonXRoot() {
public int getButtonXRoot() {
return nGetButtonXRoot(event_buffer);
}
private static native int nGetButtonXRoot(ByteBuffer event_buffer);
public final int getButtonYRoot() {
public int getButtonYRoot() {
return nGetButtonYRoot(event_buffer);
}
private static native int nGetButtonYRoot(ByteBuffer event_buffer);
public final int getButtonX() {
public int getButtonX() {
return nGetButtonX(event_buffer);
}
private static native int nGetButtonX(ByteBuffer event_buffer);
public final int getButtonY() {
public int getButtonY() {
return nGetButtonY(event_buffer);
}
private static native int nGetButtonY(ByteBuffer event_buffer);
/* Key methods */
public final long getKeyAddress() {
public long getKeyAddress() {
return nGetKeyAddress(event_buffer);
}
private static native long nGetKeyAddress(ByteBuffer event_buffer);
public final long getKeyTime() {
public long getKeyTime() {
return nGetKeyTime(event_buffer);
}
private static native int nGetKeyTime(ByteBuffer event_buffer);
public final int getKeyType() {
public int getKeyType() {
return nGetKeyType(event_buffer);
}
private static native int nGetKeyType(ByteBuffer event_buffer);
public final int getKeyKeyCode() {
public int getKeyKeyCode() {
return nGetKeyKeyCode(event_buffer);
}
private static native int nGetKeyKeyCode(ByteBuffer event_buffer);
public final int getKeyState() {
public int getKeyState() {
return nGetKeyState(event_buffer);
}
private static native int nGetKeyState(ByteBuffer event_buffer);

View file

@ -56,7 +56,7 @@ final class LinuxKeyboard {
private final long xim;
private final long xic;
private final int numlock_mask;
private final int modeswitch_mask;
private final int caps_lock_mask;
@ -80,7 +80,7 @@ final class LinuxKeyboard {
private long deferred_nanos;
private byte deferred_key_state;
public LinuxKeyboard(long display, long window) {
LinuxKeyboard(long display, long window) {
long modifier_map = getModifierMapping(display);
int tmp_numlock_mask = 0;
int tmp_modeswitch_mask = 0;
@ -194,7 +194,7 @@ final class LinuxKeyboard {
return num_chars;
}
private static native int lookupString(long event_ptr, ByteBuffer buffer, ByteBuffer compose_status);
private int lookupStringUnicode(long event_ptr, int[] translation_buffer) {
int status = utf8LookupString(xic, event_ptr, native_translation_buffer, native_translation_buffer.position(), native_translation_buffer.remaining());
if (status != XLookupChars && status != XLookupBoth)

View file

@ -54,7 +54,7 @@ final class LinuxMouse {
private final static int Button3 = 3;
private final static int Button4 = 4;
private final static int Button5 = 5;
private final static int ButtonPress = 4;
private final static int ButtonRelease = 5;
@ -74,7 +74,7 @@ final class LinuxMouse {
private EventQueue event_queue;
private long last_event_nanos;
public LinuxMouse(long display, long window, long input_window) throws LWJGLException {
LinuxMouse(long display, long window, long input_window) throws LWJGLException {
this.display = display;
this.window = window;
this.input_window = input_window;
@ -191,7 +191,7 @@ final class LinuxMouse {
private static native int nGetWindowWidth(long display, long window);
private static native long nQueryPointer(long display, long window, IntBuffer result);
public void setCursorPosition(int x, int y) {
nWarpCursor(display, window, x, transformY(y));
}
@ -200,7 +200,7 @@ final class LinuxMouse {
private void handlePointerMotion(boolean grab, boolean warp_pointer, long millis, long root_window, int x_root, int y_root, int x, int y) {
doHandlePointerMotion(grab, warp_pointer, root_window, x_root, y_root, x, y, millis*1000000);
}
private void handleButton(boolean grab, int button, byte state, long nanos) {
byte button_num;
switch (button) {
@ -259,7 +259,7 @@ final class LinuxMouse {
break;
}
}
private void resetCursor(int x, int y) {
last_x = x;
last_y = transformY(y);

View file

@ -42,7 +42,7 @@ import org.lwjgl.LWJGLException;
* $Id$
*/
final class LinuxPbufferPeerInfo extends LinuxPeerInfo {
public LinuxPbufferPeerInfo(int width, int height, PixelFormat pixel_format) throws LWJGLException {
LinuxPbufferPeerInfo(int width, int height, PixelFormat pixel_format) throws LWJGLException {
LinuxDisplay.lockAWT();
try {
GLContext.loadOpenGLLibrary();

View file

@ -40,7 +40,7 @@ import java.nio.ByteBuffer;
* $Id$
*/
abstract class LinuxPeerInfo extends PeerInfo {
public LinuxPeerInfo() {
LinuxPeerInfo() {
super(createHandle());
}
private static native ByteBuffer createHandle();

View file

@ -44,7 +44,7 @@ import java.awt.Canvas;
final class MacOSXAWTGLCanvasPeerInfo extends MacOSXCanvasPeerInfo {
private final Canvas component;
public MacOSXAWTGLCanvasPeerInfo(Canvas component, PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
MacOSXAWTGLCanvasPeerInfo(Canvas component, PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
super(pixel_format, support_pbuffer);
this.component = component;
}

View file

@ -48,7 +48,7 @@ final class MacOSXCanvasListener implements ComponentListener, HierarchyListener
private int height;
private boolean context_update;
public MacOSXCanvasListener(Canvas canvas) {
MacOSXCanvasListener(Canvas canvas) {
this.canvas = canvas;
canvas.addComponentListener(this);
canvas.addHierarchyListener(this);
@ -58,7 +58,7 @@ final class MacOSXCanvasListener implements ComponentListener, HierarchyListener
public void disableListeners() {
// Mac OS X applets will hang in Display.destroy() when parented when removing the listeners directly
java.awt.EventQueue.invokeLater(new Runnable() {
public final void run() {
public void run() {
canvas.removeComponentListener(MacOSXCanvasListener.this);
canvas.removeHierarchyListener(MacOSXCanvasListener.this);
}

View file

@ -45,7 +45,7 @@ import org.lwjgl.LWJGLException;
abstract class MacOSXCanvasPeerInfo extends MacOSXPeerInfo {
private final AWTSurfaceLock awt_surface = new AWTSurfaceLock();
public MacOSXCanvasPeerInfo(PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
protected MacOSXCanvasPeerInfo(PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
super(pixel_format, true, true, support_pbuffer, true);
}

View file

@ -0,0 +1,83 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.opengl;
/**
* An implementation of ContextAttribs for MacOS X.
* <p/><p/>
* ---- WIP - No XGL_create_context has been defined for MacOS X yet ----
*
* @author spasi <spasi@users.sourceforge.net>
*/
final class MacOSXContextAttribs extends ContextAttribs {
private static final int XGL_CONTEXT_MAJOR_VERSION_ARB = 0x2091;
private static final int XGL_CONTEXT_MINOR_VERSION_ARB = 0x2092;
private static final int XGL_CONTEXT_LAYER_PLANE_ARB = 0x2093;
private static final int XGL_CONTEXT_FLAGS_ARB = 0x2094;
private static final int XGL_CONTEXT_DEBUG_BIT_ARB = 0x0001;
private static final int XGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB = 0x0002;
MacOSXContextAttribs(final int majorVersion, final int minorVersion) {
super(majorVersion, minorVersion);
}
MacOSXContextAttribs(final ContextAttribs attribs) {
super(attribs);
}
protected int getMajorVersionAttrib() {
return XGL_CONTEXT_MAJOR_VERSION_ARB;
}
protected int getMinorVersionAttrib() {
return XGL_CONTEXT_MINOR_VERSION_ARB;
}
protected int getLayerPlaneAttrib() {
return XGL_CONTEXT_LAYER_PLANE_ARB;
}
protected int getFlagsAttrib() {
return XGL_CONTEXT_FLAGS_ARB;
}
protected int getDebugBit() {
return XGL_CONTEXT_DEBUG_BIT_ARB;
}
protected int getForwardCombatibleBit() {
return XGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB;
}
}

View file

@ -31,56 +31,62 @@
*/
package org.lwjgl.opengl;
import java.nio.ByteBuffer;
import org.lwjgl.LWJGLException;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
/**
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
final class MacOSXContextImplementation implements ContextImplementation {
public ByteBuffer create(PeerInfo peer_info, ByteBuffer shared_context_handle) throws LWJGLException {
public ByteBuffer create(PeerInfo peer_info, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException {
ByteBuffer peer_handle = peer_info.lockAndGetHandle();
try {
return nCreate(peer_handle, shared_context_handle);
return nCreate(peer_handle, attribs, shared_context_handle);
} finally {
peer_info.unlock();
}
}
private static native ByteBuffer nCreate(ByteBuffer peer_handle, ByteBuffer shared_context_handle) throws LWJGLException;
private static native ByteBuffer nCreate(ByteBuffer peer_handle, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException;
public void swapBuffers() throws LWJGLException {
Context current_context = Context.getCurrentContext();
if (current_context == null)
if ( current_context == null )
throw new IllegalStateException("No context is current");
synchronized (current_context) {
synchronized ( current_context ) {
nSwapBuffers(current_context.getHandle());
}
}
private static native void nSwapBuffers(ByteBuffer context_handle) throws LWJGLException;
public void update(ByteBuffer context_handle) {
nUpdate(context_handle);
}
private static native void nUpdate(ByteBuffer context_handle);
public void releaseCurrentContext() throws LWJGLException {
nReleaseCurrentContext();
}
private static native void nReleaseCurrentContext() throws LWJGLException;
public void releaseDrawable(ByteBuffer context_handle) throws LWJGLException {
clearDrawable(context_handle);
}
private static native void clearDrawable(ByteBuffer handle) throws LWJGLException;
static void resetView(PeerInfo peer_info, Context context) throws LWJGLException {
ByteBuffer peer_handle = peer_info.lockAndGetHandle();
try {
synchronized (context) {
synchronized ( context ) {
clearDrawable(context.getHandle());
setView(peer_handle, context.getHandle());
}
@ -88,7 +94,7 @@ final class MacOSXContextImplementation implements ContextImplementation {
peer_info.unlock();
}
}
public void makeCurrent(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException {
ByteBuffer peer_handle = peer_info.lockAndGetHandle();
try {
@ -98,25 +104,30 @@ final class MacOSXContextImplementation implements ContextImplementation {
peer_info.unlock();
}
}
private static native void setView(ByteBuffer peer_handle, ByteBuffer context_handle) throws LWJGLException;
private static native void nMakeCurrent(ByteBuffer context_handle) throws LWJGLException;
public boolean isCurrent(ByteBuffer handle) throws LWJGLException {
boolean result = nIsCurrent(handle);
return result;
}
private static native boolean nIsCurrent(ByteBuffer context_handle) throws LWJGLException;
public void setSwapInterval(int value) {
Context current_context = Context.getCurrentContext();
synchronized (current_context) {
synchronized ( current_context ) {
nSetSwapInterval(current_context.getHandle(), value);
}
}
private static native void nSetSwapInterval(ByteBuffer context_handle, int value);
public void destroy(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException {
nDestroy(handle);
}
private static native void nDestroy(ByteBuffer context_handle) throws LWJGLException;
}

View file

@ -44,7 +44,7 @@ import org.lwjgl.LWJGLException;
final class MacOSXDisplayPeerInfo extends MacOSXCanvasPeerInfo {
private boolean locked = false;
public MacOSXDisplayPeerInfo(PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
MacOSXDisplayPeerInfo(PixelFormat pixel_format, boolean support_pbuffer) throws LWJGLException {
super(pixel_format, support_pbuffer);
}

View file

@ -42,7 +42,7 @@ import org.lwjgl.LWJGLException;
* $Id$
*/
final class MacOSXPbufferPeerInfo extends MacOSXPeerInfo {
public MacOSXPbufferPeerInfo(int width, int height, PixelFormat pixel_format) throws LWJGLException {
MacOSXPbufferPeerInfo(int width, int height, PixelFormat pixel_format) throws LWJGLException {
super(pixel_format, false, false, true, false);
nCreate(getHandle(), width, height);
}

View file

@ -43,7 +43,7 @@ import org.lwjgl.LWJGLUtil;
* $Id$
*/
abstract class MacOSXPeerInfo extends PeerInfo {
public MacOSXPeerInfo(PixelFormat pixel_format, boolean use_display_bpp, boolean support_window, boolean support_pbuffer, boolean double_buffered) throws LWJGLException {
MacOSXPeerInfo(PixelFormat pixel_format, boolean use_display_bpp, boolean support_window, boolean support_pbuffer, boolean double_buffered) throws LWJGLException {
super(createHandle());
if (pixel_format.isFloatingPoint() && !LWJGLUtil.isMacOSXEqualsOrBetterThan(10, 4))
throw new LWJGLException("Floating point pixel format requested, but is not supported");

View file

@ -197,6 +197,31 @@ public final class Pbuffer implements Drawable {
* with the Display context (if created).
*/
public Pbuffer(int width, int height, PixelFormat pixel_format, RenderTexture renderTexture, Drawable shared_drawable) throws LWJGLException {
this(width, height, pixel_format, renderTexture, shared_drawable, null);
}
/**
* Create an instance of a Pbuffer with a unique OpenGL context. The buffer is single-buffered.
* <p/>
* NOTE: The Pbuffer will have its own context that shares display lists and textures with <code>shared_context</code>,
* or, if <code>shared_context</code> is <code>null</code>, the Display context if it is created. The Pbuffer
* will have its own OpenGL state. Therefore, state changes to a pbuffer will not be seen in the window context and vice versa.
* <p/>
* The renderTexture parameter defines the necessary state for enabling render-to-texture. When this parameter is null,
* render-to-texture is not available. Before using render-to-texture, the Pbuffer capabilities must be queried to ensure that
* it is supported. Currently only windows platform can support this feature, so it is recommended that EXT_framebuffer_object
* or similar is used if available, for maximum portability.
* <p/>
*
* @param width Pbuffer width
* @param height Pbuffer height
* @param pixel_format Minimum Pbuffer context properties
* @param renderTexture
* @param shared_drawable If non-null the Pbuffer will share display lists and textures with it. Otherwise, the Pbuffer will share
* with the Display context (if created).
* @param attribs The ContextAttribs to use when creating the context. (optional, may be null)
*/
public Pbuffer(int width, int height, PixelFormat pixel_format, RenderTexture renderTexture, Drawable shared_drawable, ContextAttribs attribs) throws LWJGLException {
if (pixel_format == null)
throw new NullPointerException("Pixel format must be non-null");
this.width = width;
@ -210,7 +235,7 @@ public final class Pbuffer implements Drawable {
if (display_drawable != null)
shared_context = display_drawable.getContext();
}
this.context = new Context(peer_info, shared_context);
this.context = new Context(peer_info, attribs, shared_context);
}
private static PeerInfo createPbuffer(int width, int height, PixelFormat pixel_format, RenderTexture renderTexture) throws LWJGLException {
@ -229,7 +254,7 @@ public final class Pbuffer implements Drawable {
public Context getContext() {
return context;
}
private void checkDestroyed() {
if (destroyed)
throw new IllegalStateException("Pbuffer is destroyed");

View file

@ -51,10 +51,10 @@ abstract class PeerInfo {
this.handle = handle;
}
private final void lockAndInitHandle() throws LWJGLException {
private void lockAndInitHandle() throws LWJGLException {
doLockAndInitHandle();
}
public synchronized final void unlock() throws LWJGLException {
if (lock_count <= 0)
throw new IllegalStateException("PeerInfo not locked!");

View file

@ -1,31 +1,31 @@
/*
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
@ -35,42 +35,51 @@ package org.lwjgl.opengl;
* This class describes pixel format properties for an OpenGL context. Instances
* of this class is used as arguments to Display.create(), Pbuffer.create() and
* AWTGLCanvas, to indicate minimum required properties.
*
* <p/>
* Instants of this class are immutable. An example of the expected way to set
* the PixelFormat property values is the following:
* <code>PixelFormat pf = new PixelFormat().withDepth(24).withSamples(4).withSRGB(true);</code>
* <p/>
* WARNING: Some pixel formats are known to cause troubles on certain buggy drivers.
* Example: Under Windows, specifying samples != 0 will enable the ARB
* pixel format selection path, which could trigger a crash.
* Example: Under Windows, specifying samples != 0 will enable the ARB
* pixel format selection path, which could trigger a crash.
*
* @author elias_naur@sourceforge.net
* @version $Revision$
*/
public final class PixelFormat {
/**
* The number of bits per pixel, exluding alpha.
* The number of bits per pixel, exluding alpha.
* This parameter is ignored in Display.create().
*/
private final int bpp;
private int bpp;
/** The number of alpha bits. */
private final int alpha;
/** The number of depth buffer bits*/
private final int depth;
private int alpha;
/** The number of depth buffer bits */
private int depth;
/** The number of stencil bits */
private final int stencil;
private int stencil;
/**
* The number of samples to use in anti-aliasing.
* 0 means that anti-aliasing is disabled.
*/
private final int samples;
/** The number of auxilliary buffers */
private final int num_aux_buffers;
private int samples;
/** The number of auxiliary buffers */
private int num_aux_buffers;
/** The number of bits per pixel in the accumulation buffer */
private final int accum_bpp;
private int accum_bpp;
/** The number of alpha bits in the accumulation buffer */
private final int accum_alpha;
private int accum_alpha;
/** Whether this format requires a stereo buffer */
private final boolean stereo;
private boolean stereo;
/** Whether this format specifies a floating point format */
private final boolean floating_point;
private boolean floating_point;
/** Whether this format specifies a packed floating point format (32 bit unsigned - R11F_G11F_B10F) */
private boolean floating_point_packed;
/** Whether this format specifies an sRGB format */
private boolean sRGB;
/**
* Default pixel format is minimum 8 bits depth, and no alpha
@ -101,51 +110,269 @@ public final class PixelFormat {
this.alpha = alpha;
this.depth = depth;
this.stencil = stencil;
this.samples = samples;
this.num_aux_buffers = num_aux_buffers;
this.accum_bpp = accum_bpp;
this.accum_alpha = accum_alpha;
this.stereo = stereo;
this.floating_point = floating_point;
this.floating_point_packed = false;
this.sRGB = false;
}
private PixelFormat(final PixelFormat pf) {
this.bpp = pf.bpp;
this.alpha = pf.alpha;
this.depth = pf.depth;
this.stencil = pf.stencil;
this.samples = pf.samples;
this.num_aux_buffers = pf.num_aux_buffers;
this.accum_bpp = pf.accum_bpp;
this.accum_alpha = pf.accum_alpha;
this.stereo = pf.stereo;
this.floating_point = pf.floating_point;
this.floating_point_packed = pf.floating_point_packed;
this.sRGB = pf.sRGB;
}
public int getBitsPerPixel() {
return bpp;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new bits per pixel value.
*
* @param bpp the new bits per pixel value.
*
* @return the new PixelFormat
*/
public PixelFormat withBitsPerPixel(final int bpp) {
if ( bpp < 0 )
throw new IllegalArgumentException("Invalid number of bits per pixel specified: " + bpp);
final PixelFormat pf = new PixelFormat(this);
pf.bpp = bpp;
return pf;
}
public int getAlphaBits() {
return alpha;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new alpha bits value.
*
* @param alpha the new alpha bits value.
*
* @return the new PixelFormat
*/
public PixelFormat withAlphaBits(final int alpha) {
if ( alpha < 0 )
throw new IllegalArgumentException("Invalid number of alpha bits specified: " + alpha);
final PixelFormat pf = new PixelFormat(this);
pf.alpha = alpha;
return pf;
}
public int getDepthBits() {
return depth;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new depth bits value.
*
* @param depth the new depth bits value.
*
* @return the new PixelFormat
*/
public PixelFormat withDepthBits(final int depth) {
if ( depth < 0 )
throw new IllegalArgumentException("Invalid number of depth bits specified: " + depth);
final PixelFormat pf = new PixelFormat(this);
pf.depth = depth;
return pf;
}
public int getStencilBits() {
return stencil;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new stencil bits value.
*
* @param stencil the new stencil bits value.
*
* @return the new PixelFormat
*/
public PixelFormat withStencilBits(final int stencil) {
if ( stencil < 0 )
throw new IllegalArgumentException("Invalid number of stencil bits specified: " + stencil);
final PixelFormat pf = new PixelFormat(this);
pf.stencil = stencil;
return pf;
}
public int getSamples() {
return samples;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new samples value.
*
* @param samples the new samples value.
*
* @return the new PixelFormat
*/
public PixelFormat withSamples(final int samples) {
if ( samples < 0 )
throw new IllegalArgumentException("Invalid number of samples specified: " + samples);
final PixelFormat pf = new PixelFormat(this);
pf.samples = samples;
return pf;
}
public int getAuxBuffers() {
return num_aux_buffers;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new auxiliary buffers value.
*
* @param num_aux_buffers the new auxiliary buffers value.
*
* @return the new PixelFormat
*/
public PixelFormat withAuxBuffers(final int num_aux_buffers) {
if ( num_aux_buffers < 0 )
throw new IllegalArgumentException("Invalid number of auxiliary buffers specified: " + num_aux_buffers);
final PixelFormat pf = new PixelFormat(this);
pf.num_aux_buffers = num_aux_buffers;
return pf;
}
public int getAccumulationBitsPerPixel() {
return accum_bpp;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new bits per pixel in the accumulation buffer value.
*
* @param accum_bpp the new bits per pixel in the accumulation buffer value.
*
* @return the new PixelFormat
*/
public PixelFormat withAccumulationBitsPerPixel(final int accum_bpp) {
if ( accum_bpp < 0 )
throw new IllegalArgumentException("Invalid number of bits per pixel in the accumulation buffer specified: " + accum_bpp);
final PixelFormat pf = new PixelFormat(this);
pf.accum_bpp = accum_bpp;
return pf;
}
public int getAccumulationAlpha() {
return accum_alpha;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new alpha bits in the accumulation buffer value.
*
* @param accum_alpha the new alpha bits in the accumulation buffer value.
*
* @return the new PixelFormat
*/
public PixelFormat withAccumulationAlpha(final int accum_alpha) {
if ( accum_alpha < 0 )
throw new IllegalArgumentException("Invalid number of alpha bits in the accumulation buffer specified: " + accum_alpha);
final PixelFormat pf = new PixelFormat(this);
pf.accum_alpha = accum_alpha;
return pf;
}
public boolean isStereo() {
return stereo;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new stereo value.
*
* @param stereo the new stereo value.
*
* @return the new PixelFormat
*/
public PixelFormat withStereo(final boolean stereo) {
final PixelFormat pf = new PixelFormat(this);
pf.stereo = stereo;
return pf;
}
public boolean isFloatingPoint() {
return floating_point;
}
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new floating point value.
* If floating_point is true, floating_point_packed will be reset to false.
*
* @param floating_point the new floating point value.
*
* @return the new PixelFormat
*/
public PixelFormat withFloatingPoint(final boolean floating_point) {
final PixelFormat pf = new PixelFormat(this);
pf.floating_point = floating_point;
if ( floating_point )
pf.floating_point_packed = false;
return pf;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new packed floating point value.
* If floating_point_packed is true, floating_point will be reset to false.
*
* @param floating_point_packed the new packed floating point value.
*
* @return the new PixelFormat
*/
public PixelFormat withFloatingPointPacked(final boolean floating_point_packed) {
final PixelFormat pf = new PixelFormat(this);
pf.floating_point_packed = floating_point_packed;
if ( floating_point_packed )
pf.floating_point = false;
return pf;
}
public boolean isSRGB() {
return sRGB;
}
/**
* Returns a new PixelFormat object with the same properties as this PixelFormat and the new sRGB value.
*
* @param sRGB the new floating point value.
*
* @return the new PixelFormat
*/
public PixelFormat withSRGB(final boolean sRGB) {
final PixelFormat pf = new PixelFormat(this);
pf.sRGB = sRGB;
return pf;
}
}

View file

@ -49,7 +49,7 @@ final class WindowsAWTGLCanvasPeerInfo extends WindowsPeerInfo {
private final PixelFormat pixel_format;
private boolean has_pixel_format= false;
public WindowsAWTGLCanvasPeerInfo(Canvas component, PixelFormat pixel_format) {
WindowsAWTGLCanvasPeerInfo(Canvas component, PixelFormat pixel_format) {
this.component = component;
this.pixel_format = pixel_format;
}

View file

@ -0,0 +1,81 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.opengl;
/**
* An implementation of ContextAttribs using WGL_create_context.
*
* @author spasi <spasi@users.sourceforge.net>
*/
final class WindowsContextAttribs extends ContextAttribs {
private static final int WGL_CONTEXT_MAJOR_VERSION_ARB = 0x2091;
private static final int WGL_CONTEXT_MINOR_VERSION_ARB = 0x2092;
private static final int WGL_CONTEXT_LAYER_PLANE_ARB = 0x2093;
private static final int WGL_CONTEXT_FLAGS_ARB = 0x2094;
private static final int WGL_CONTEXT_DEBUG_BIT_ARB = 0x0001;
private static final int WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB = 0x0002;
WindowsContextAttribs(final int majorVersion, final int minorVersion) {
super(majorVersion, minorVersion);
}
WindowsContextAttribs(final ContextAttribs attribs) {
super(attribs);
}
protected int getMajorVersionAttrib() {
return WGL_CONTEXT_MAJOR_VERSION_ARB;
}
protected int getMinorVersionAttrib() {
return WGL_CONTEXT_MINOR_VERSION_ARB;
}
protected int getLayerPlaneAttrib() {
return WGL_CONTEXT_LAYER_PLANE_ARB;
}
protected int getFlagsAttrib() {
return WGL_CONTEXT_FLAGS_ARB;
}
protected int getDebugBit() {
return WGL_CONTEXT_DEBUG_BIT_ARB;
}
protected int getForwardCombatibleBit() {
return WGL_CONTEXT_FORWARD_COMPATIBLE_BIT_ARB;
}
}

View file

@ -31,33 +31,35 @@
*/
package org.lwjgl.opengl;
import java.nio.ByteBuffer;
import org.lwjgl.LWJGLException;
import org.lwjgl.LWJGLUtil;
import java.nio.ByteBuffer;
import java.nio.IntBuffer;
/**
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
final class WindowsContextImplementation implements ContextImplementation {
public ByteBuffer create(PeerInfo peer_info, ByteBuffer shared_context_handle) throws LWJGLException {
public ByteBuffer create(PeerInfo peer_info, IntBuffer attribs, ByteBuffer shared_context_handle) throws LWJGLException {
ByteBuffer peer_handle = peer_info.lockAndGetHandle();
try {
return nCreate(peer_handle, shared_context_handle);
return nCreate(peer_handle, attribs, shared_context_handle);
} finally {
peer_info.unlock();
}
}
private static native ByteBuffer nCreate(ByteBuffer peer_handle, ByteBuffer shared_context_handle) throws LWJGLException;
private static native ByteBuffer nCreate(ByteBuffer peer_handle, IntBuffer attribs_handle, ByteBuffer shared_context_handle) throws LWJGLException;
public void swapBuffers() throws LWJGLException {
Context current_context = Context.getCurrentContext();
if (current_context == null)
if ( current_context == null )
throw new IllegalStateException("No context is current");
synchronized (current_context) {
synchronized ( current_context ) {
PeerInfo current_peer_info = current_context.getPeerInfo();
ByteBuffer peer_handle = current_peer_info.lockAndGetHandle();
try {
@ -67,6 +69,7 @@ final class WindowsContextImplementation implements ContextImplementation {
}
}
}
private static native void nSwapBuffers(ByteBuffer peer_info_handle) throws LWJGLException;
public void releaseDrawable(ByteBuffer context_handle) throws LWJGLException {
@ -78,6 +81,7 @@ final class WindowsContextImplementation implements ContextImplementation {
public void releaseCurrentContext() throws LWJGLException {
nReleaseCurrentContext();
}
private static native void nReleaseCurrentContext() throws LWJGLException;
public void makeCurrent(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException {
@ -88,24 +92,28 @@ final class WindowsContextImplementation implements ContextImplementation {
peer_info.unlock();
}
}
private static native void nMakeCurrent(ByteBuffer peer_handle, ByteBuffer context_handle) throws LWJGLException;
public boolean isCurrent(ByteBuffer handle) throws LWJGLException {
boolean result = nIsCurrent(handle);
return result;
}
private static native boolean nIsCurrent(ByteBuffer context_handle) throws LWJGLException;
public void setSwapInterval(int value) {
boolean success = nSetSwapInterval(value);
if (!success)
if ( !success )
LWJGLUtil.log("Failed to set swap interval");
Util.checkGLError();
}
private static native boolean nSetSwapInterval(int value);
public void destroy(PeerInfo peer_info, ByteBuffer handle) throws LWJGLException {
nDestroy(handle);
}
private static native void nDestroy(ByteBuffer context_handle) throws LWJGLException;
}

View file

@ -150,7 +150,7 @@ final class WindowsDisplay implements DisplayImplementation {
private long small_icon;
private long large_icon;
public WindowsDisplay() {
WindowsDisplay() {
current_display = this;
}
@ -191,7 +191,7 @@ final class WindowsDisplay implements DisplayImplementation {
private native long nCreateWindow(boolean fullscreen, int x, int y, int width, int height, boolean undecorated, boolean child_window, long parent_hwnd) throws LWJGLException;
private static boolean isUndecorated() {
return Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.undecorated");
return Display.getPrivilegedBoolean("org.lwjgl.opengl.Window.undecorated");
}
private static long getHwnd(Canvas parent) throws LWJGLException {
@ -200,7 +200,7 @@ final class WindowsDisplay implements DisplayImplementation {
ByteBuffer parent_peer_info_handle = parent_peer_info.lockAndGetHandle();
try {
return parent_peer_info.getHwnd();
} finally {
} finally {
parent_peer_info.unlock();
}
}
@ -350,7 +350,7 @@ final class WindowsDisplay implements DisplayImplementation {
}
return null;
}
public String getVersion() {
String driver = getAdapter();
if (driver != null) {
@ -449,11 +449,11 @@ final class WindowsDisplay implements DisplayImplementation {
public void pollMouse(IntBuffer coord_buffer, ByteBuffer buttons) {
mouse.poll(coord_buffer, buttons);
}
public void readMouse(ByteBuffer buffer) {
mouse.read(buffer);
}
public void grabMouse(boolean grab) {
mouse.grab(grab, shouldGrab());
updateCursor();
@ -540,11 +540,11 @@ final class WindowsDisplay implements DisplayImplementation {
keyboard.destroy();
keyboard = null;
}
public void pollKeyboard(ByteBuffer keyDownBuffer) {
keyboard.poll(keyDownBuffer);
}
public void readKeyboard(ByteBuffer buffer) {
keyboard.read(buffer);
}
@ -576,7 +576,7 @@ final class WindowsDisplay implements DisplayImplementation {
}
}
private native int nGetPbufferCapabilities(PixelFormat format) throws LWJGLException;
public boolean isBufferLost(PeerInfo handle) {
return ((WindowsPbufferPeerInfo)handle).isBufferLost();
}
@ -586,7 +586,7 @@ final class WindowsDisplay implements DisplayImplementation {
IntBuffer pBufferAttribs) throws LWJGLException {
return new WindowsPbufferPeerInfo(width, height, pixel_format, pixelFormatCaps, pBufferAttribs);
}
public void setPbufferAttrib(PeerInfo handle, int attrib, int value) {
((WindowsPbufferPeerInfo)handle).setPbufferAttrib(attrib, value);
}
@ -594,11 +594,11 @@ final class WindowsDisplay implements DisplayImplementation {
public void bindTexImageToPbuffer(PeerInfo handle, int buffer) {
((WindowsPbufferPeerInfo)handle).bindTexImageToPbuffer(buffer);
}
public void releaseTexImageFromPbuffer(PeerInfo handle, int buffer) {
((WindowsPbufferPeerInfo)handle).releaseTexImageFromPbuffer(buffer);
}
private void freeSmallIcon() {
if (small_icon != 0) {
destroyIcon(small_icon);
@ -629,12 +629,12 @@ final class WindowsDisplay implements DisplayImplementation {
boolean done_small = false;
boolean done_large = false;
int used = 0;
int small_icon_size = 16;
int large_icon_size = 32;
for (int i=0;i<icons.length;i++) {
int size = icons[i].limit() / 4;
if ((((int) Math.sqrt(size)) == small_icon_size) && (!done_small)) {
freeSmallIcon();
small_icon = createIcon(small_icon_size, small_icon_size, icons[i].asIntBuffer());
@ -650,7 +650,7 @@ final class WindowsDisplay implements DisplayImplementation {
done_large = true;
}
}
return used;
}
private static native long createIcon(int width, int height, IntBuffer icon);
@ -712,7 +712,7 @@ final class WindowsDisplay implements DisplayImplementation {
else
return defWindowProc(hwnd, msg, wParam, lParam);
}
private static native int defWindowProc(long hwnd, int msg, long wParam, long lParam);
private void checkCursorState() {

View file

@ -43,13 +43,13 @@ import org.lwjgl.LWJGLException;
*/
final class WindowsDisplayPeerInfo extends WindowsPeerInfo {
private final PixelFormat pixel_format;
public WindowsDisplayPeerInfo(PixelFormat pixel_format) throws LWJGLException {
WindowsDisplayPeerInfo(PixelFormat pixel_format) throws LWJGLException {
this.pixel_format = pixel_format;
GLContext.loadOpenGLLibrary();
}
final PixelFormat getPixelFormat() {
PixelFormat getPixelFormat() {
return pixel_format;
}

View file

@ -39,7 +39,7 @@ final class WindowsFileVersion {
private final int product_version_ms;
private final int product_version_ls;
public WindowsFileVersion(int product_version_ms, int product_version_ls) {
WindowsFileVersion(int product_version_ms, int product_version_ls) {
this.product_version_ms = product_version_ms;
this.product_version_ls = product_version_ls;
}

View file

@ -63,7 +63,7 @@ final class WindowsKeyboard {
private long retained_millis;
private boolean retained_repeat;
public WindowsKeyboard(long hwnd) throws LWJGLException {
WindowsKeyboard(long hwnd) throws LWJGLException {
this.hwnd = hwnd;
keyboard_state = BufferUtils.createByteBuffer(256);
}
@ -71,7 +71,7 @@ final class WindowsKeyboard {
public void destroy() {
}
boolean isKeyDown(int lwjgl_keycode) {
return key_down_buffer[lwjgl_keycode] == 1;
}
@ -84,7 +84,7 @@ final class WindowsKeyboard {
} else {
if (grabbed) {
grabbed = false;
}
}
}
}
@ -93,7 +93,7 @@ final class WindowsKeyboard {
keyDownBuffer.put(key_down_buffer);
keyDownBuffer.position(old_position);
}
private static native int MapVirtualKey(int uCode, int uMapType);
private static native int ToUnicode(int wVirtKey, int wScanCode, ByteBuffer lpKeyState, CharBuffer pwszBuff, int cchBuff, int flags);
private static native int ToAscii(int wVirtKey, int wScanCode, ByteBuffer lpKeyState, ByteBuffer lpChar, int flags);
@ -108,7 +108,7 @@ final class WindowsKeyboard {
}
private boolean checkShiftKey(int virt_key, byte state) {
int key_state = (GetKeyState(virt_key) >>> 15) & 0x1;
int key_state = (GetKeyState(virt_key) >>> 15) & 0x1;
int lwjgl_code = WindowsKeycodes.mapVirtualKeyToLWJGLCode(virt_key);
return (key_down_buffer[lwjgl_code] == 1 - state) && (key_state == state);
}

View file

@ -63,7 +63,7 @@ final class WindowsMouse {
private int last_x;
private int last_y;
public WindowsMouse(long hwnd) throws LWJGLException {
WindowsMouse(long hwnd) throws LWJGLException {
this.hwnd = hwnd;
this.mouse_button_count = WindowsDisplay.getSystemMetrics(WindowsDisplay.SM_CMOUSEBUTTONS);
this.has_wheel = WindowsDisplay.getSystemMetrics(WindowsDisplay.SM_MOUSEWHEELPRESENT) != 0;
@ -109,7 +109,7 @@ final class WindowsMouse {
}
accum_dx = accum_dy = accum_dwheel = 0;
}
private void putMouseEventWithCoords(byte button, byte state, int coord1, int coord2, int dz, long nanos) {
mouse_event.clear();
mouse_event.put(button).put(state).putInt(coord1).putInt(coord2).putInt(dz).putLong(nanos);
@ -149,7 +149,7 @@ final class WindowsMouse {
if (mouse_grabbed) {
mouse_grabbed = false;
WindowsDisplay.resetCursorClipping();
}
}
}
event_queue.clearEvents();
}

View file

@ -43,7 +43,7 @@ import org.lwjgl.LWJGLException;
* $Id$
*/
final class WindowsPbufferPeerInfo extends WindowsPeerInfo {
public WindowsPbufferPeerInfo(int width, int height, PixelFormat pixel_format, IntBuffer pixelFormatCaps, IntBuffer pBufferAttribs) throws LWJGLException {
WindowsPbufferPeerInfo(int width, int height, PixelFormat pixel_format, IntBuffer pixelFormatCaps, IntBuffer pBufferAttribs) throws LWJGLException {
nCreate(getHandle(), width, height, pixel_format, pixelFormatCaps, pBufferAttribs);
}
private static native void nCreate(ByteBuffer handle, int width, int height, PixelFormat pixel_format, IntBuffer pixelFormatCaps, IntBuffer pBufferAttribs) throws LWJGLException;
@ -62,12 +62,12 @@ final class WindowsPbufferPeerInfo extends WindowsPeerInfo {
nBindTexImageToPbuffer(getHandle(), buffer);
}
private static native void nBindTexImageToPbuffer(ByteBuffer handle, int buffer);
public void releaseTexImageFromPbuffer(int buffer) {
nReleaseTexImageFromPbuffer(getHandle(), buffer);
}
private static native void nReleaseTexImageFromPbuffer(ByteBuffer handle, int buffer);
public void destroy() {
nDestroy(getHandle());
}

View file

@ -43,7 +43,7 @@ import org.lwjgl.LWJGLException;
* $Id$
*/
abstract class WindowsPeerInfo extends PeerInfo {
public WindowsPeerInfo() {
protected WindowsPeerInfo() {
super(createHandle());
}
private static native ByteBuffer createHandle();

View file

@ -37,20 +37,21 @@ import java.util.Arrays;
import java.util.Collection;
import java.util.EnumSet;
import java.util.Iterator;
import java.lang.annotation.Annotation;
import com.sun.mirror.declaration.InterfaceDeclaration;
import com.sun.mirror.declaration.MethodDeclaration;
import com.sun.mirror.type.InterfaceType;
/**
*
* Generator visitor for the context capabilities generator tool
*
* @author elias_naur <elias_naur@users.sourceforge.net>
* @version $Revision$
* $Id$
* $Id$
*/
public class ContextCapabilitiesGenerator {
private final static String STUBS_LOADED_NAME = "loaded_stubs";
private final static String ALL_INIT_METHOD_NAME = "initAllStubs";
private final static String POINTER_INITIALIZER_POSTFIX = "_initNativeFunctionAddresses";
@ -63,18 +64,18 @@ public class ContextCapabilitiesGenerator {
writer.println("\tfinal StateTracker tracker;");
writer.println("\tfinal IntBuffer scratch_int_buffer = BufferUtils.createIntBuffer(16);");
writer.println();
if (!context_specific) {
if ( !context_specific ) {
writer.println("\tprivate static boolean " + STUBS_LOADED_NAME + " = false;");
}
}
public static void generateInitializerPrologue(PrintWriter writer) {
writer.println("\t" + Utils.CONTEXT_CAPS_CLASS_NAME + "() throws LWJGLException {");
writer.println("\t\tSet " + CACHED_EXTS_VAR_NAME + " = " + ALL_INIT_METHOD_NAME + "();");
writer.println("\t" + Utils.CONTEXT_CAPS_CLASS_NAME + "(boolean forwardCombatible) throws LWJGLException {");
writer.println("\t\tSet " + CACHED_EXTS_VAR_NAME + " = " + ALL_INIT_METHOD_NAME + "(forwardCombatible);");
}
private static String translateFieldName(String interface_name) {
if (interface_name.startsWith("GL"))
if ( interface_name.startsWith("GL") )
return CORE_PREFIX + interface_name;
else
return EXTENSION_PREFIX + interface_name;
@ -82,9 +83,9 @@ public class ContextCapabilitiesGenerator {
public static void generateSuperClassAdds(PrintWriter writer, InterfaceDeclaration d) {
Collection<InterfaceType> super_interfaces = d.getSuperinterfaces();
if (super_interfaces.size() > 1)
if ( super_interfaces.size() > 1 )
throw new RuntimeException(d + " extends more than one other interface");
if (super_interfaces.size() == 1) {
if ( super_interfaces.size() == 1 ) {
InterfaceType super_interface = super_interfaces.iterator().next();
writer.print("\t\tif (" + CACHED_EXTS_VAR_NAME + ".contains(\"");
writer.println(translateFieldName(d.getSimpleName()) + "\"))");
@ -99,9 +100,9 @@ public class ContextCapabilitiesGenerator {
writer.print(CACHED_EXTS_VAR_NAME + ".contains(\"");
writer.print(translated_field_name + "\")");
Collection<InterfaceType> super_interfaces = d.getSuperinterfaces();
if (super_interfaces.size() > 1)
if ( super_interfaces.size() > 1 )
throw new RuntimeException(d + " extends more than one other interface");
if (super_interfaces.size() == 1) {
if ( super_interfaces.size() == 1 ) {
InterfaceType super_interface = super_interfaces.iterator().next();
writer.println();
writer.print("\t\t\t&& " + CACHED_EXTS_VAR_NAME + ".contains(\"");
@ -113,23 +114,26 @@ public class ContextCapabilitiesGenerator {
private static String getAddressesInitializerName(String class_name) {
return class_name + POINTER_INITIALIZER_POSTFIX;
}
public static void generateInitStubsPrologue(PrintWriter writer, boolean context_specific) {
writer.println("\tprivate Set " + ALL_INIT_METHOD_NAME + "() throws LWJGLException {");
if (!context_specific) {
writer.println("\tprivate Set " + ALL_INIT_METHOD_NAME + "(boolean forwardCombatible) throws LWJGLException {");
if ( !context_specific ) {
writer.println("\t\tif (" + STUBS_LOADED_NAME + ")");
writer.println("\t\t\treturn GLContext.getSupportedExtensions();");
writer.println("\t\torg.lwjgl.opengl.GL11." + Utils.STUB_INITIALIZER_NAME + "();");
} else {
writer.println("\t\tif (!" + getAddressesInitializerName("GL11") + "())");
writer.println("\t\tif (!" + getAddressesInitializerName("GL11") + "(forwardCombatible))");
writer.println("\t\t\tthrow new LWJGLException(\"GL11 not supported\");");
}
// Try to initialize GL30.glGetStringi here, in case we have created an OpenGL 3.0 context
// (it will be used in GLContext.getSupportedExtensions)
writer.println("\t\tGL30_glGetStringi_pointer = GLContext.getFunctionAddress(\"glGetStringi\");");
writer.println("\t\tGLContext.setCapabilities(this);");
writer.println("\t\tSet " + CACHED_EXTS_VAR_NAME + " = GLContext.getSupportedExtensions();");
}
public static void generateInitStubsEpilogue(PrintWriter writer, boolean context_specific) {
if (!context_specific) {
if ( !context_specific ) {
writer.println("\t\t" + STUBS_LOADED_NAME + " = true;");
}
writer.println("\t\treturn " + CACHED_EXTS_VAR_NAME + ";");
@ -137,19 +141,28 @@ public class ContextCapabilitiesGenerator {
}
public static void generateUnloadStubs(PrintWriter writer, InterfaceDeclaration d) {
if (d.getMethods().size() > 0) {
if ( d.getMethods().size() > 0 ) {
writer.print("\t\tGLContext.resetNativeStubs(" + Utils.getSimpleClassName(d));
writer.println(".class);");
}
}
public static void generateInitStubs(PrintWriter writer, InterfaceDeclaration d, boolean context_specific) {
if (d.getMethods().size() > 0) {
if (context_specific) {
if ( d.getMethods().size() > 0 ) {
if ( context_specific ) {
writer.print("\t\tif (" + CACHED_EXTS_VAR_NAME + ".contains(\"");
writer.print(translateFieldName(d.getSimpleName()) + "\")");
writer.println(" && !" + getAddressesInitializerName(d.getSimpleName()) + "())");
writer.print("\t\t\t" + CACHED_EXTS_VAR_NAME + ".remove(\"");
writer.print(" && !" + getAddressesInitializerName(d.getSimpleName()) + "(");
if ( d.getAnnotation(DeprecatedGL.class) != null )
writer.print("forwardCombatible");
if ( d.getAnnotation(Dependent.class) != null ) {
if ( d.getAnnotation(DeprecatedGL.class) != null )
writer.print(",");
writer.print("supported_extensions");
}
writer.println("))");
//writer.print("\t\t\t" + CACHED_EXTS_VAR_NAME + ".remove(\"");
writer.print("\t\t\tremove(" + CACHED_EXTS_VAR_NAME + ", \"");
writer.println(translateFieldName(d.getSimpleName()) + "\");");
} else {
writer.print("\t\tGLContext." + Utils.STUB_INITIALIZER_NAME + "(" + Utils.getSimpleClassName(d));
@ -157,7 +170,7 @@ public class ContextCapabilitiesGenerator {
}
}
}
private static void generateAddExtension(PrintWriter writer, InterfaceDeclaration d) {
writer.print(CACHED_EXTS_VAR_NAME + ".add(\"");
writer.println(translateFieldName(d.getSimpleName()) + "\");");
@ -165,46 +178,71 @@ public class ContextCapabilitiesGenerator {
public static void generateAddressesInitializers(PrintWriter writer, InterfaceDeclaration d) {
Iterator<? extends MethodDeclaration> methods = d.getMethods().iterator();
if (methods.hasNext()) {
writer.println("\tprivate boolean " + getAddressesInitializerName(d.getSimpleName()) + "() {");
writer.println("\t\treturn ");
while (methods.hasNext()) {
MethodDeclaration method = methods.next();
writer.print("\t\t\t(" + Utils.getFunctionAddressName(d, method) + " = ");
PlatformDependent platform_dependent = method.getAnnotation(PlatformDependent.class);
if (platform_dependent != null) {
EnumSet<Platform> platform_set = EnumSet.copyOf(Arrays.asList(platform_dependent.value()));
writer.print("GLContext.getPlatformSpecificFunctionAddress(\"");
writer.print(Platform.ALL.getPrefix() + "\", ");
writer.print("new String[]{");
Iterator<Platform> platforms = platform_set.iterator();
while (platforms.hasNext()) {
writer.print("\"" + platforms.next().getOSPrefix() + "\"");
if(platforms.hasNext())
writer.print(", ");
}
writer.print("}, new String[]{");
platforms = platform_set.iterator();
while (platforms.hasNext()) {
writer.print("\"" + platforms.next().getPrefix() + "\"");
if(platforms.hasNext())
writer.print(", ");
}
writer.print("}, ");
} else
writer.print("GLContext.getFunctionAddress(");
writer.print("\"" + method.getSimpleName() + "\")) != 0");
if (methods.hasNext())
writer.println(" &&");
}
writer.println(";");
writer.println("\t}");
writer.println();
if ( !methods.hasNext() )
return;
writer.print("\tprivate boolean " + getAddressesInitializerName(d.getSimpleName()) + "(");
DeprecatedGL deprecated = d.getAnnotation(DeprecatedGL.class);
Dependent dependent = d.getAnnotation(Dependent.class);
if ( deprecated != null )
writer.print("boolean forwardCombatible");
if ( dependent != null ) {
if ( deprecated != null )
writer.print(",");
writer.print("Set supported_extensions");
}
writer.println(") {");
writer.println("\t\treturn ");
while ( methods.hasNext() ) {
MethodDeclaration method = methods.next();
deprecated = method.getAnnotation(DeprecatedGL.class);
dependent = method.getAnnotation(Dependent.class);
writer.print("\t\t\t(");
if ( deprecated != null )
writer.print("forwardCombatible || ");
if ( dependent != null )
writer.print("!supported_extensions.contains(\"" + dependent.value() + "\") || ");
if ( deprecated != null || dependent != null )
writer.print('(');
writer.print(Utils.getFunctionAddressName(d, method) + " = ");
PlatformDependent platform_dependent = method.getAnnotation(PlatformDependent.class);
if ( platform_dependent != null ) {
EnumSet<Platform> platform_set = EnumSet.copyOf(Arrays.asList(platform_dependent.value()));
writer.print("GLContext.getPlatformSpecificFunctionAddress(\"");
writer.print(Platform.ALL.getPrefix() + "\", ");
writer.print("new String[]{");
Iterator<Platform> platforms = platform_set.iterator();
while ( platforms.hasNext() ) {
writer.print("\"" + platforms.next().getOSPrefix() + "\"");
if ( platforms.hasNext() )
writer.print(", ");
}
writer.print("}, new String[]{");
platforms = platform_set.iterator();
while ( platforms.hasNext() ) {
writer.print("\"" + platforms.next().getPrefix() + "\"");
if ( platforms.hasNext() )
writer.print(", ");
}
writer.print("}, ");
} else
writer.print("GLContext.getFunctionAddress(");
writer.print("\"" + method.getSimpleName() + "\")) != 0");
if ( deprecated != null || dependent != null )
writer.print(')');
if ( methods.hasNext() )
writer.println(" &&");
}
writer.println(";");
writer.println("\t}");
writer.println();
}
public static void generateSymbolAddresses(PrintWriter writer, InterfaceDeclaration d) {
for (MethodDeclaration method : d.getMethods()) {
for ( MethodDeclaration method : d.getMethods() ) {
writer.println("\tlong " + Utils.getFunctionAddressName(d, method) + ";");
}
}
@ -212,4 +250,4 @@ public class ContextCapabilitiesGenerator {
public static void generateField(PrintWriter writer, InterfaceDeclaration d) {
writer.println("\tpublic final boolean " + translateFieldName(d.getSimpleName()) + ";");
}
}
}

View file

@ -64,7 +64,7 @@ import com.sun.mirror.util.DeclarationFilter;
*/
public class ContextGeneratorProcessorFactory implements AnnotationProcessorFactory, RoundCompleteListener {
private static boolean first_round = true;
// Process any set of annotations
private static final Collection<String> supportedAnnotations =
unmodifiableCollection(Arrays.asList("*"));
@ -114,6 +114,7 @@ public class ContextGeneratorProcessorFactory implements AnnotationProcessorFact
writer.println("package org.lwjgl.opengl;");
writer.println();
writer.println("import org.lwjgl.LWJGLException;");
writer.println("import org.lwjgl.LWJGLUtil;");
writer.println("import org.lwjgl.BufferUtils;");
writer.println("import java.util.Set;");
writer.println("import java.nio.IntBuffer;");
@ -139,6 +140,12 @@ public class ContextGeneratorProcessorFactory implements AnnotationProcessorFact
}
writer.println();
}
writer.println("\tprivate static void remove(Set supported_extensions, String extension) {");
writer.println("\t\tLWJGLUtil.log(extension + \" was reported as available but an entry point is missing\");");
writer.println("\t\tsupported_extensions.remove(extension);");
writer.println("\t}\n");
ContextCapabilitiesGenerator.generateInitStubsPrologue(writer, context_specific);
for (TypeDeclaration typedecl : interface_decls) {
InterfaceDeclaration interface_decl = (InterfaceDeclaration)typedecl;

View file

@ -0,0 +1,47 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.util.generator;
/**
* Use this annotation on extensions with functionality that depends on the presence of other extensions.
* Functions in such extensions marked with this annotation will only be loaded if the specified extension is present.
*
* @author spasi <spasi@users.sourceforge.net>
*/
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
@Target({ ElementType.TYPE, ElementType.METHOD })
public @interface Dependent {
String value() default "";
}

View file

@ -0,0 +1,46 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.util.generator;
/**
* Use this annotation on extensions with deprecated functionality.
* Functions in such extensions marked with this annotation will not be loaded in a forward combatible context.
*
* @author spasi <spasi@users.sourceforge.net>
*/
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
@Target({ ElementType.TYPE, ElementType.METHOD })
public @interface DeprecatedGL {
}

View file

@ -0,0 +1,47 @@
/*
* Copyright (c) 2002-2008 LWJGL Project
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
* met:
*
* * Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
*
* * Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* * Neither the name of 'LWJGL' nor the names of
* its contributors may be used to endorse or promote products derived
* from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
* "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
* CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
* EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
* PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
* PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
* SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
package org.lwjgl.util.generator;
/**
* Unsigned binary representing an absolute absolute or relative time interval.
* Precision is nanoseconds but accuracy is implementation-dependent.
*
* @author spasi <spasi@users.sourceforge.net>
*/
import java.lang.annotation.ElementType;
import java.lang.annotation.Target;
@NativeType
@Target({ElementType.PARAMETER, ElementType.METHOD})
public @interface GLtime {
}

View file

@ -283,6 +283,8 @@ public class JavaMethodsGenerator {
result = method_name.substring(0, method_name.length() - (postfix.length() + 1 + extension_postfix.length()));
else if (method_name.endsWith(postfix + extension_postfix))
result = method_name.substring(0, method_name.length() - (postfix.length() + extension_postfix.length()));
else if ( method_name.endsWith("_v" + extension_postfix) )
result = method_name.substring(0, method_name.length() - (2 + extension_postfix.length()));
else if (method_name.endsWith("v" + extension_postfix))
result = method_name.substring(0, method_name.length() - (1 + extension_postfix.length()));
else