GLDrawable.swapBuffers(); behaviour

GLDrawable.swapBuffers(); only works correctly in windowed-mode.
In fullscreen the screen remains black until JOGL swaps buffers when finishing GLDrawable.display().

Hardware: ATi Radeon 9700pro
Drivers: Catalys 4.7
OS: Windows XP Pro

Adding to that:

In windowed-mode it doesn’t matter if you properly set:
GLDrawable.setAutoSwapBufferMode(…);

In fullscreen it does matter, so I added that code to fix the problem.

Still unpredicted behaviour though.

HTH.

Do you have a test case illustrating the problem? Could you file a bug with the JOGL Issue Tracker?

Testcase! (The forum messed up quite a bit of the formatting)

Note:
windowed + automatic-swap = only dark-green box (as expected)
fullscreen + automatic-swap = only dark-green box (as expected)

forced-swap + canvas.setAutoSwapBufferMode(true); combo
(which is wrong, but shows the unpredicted behaviour)
windowed + forced-swap = dark/bright green boxes flicking (hm…)
fullscreen + forced-swap = only dark-green box (hm…)
^^^^^^^^^^ both should result in the same gfx, but are different.

What happens:
in fullscreen-mode the swapBuffers() is ignored (correct)
in windowed-mode the swapBuffer() is processed (wrong, as: canvas.setAutoSwapBufferMode(true))

forced-swap + canvas.setAutoSwapBufferMode(false); combo works just fine.



import java.awt.*;
import java.awt.event.*;
import javax.swing.JOptionPane;
import javax.swing.UIManager;

import net.java.games.jogl.*;

public class Run
{
   public static void main(String[] args) throws Exception
   {
      new Run();
   }



   private Run()
   {
      try
      {
         UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
      }
      catch (Exception exc)
      {
         //
      }

      // Settings

      final boolean fullscreen = JOptionPane.OK_OPTION == JOptionPane.showConfirmDialog(new Frame(), "Do you want to enter fullscreen-mode?", "Fullscreen?", JOptionPane.YES_NO_OPTION);

      try
      {
         Thread.sleep(500);
      }
      catch (Exception exc)
      {
         //
      }

      final boolean forcedSwap = JOptionPane.OK_OPTION == JOptionPane.showConfirmDialog(new Frame(), "Do you want to forcibly swap buffers?", "ForcedSwap?", JOptionPane.YES_NO_OPTION);

      // GUI

      final GLCapabilities caps = new GLCapabilities();
      caps.setHardwareAccelerated(true);

      final GLCanvas canvas = GLDrawableFactory.getFactory().createGLCanvas(caps);

      /*
       * If this mode is set to true, whatever the "forcedSwap" value might be,
       * behaviour changes in fullscreen/windowed-mode.
       */
      canvas.setAutoSwapBufferMode(true);
      // Should be: [!forcedSwap] in perfect code

      canvas.setNoAutoRedrawMode(true);
      canvas.addGLEventListener(new Renderer(forcedSwap));
      canvas.addKeyListener(new KeyboardShutdown());

      final Frame frame = new Frame();
      frame.setTitle("Bouncing box");
      frame.setResizable(false);
      frame.add(canvas, BorderLayout.CENTER);

      if (fullscreen)
      {
         frame.setUndecorated(true);

         GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
         GraphicsDevice device = env.getDefaultScreenDevice();
         device.setFullScreenWindow(frame);
      }
      else
      {
         frame.setSize(640, 480);
         frame.setLocationRelativeTo(null);
         frame.setVisible(true);
      }

      frame.addWindowListener(new FrameShutdown());

      canvas.requestFocus();

      running = true;
      n00bL00p(frame, canvas);
   }

   /**
    * LOOP
    */

   private boolean running;



   private void n00bL00p(Frame frame, GLCanvas canvas)
   {
      while (running)
      {
         logic();
         canvas.display();
      }

      // Close
      frame.setVisible(false);
      frame.dispose();
      System.exit(0);
   }

