glReadPixels with PBO not asynchronous?

Started by tyr, February 01, 2014, 17:28:03

Previous topic - Next topic

tyr

Hi,

I'm trying to get a buffered image out of my framebuffer. From reading online it seems that using two PBO buffers and asynchronous glReadPixels is fastest. However, my glReadPixels call seems to block. Note that I'm using a PBuffer setup (is this the reason?) since I want to be able to run my application completely command line. Any suggestions as to what I'm doing wrong?

Code below:

///////////In the constructor/////////
      pbuffer = new Pbuffer(1800, 1200, new PixelFormat(), null, null);
      pbuffer.makeCurrent();
         
           int pbo1 = ARBBufferObject.glGenBuffersARB();
           int pbo2 = ARBBufferObject.glGenBuffersARB();          
          
           ARBBufferObject.glBindBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, pbo1);
           ARBBufferObject.glBufferDataARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, 1800*1200*4, ARBPixelBufferObject.GL_STREAM_READ_ARB);
          
           ARBBufferObject.glBindBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, pbo2);
           ARBBufferObject.glBufferDataARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, 1800*1200*4, ARBPixelBufferObject.GL_STREAM_READ_ARB);

//After GL setup and drawing////

      int[] pixelInts = new int[1800*1200];
          
      GL11.glReadBuffer(GL.GL_FRONT);
             
                //set up a read from the "next" buffer, pbo2
      ARBBufferObject.glBindBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_BINDING_ARB, pbo2);             
      long t = new Date().getTime();
      GL11.glReadPixels(0, 0, 1800, 1200, GL.GL_BGRA, GL.GL_UNSIGNED_BYTE, 0);                 
      System.out.println("time: " + (new Date().getTime()-t));  //for a dense scene it gives me about 50ms :(
         
                //get the data from the current buffer, pbo1
      ARBBufferObject.glBindBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_BINDING_ARB, pbo1);
      if (pixelsRGB == null)
                pixelsRGB = ARBBufferObject.glMapBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, ARBPixelBufferObject.GL_READ_ONLY_ARB, null);
      else
                pixelsRGB = ARBBufferObject.glMapBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB, ARBPixelBufferObject.GL_READ_ONLY_ARB, pixelsRGB);
             
             
      if (pixelsRGB == null)
      {
             int aux = pbo1;
             pbo1 = pbo2;
             pbo2 = aux;
                return;
      }

          ARBBufferObject.glUnmapBufferARB(ARBPixelBufferObject.GL_PIXEL_PACK_BUFFER_ARB);     // release pointer to the mapped buffer
          int aux = pbo1;
          pbo1 = pbo2;
          pbo2 = aux;
             

//the rest is filling in the image with pixel data...

           int p = width * height * 4; // Points to first byte (red) in each row.
           int q;                  // Index into ByteBuffer
           int i = 0;                  // Index into target int[]
           int w3 = width * 4;         // Number of bytes in each row

           for (int row = 0; row < height; row++) {
               p -= w3;
               q = p;
               for (int col = 0; col < width; col++) {
                  
                  int iB = pixelsRGB.get(q++);
                  int iG = pixelsRGB.get(q++);                  
                   int iR = pixelsRGB.get(q++);                  
                  
                   int iA = pixelsRGB.get(q++);

                   pixelInts[i++] = 0xFF000000
                           | ((iR & 0x000000FF) << 16)
                           | ((iG & 0x000000FF) << 8)
                           | (iB & 0x000000FF);
               }

           }
          
           image.setRGB(0, 0, width, height, pixelInts, 0, width);