• Immutable Page
  • Info
  • Attachments

GLTexture

/**
 * Returns a 2D matrix adjusted texture co-ordinate x
 */
#define COMP_TEX_COORD_X(m, vx) ((m).xx * (vx) + (m).x0)
/**
 * Returns a 2D matrix adjusted texture co-ordinate y
 */
#define COMP_TEX_COORD_Y(m, vy) ((m).yy * (vy) + (m).y0)

/**
 * Returns a 2D matrix adjusted texture co-ordinate xy
 */
#define COMP_TEX_COORD_XY(m, vx, vy)            \
    ((m).xx * (vx) + (m).xy * (vy) + (m).x0)
/**
 * Returns a 2D matrix adjusted texture co-ordinate yx
 */
#define COMP_TEX_COORD_YX(m, vx, vy)            \
    ((m).yx * (vx) + (m).yy * (vy) + (m).y0)

/**
 * Class which represents an openGL texture
 */
class GLTexture : public CompRect {
    public:

        typedef enum {
            Fast,
            Good
        } Filter;

        typedef struct {
            float xx; float yx;
            float xy; float yy;
            float x0; float y0;
        } Matrix;

        typedef std::vector<Matrix> MatrixList;

        /**
         * Class which represents a list of openGL textures,
         * usually used for texture tiling
         */
        class List : public std::vector <GLTexture *> {

            public:
                List ();
                List (unsigned int);
                List (const List &);
                ~List ();

                List & operator= (const List &);

                void clear ();
        };

        typedef boost::function<List (Pixmap, int, int, int)> BindPixmapProc;
        typedef unsigned int BindPixmapHandle;

    public:

        /**
         * Returns the openGL texture name
         */
        GLuint name () const;

        /**
         * Returns the openGL texture target
         */
        GLenum target () const;

        /**
         * Returns the openGL texture filter
         */
        GLenum filter () const;

        /**
         * Returns a 2D 2x3 matrix describing the transformation of
         * the texture
         */
        const Matrix & matrix () const;

        /**
         * Establishes the texture as the current drawing texture
         * in the openGL context
         *
         * @param filter Defines what kind of filtering level this
         * texture should be drawn with
         */
        virtual void enable (Filter filter);

        /**
         * Stops the textures from being the current drawing texture
         * in the openGL context
         */
        virtual void disable ();

        /**
         * Returns true if this texture is MipMapped
         */
        bool mipmap () const;

        /**
         * Sets if this texture should be MipMapped
         */
        void setMipmap (bool);

        /**
         * Sets the openGL filter which should be used on this
         * texture
         */
        void setFilter (GLenum);
        void setWrap (GLenum);

        /**
         * Increases the reference count of a texture
         */
        static void incRef (GLTexture *);

        /**
         * Decreases the reference count of a texture
         */
        static void decRef (GLTexture *);

        /**
         * Returns a GLTexture::List with the contents of
         * some pixmap
         *
         * @param pixmap Specifies the pixmap data which should be converted
         * into texture data
         * @param width Specifies the width of the texture
         * @param height Specifies the height of the texture
         * @param depth Specifies the color depth of the texture
         */
        static List bindPixmapToTexture (Pixmap pixmap,
                                         int width,
                                         int height,
                                         int depth);

        /**
         * Returns a GLTexture::List with the contents of of
         * a raw image buffer
         *
         * @param image Specifies a raw image buffer which should be converted
         * into texture data
         * @param size Specifies the size of this new texture
         */
        static List imageBufferToTexture (const char *image,
                                          CompSize   size);

        static List imageDataToTexture (const char *image,
                                        CompSize   size,
                                        GLenum     format,
                                        GLenum     type);

        /**
         * Uses image loading plugins to read an image from the disk and
         * return a GLTexture::List with its contents
         *
         * @param imageFileName The filename of the image
         * @param size          The size of this new texture
         */
        static List readImageToTexture (CompString &imageFileName,
                                        CompSize   &size);

        friend class PrivateTexture;

    protected:
        GLTexture ();
        virtual ~GLTexture ();

        void setData (GLenum target, Matrix &m, bool mipmap);

    private:
        PrivateTexture *priv;
};

Using lists of textures

In order to overcome hardware maximum texture size limitations, compiz supports tiled texturing. As such, all texture generation functions (such as bindPixmapTotexture, imageDataToTexture, readImageToTexture, etc) will all return a GLTexture:List. When rendering these textures you must loop through each texture in the list in order that you render each part of the texture that the user sees.

On especially small textures, it is ok to directly access the first item in the list for the sake of optimization, however whenever it is not clear what the size of the texture is, you should always loop the list.

Enabling and disabling the texture, and drawing it with openGL

Because there are different texture binding backends, it is not safe to enable the texture target using openGL directly. Instead, you should use the ::enable () and ::disable () member functions. The ::enable () member function also allows you to specifiy a level of texture filtering, either Fast or Good. If you are drawing the texture at a smaller size then the render size, then it should be safe to use the Fast filter.

Getting openGL information about the texture

It is possible to get the ::name () and ::target () of the texture, to use that data for openGL purposes

Mipmapping

Compiz also supports a mipmapping filter to make textures appear smoother when viewed at angles. To enable this you can use the ::setMipmap and ::mipmap functions in order to enable this. Mipmapping is not available on certain hardware. In this case, the function will simply fail silently.

Texture Matrix manipulation

Since all textures are 2D, it is possible to perform basic 2D Manipulation operations on the texture.

Member variable

Function

.x0

X Position on the screen

.y0

Y Position on the screen

.xx

X Scale Factor

.yy

Y Scale Factor

.xy

X Shear Factor

.yx

Y Shear Factor

The COMP_TEX_COORD functions return matrix-adjusted values for texture positions. The "real" value of your co-ordinate on the texture itself should be inputted into these functions, and these functions will return the appropriate number to feed to functions such as glTexCoord2f.

Overloading the binding of textures

For whatever reason, you may wish to write your own texture binding method which overloads the standard GLX_ext_texture_from_pixmap method. It is possible to do this, by overloading the ::enable () and ::disable () methods of the GLTexture through your own class. Then on your plugin's init function you should use GLTexture::BindPixmapHandle hnd = GLScreen::get (screen)->registerBindPixmap (YourPixmap::bindPixmapToTexture) and on fini you must also call GLScreen::get (screen)->unregistrerBindPixmap (hnd).

A sample implementation can be found in the Copy To Texture plugin.

Development/zero-nine/OpenGLClasses/GLTexture (last edited 2010-10-17 03:00:43 by 58-7-165-35)