   /**
    * LOGIC
    */

   private int w, h;

   private int rectX, rectY, rectR, rectSpeedX, rectSpeedY;



   private void logic()
   {
      rectX += rectSpeedX;
      rectY += rectSpeedY;

      if (rectX < 0 || rectX > w)
      {
         rectSpeedX *= -1;
      }

      if (rectY < 0 || rectY > h)
      {
         rectSpeedY *= -1;
      }
   }

   /**
    * RENDERER
    */

   private class Renderer implements GLEventListener
   {
      private final boolean forcedSwap;



      public Renderer(boolean forcedSwap)
      {
         this.forcedSwap = forcedSwap;
      }



      public void init(GLDrawable d)
      {
         GL gl = d.getGL();
         gl.glShadeModel(GL.GL_SMOOTH);
         gl.glClearColor(0.0F, 0.0F, 0.0F, 1.0F);

         rectR = 32;
         rectSpeedX = 4;
         rectSpeedY = 4;
      }



      public void display(GLDrawable d)
      {
         GL gl = d.getGL();

         // Bright green box
         this.renderBox(gl, rectX - rectR, rectY, rectR, new float[] { 0.0F, 1.0F, 0.0F });

         if (forcedSwap)
         {
            // Swap in-between
            d.swapBuffers();
         }

         // Dark green box
         this.renderBox(gl, rectX + rectR, rectY, rectR, new float[] { 0.0F, 0.5F, 0.0F });

         if (forcedSwap)
         {
            // Swap finally
            d.swapBuffers();
         }
      }



      private void renderBox(GL gl, int x, int y, int r, float[] color)
      {
         gl.glClear(GL.GL_COLOR_BUFFER_BIT);

         this.enable2D(gl);

         gl.glColor3fv(color);
         gl.glBegin(GL.GL_QUADS);
         gl.glVertex2f(x - r, y - r);
         gl.glVertex2f(x + r, y - r);
         gl.glVertex2f(x + r, y + r);
         gl.glVertex2f(x - r, y + r);
         gl.glEnd();

         this.disable2D(gl);

         try
         {
            Thread.sleep(10L);
         }
         catch (Exception exc)
         {
            // Terrible I know, just for testing.
         }
      }



      public void displayChanged(GLDrawable arg0, boolean arg1, boolean arg2)
      {
         //
      }



      public void reshape(GLDrawable arg0, int arg1, int arg2, int arg3, int arg4)
      {
         w = arg3;
         h = arg4;
      }



      private final void enable2D(GL gl)
      {
         // Java2D coord-system
         gl.glMatrixMode(GL.GL_PROJECTION);
         gl.glPushMatrix();
         gl.glLoadIdentity();

         gl.glScalef(1.0F / (w / 2), 1.0F / (h / 2), 1);
         gl.glTranslatef(-w / 2, h / 2, 0);
         gl.glScalef(1, -1, 1);

         gl.glMatrixMode(GL.GL_MODELVIEW);
         gl.glPushMatrix();
         gl.glLoadIdentity();
      }



      private final void disable2D(GL gl)
      {
         gl.glMatrixMode(GL.GL_PROJECTION);
         gl.glPopMatrix();
         gl.glMatrixMode(GL.GL_MODELVIEW);
         gl.glPopMatrix();
      }
   }

   /**
    * SHUT DOWN
    */

   private class FrameShutdown extends WindowAdapter
   {
      public void windowClosing(WindowEvent event)
      {
         running = false;
      }
   }

   private class KeyboardShutdown extends KeyAdapter
   {
      public void keyPressed(KeyEvent event)
      {
         if (event.getKeyCode() == KeyEvent.VK_ESCAPE)
         {
            running = false;
         }
      }
   }
}

Please go to https://jogl.dev.java.net/servlets/ProjectIssues and open a new bug, attaching your test case. You’ll need to be an Observer of the project to properly modify your bug report. Thanks.