use whole viewport to render
+ .. attribute:: depth
+
+ use depth component of render as array of float - not suitable for texture source,
+ should only be used with bge.texture.imageToArray(mode='F')
+
+ .. attribute:: zbuff
+
+ use depth component of render as grey scale color - suitable for texture source
+
.. class:: ImageViewport()
Image source from viewport
use whole viewport to capture
+ .. attribute:: depth
+
+ use depth component of viewport as array of float - not suitable for texture source,
+ should only be used with bge.texture.imageToArray(mode='F')
+
+ .. attribute:: zbuff
+
+ use depth component of viewport as grey scale color - suitable for texture source
+
.. class:: Texture(gameObj)
Texture objects
0 to force a fixed 0 color channel and 1 to force a fixed 255 color channel.
Example: "BGR" will return 3 bytes per pixel with the Blue, Green and Red channels in that order.
"RGB1" will return 4 bytes per pixel with the Red, Green, Blue channels in that order and the alpha channel forced to 255.
+ A special mode "F" allows to return the image as an array of float. This mode should only be used to retrieve
+ the depth buffer of the ImageViewport and ImageRender object.
The default mode is "RGBA".
+
:type mode: string
:rtype: :class:`~bgl.buffer`
:return: A object representing the image as one dimensional array of bytes of size (pixel_size*width*height),
line by line starting from the bottom of the image. The pixel size and format is determined by the mode
- parameter.
+ parameter. For mode 'F', the array is a one dimensional array of float of size (width*height).
.. function:: materialID(object,name)
virtual unsigned int filter (unsigned int * src, short x, short y,
short * size, unsigned int pixSize, unsigned int val = 0)
{ return val; }
+ /// filter pixel, source float buffer
+ virtual unsigned int filter (float * src, short x, short y,
+ short * size, unsigned int pixSize, unsigned int val = 0)
+ { return val; }
/// get source pixel size
virtual unsigned int getPixelSize (void) { return 1; }
#include "FilterBase.h"
-
/// class for RGB24 conversion
class FilterRGB24 : public FilterBase
{
{ VT_RGBA(val,src[2],src[1],src[0],0xFF); return val; }
};
+/// class for Z_buffer conversion
+class FilterZZZA : public FilterBase
+{
+public:
+ /// constructor
+ FilterZZZA (void) {}
+ /// destructor
+ virtual ~FilterZZZA (void) {}
+
+ /// get source pixel size
+ virtual unsigned int getPixelSize (void) { return 1; }
+
+protected:
+ /// filter pixel, source float buffer
+ virtual unsigned int filter (float * src, short x, short y,
+ short * size, unsigned int pixSize, unsigned int val)
+ {
+ // calculate gray value
+ // convert float to unsigned char
+ unsigned int depth = int(src[0] * 255);
+ // return depth scale value
+ VT_R(val) = depth;
+ VT_G(val) = depth;
+ VT_B(val) = depth;
+ VT_A(val) = 0xFF;
+
+ return val;
+ }
+};
+
+
+/// class for Z_buffer conversion
+class FilterDEPTH : public FilterBase
+{
+public:
+ /// constructor
+ FilterDEPTH (void) {}
+ /// destructor
+ virtual ~FilterDEPTH (void) {}
+
+ /// get source pixel size
+ virtual unsigned int getPixelSize (void) { return 1; }
+
+protected:
+ /// filter pixel, source float buffer
+ virtual unsigned int filter (float * src, short x, short y,
+ short * size, unsigned int pixSize, unsigned int val)
+ {
+ // Copy the float value straight away
+ // The user can retrieve the original float value by using
+ // 'F' mode in BGL buffer
+ memcpy(&val, src, sizeof (unsigned int));
+ return val;
+ }
+};
+
+
+
+
/// class for YV12 conversion
class FilterYV12 : public FilterBase
{
// constructor
ImageBase::ImageBase (bool staticSrc) : m_image(NULL), m_imgSize(0),
m_avail(false), m_scale(false), m_scaleChange(false), m_flip(false),
+m_zbuff(false),
+m_depth(false),
m_staticSources(staticSrc), m_pyfilter(NULL)
{
m_size[0] = m_size[1] = 0;
{
buffer = BGL_MakeBuffer( GL_BYTE, 1, &dimensions, image);
}
+ else if (!strcasecmp(mode, "F"))
+ {
+ // this mode returns the image as an array of float.
+ // This makes sense ONLY for the depth buffer:
+ // source = VideoTexture.ImageViewport()
+ // source.depth = True
+ // depth = VideoTexture.imageToArray(source, 'F')
+
+ // adapt dimension from byte to float
+ dimensions /= sizeof(float);
+ buffer = BGL_MakeBuffer( GL_FLOAT, 1, &dimensions, image);
+ }
else
{
int i, c, ncolor, pixels;
return 0;
}
+// get zbuff
+PyObject * Image_getZbuff (PyImage * self, void * closure)
+{
+ if (self->m_image != NULL && self->m_image->getZbuff()) Py_RETURN_TRUE;
+ else Py_RETURN_FALSE;
+}
+
+// set zbuff
+int Image_setZbuff (PyImage * self, PyObject * value, void * closure)
+{
+ // check parameter, report failure
+ if (value == NULL || !PyBool_Check(value))
+ {
+ PyErr_SetString(PyExc_TypeError, "The value must be a bool");
+ return -1;
+ }
+ // set scale
+ if (self->m_image != NULL) self->m_image->setZbuff(value == Py_True);
+ // success
+ return 0;
+}
+
+// get depth
+PyObject * Image_getDepth (PyImage * self, void * closure)
+{
+ if (self->m_image != NULL && self->m_image->getDepth()) Py_RETURN_TRUE;
+ else Py_RETURN_FALSE;
+}
+
+// set depth
+int Image_setDepth (PyImage * self, PyObject * value, void * closure)
+{
+ // check parameter, report failure
+ if (value == NULL || !PyBool_Check(value))
+ {
+ PyErr_SetString(PyExc_TypeError, "The value must be a bool");
+ return -1;
+ }
+ // set scale
+ if (self->m_image != NULL) self->m_image->setDepth(value == Py_True);
+ // success
+ return 0;
+}
+
+
+
// get filter source object
PyObject *Image_getSource (PyImage *self, PyObject *args)
bool getFlip (void) { return m_flip; }
/// set vertical flip
void setFlip (bool flip) { m_flip = flip; }
+ /// get Z buffer
+ bool getZbuff (void) { return m_zbuff; }
+ /// set Z buffer
+ void setZbuff (bool zbuff) { m_zbuff = zbuff; }
+ /// get depth
+ bool getDepth (void) { return m_depth; }
+ /// set depth
+ void setDepth (bool depth) { m_depth = depth; }
/// get source object
PyImage * getSource (const char * id);
bool m_scaleChange;
/// flip image vertically
bool m_flip;
+ /// use the Z buffer as a texture
+ bool m_zbuff;
+ /// extract the Z buffer with unisgned int precision
+ bool m_depth;
/// source image list
ImageSourceList m_sources;
PyObject *Image_getSource (PyImage *self, PyObject *args);
// set filter source object
PyObject *Image_setSource (PyImage *self, PyObject *args);
-
+// get Z buffer
+PyObject * Image_getZbuff (PyImage * self, void * closure);
+// set Z buffer
+int Image_setZbuff (PyImage * self, PyObject * value, void * closure);
+// get depth
+PyObject * Image_getDepth (PyImage * self, void * closure);
+// set depth
+int Image_setDepth (PyImage * self, PyObject * value, void * closure);
+
// get pixel filter object
PyObject *Image_getFilter (PyImage *self, void *closure);
// set pixel filter object
{(char*)"size", (getter)Image_getSize, NULL, (char*)"image size", NULL},
{(char*)"scale", (getter)Image_getScale, (setter)Image_setScale, (char*)"fast scale of image (near neighbor)", NULL},
{(char*)"flip", (getter)Image_getFlip, (setter)Image_setFlip, (char*)"flip image vertically", NULL},
+ {(char*)"zbuff", (getter)Image_getZbuff, (setter)Image_setZbuff, (char*)"use depth buffer as texture", NULL},
+ {(char*)"depth", (getter)Image_getDepth, (setter)Image_setDepth, (char*)"get depth information from z-buffer using unsigned int precision", NULL},
{(char*)"filter", (getter)Image_getFilter, (setter)Image_setFilter, (char*)"pixel filter", NULL},
{NULL}
};
{(char*)"size", (getter)Image_getSize, NULL, (char*)"image size", NULL},
{(char*)"scale", (getter)Image_getScale, (setter)Image_setScale, (char*)"fast scale of image (near neighbor)", NULL},
{(char*)"flip", (getter)Image_getFlip, (setter)Image_setFlip, (char*)"flip image vertically", NULL},
+ {(char*)"zbuff", (getter)Image_getZbuff, (setter)Image_setZbuff, (char*)"use depth buffer as texture", NULL},
+ {(char*)"depth", (getter)Image_getDepth, (setter)Image_setDepth, (char*)"get depth information from z-buffer using unsigned int precision", NULL},
{(char*)"filter", (getter)Image_getFilter, (setter)Image_setFilter, (char*)"pixel filter", NULL},
{NULL}
};
//glGetIntegerv(GL_VIEWPORT, m_viewport);
// create buffer for viewport image
+ // Warning: this buffer is also used to get the depth buffer as an array of
+ // float (1 float = 4 bytes per pixel)
m_viewportImage = new BYTE [4 * getViewportSize()[0] * getViewportSize()[1]];
// set attributes
setWhole(false);
// destructor
ImageViewport::~ImageViewport (void)
-{ delete [] m_viewportImage; }
+{
+ delete [] m_viewportImage;
+}
// use whole viewport to capture image
}
// if texture can be directly created
if (texId != 0 && m_pyfilter == NULL && m_capSize[0] == calcSize(m_capSize[0])
- && m_capSize[1] == calcSize(m_capSize[1]) && !m_flip)
+ && m_capSize[1] == calcSize(m_capSize[1]) && !m_flip && !m_zbuff && !m_depth)
{
// just copy current viewport to texture
glBindTexture(GL_TEXTURE_2D, texId);
// otherwise copy viewport to buffer, if image is not available
else if (!m_avail)
{
+ if (m_zbuff)
+ {
+ // Use read pixels with the depth buffer
+ // *** misusing m_viewportImage here, but since it has the correct size
+ // (4 bytes per pixel = size of float) and we just need it to apply
+ // the filter, it's ok
+ glReadPixels(m_upLeft[0], m_upLeft[1], (GLsizei)m_capSize[0], (GLsizei)m_capSize[1],
+ GL_DEPTH_COMPONENT, GL_FLOAT, m_viewportImage);
+ // filter loaded data
+ FilterZZZA filt;
+ filterImage(filt, (float *)m_viewportImage, m_capSize);
+ }
+ else
+
+ if (m_depth)
+ {
+ // Use read pixels with the depth buffer
+ // See warning above about m_viewportImage.
+ glReadPixels(m_upLeft[0], m_upLeft[1], (GLsizei)m_capSize[0], (GLsizei)m_capSize[1],
+ GL_DEPTH_COMPONENT, GL_FLOAT, m_viewportImage);
+ // filter loaded data
+ FilterDEPTH filt;
+ filterImage(filt, (float *)m_viewportImage, m_capSize);
+ }
+ else
+
// get frame buffer data
if (m_alpha)
{
{(char*)"size", (getter)Image_getSize, NULL, (char*)"image size", NULL},
{(char*)"scale", (getter)Image_getScale, (setter)Image_setScale, (char*)"fast scale of image (near neighbor)", NULL},
{(char*)"flip", (getter)Image_getFlip, (setter)Image_setFlip, (char*)"flip image vertically", NULL},
+ {(char*)"zbuff", (getter)Image_getZbuff, (setter)Image_setZbuff, (char*)"use depth buffer as texture", NULL},
+ {(char*)"depth", (getter)Image_getDepth, (setter)Image_setDepth, (char*)"get depth information from z-buffer as array of float", NULL},
{(char*)"filter", (getter)Image_getFilter, (setter)Image_setFilter, (char*)"pixel filter", NULL},
{NULL}
};