856 lines
21 KiB
C
856 lines
21 KiB
C
/* $Id: texutil.c,v 1.15 2001/03/18 08:53:50 gareth Exp $ */
|
|
|
|
/*
|
|
* Mesa 3-D graphics library
|
|
* Version: 3.5
|
|
*
|
|
* Copyright (C) 1999-2001 Brian Paul All Rights Reserved.
|
|
*
|
|
* Permission is hereby granted, free of charge, to any person obtaining a
|
|
* copy of this software and associated documentation files (the "Software"),
|
|
* to deal in the Software without restriction, including without limitation
|
|
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
|
* and/or sell copies of the Software, and to permit persons to whom the
|
|
* Software is furnished to do so, subject to the following conditions:
|
|
*
|
|
* The above copyright notice and this permission notice shall be included
|
|
* in all copies or substantial portions of the Software.
|
|
*
|
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
|
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
|
* BRIAN PAUL BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN
|
|
* AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
|
* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
|
*
|
|
* Authors:
|
|
* Gareth Hughes <gareth@valinux.com>
|
|
*/
|
|
|
|
#ifdef PC_HEADER
|
|
#include "all.h"
|
|
#else
|
|
#include "glheader.h"
|
|
#include "context.h"
|
|
#include "enums.h"
|
|
#include "image.h"
|
|
#include "macros.h"
|
|
#include "mem.h"
|
|
#include "mtypes.h"
|
|
#include "texformat.h"
|
|
#include "texutil.h"
|
|
#endif
|
|
|
|
#define DBG 0
|
|
|
|
|
|
struct gl_texture_convert {
|
|
GLint xoffset, yoffset, zoffset; /* Subimage offset */
|
|
GLint width, height, depth; /* Subimage region */
|
|
|
|
GLint imageWidth, imageHeight; /* Full image dimensions */
|
|
GLenum format, type;
|
|
|
|
const struct gl_pixelstore_attrib *packing;
|
|
|
|
const GLvoid *srcImage;
|
|
GLvoid *dstImage;
|
|
|
|
GLint index;
|
|
};
|
|
|
|
typedef GLboolean (*convert_func)( struct gl_texture_convert *convert );
|
|
|
|
#define CONVERT_STRIDE_BIT 0x1
|
|
#define CONVERT_PACKING_BIT 0x2
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* RGBA8888 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLuint
|
|
#define DST_TEXELS_PER_DWORD 1
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( src[3], src[2], src[1], src[0] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_rgba8888_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( src[0], src[1], src[2], src[3] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) CONVERT_TEXEL( src )
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_abgr8888_to_rgba8888
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( src[0], src[1], src[2], 0xff )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) CONVERT_TEXEL( src )
|
|
|
|
#define SRC_TEXEL_BYTES 3
|
|
|
|
#define TAG(x) x##_bgr888_to_rgba8888
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_RGBA8888( name ) \
|
|
static GLboolean \
|
|
convert_##name##_rgba8888( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_ABGR_EXT && \
|
|
convert->type == GL_UNSIGNED_INT_8_8_8_8_REV ) \
|
|
{ \
|
|
tab = name##_tab_rgba8888_direct; \
|
|
} \
|
|
else if ( convert->format == GL_RGBA && \
|
|
( convert->type == GL_UNSIGNED_BYTE || \
|
|
convert->type == GL_UNSIGNED_INT_8_8_8_8 ) ) \
|
|
{ \
|
|
tab = name##_tab_abgr8888_to_rgba8888; \
|
|
} \
|
|
else if ( convert->format == GL_RGB && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_bgr888_to_rgba8888; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_RGBA8888( texsubimage2d )
|
|
CONVERT_RGBA8888( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* ARGB8888 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLuint
|
|
#define DST_TEXELS_PER_DWORD 1
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( src[3], src[2], src[1], src[0] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_argb8888_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( src[3], src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) CONVERT_TEXEL( src )
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_abgr8888_to_argb8888
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_8888( 0xff, src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) CONVERT_TEXEL( src )
|
|
|
|
#define SRC_TEXEL_BYTES 3
|
|
|
|
#define TAG(x) x##_bgr888_to_argb8888
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_ARGB8888( name ) \
|
|
static GLboolean \
|
|
convert_##name##_argb8888( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_BGRA && \
|
|
convert->type == GL_UNSIGNED_INT_8_8_8_8_REV ) \
|
|
{ \
|
|
tab = name##_tab_argb8888_direct; \
|
|
} \
|
|
else if ( convert->format == GL_RGBA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_abgr8888_to_argb8888; \
|
|
} \
|
|
else if ( convert->format == GL_RGB && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_bgr888_to_argb8888; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_ARGB8888( texsubimage2d )
|
|
CONVERT_ARGB8888( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* RGB888 textures:
|
|
*/
|
|
|
|
static GLboolean
|
|
convert_texsubimage2d_rgb888( struct gl_texture_convert *convert )
|
|
{
|
|
/* This is a placeholder for now...
|
|
*/
|
|
return GL_FALSE;
|
|
}
|
|
|
|
static GLboolean
|
|
convert_texsubimage3d_rgb888( struct gl_texture_convert *convert )
|
|
{
|
|
/* This is a placeholder for now...
|
|
*/
|
|
return GL_FALSE;
|
|
}
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* RGB565 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLushort
|
|
#define DST_TEXELS_PER_DWORD 2
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_565( src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 2
|
|
|
|
#define TAG(x) x##_rgb565_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_565( src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_565( src[0], src[1], src[2] )) | \
|
|
(PACK_COLOR_565( src[3], src[4], src[5] ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 3
|
|
|
|
#define TAG(x) x##_bgr888_to_rgb565
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_565( src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_565( src[0], src[1], src[2] )) | \
|
|
(PACK_COLOR_565( src[4], src[5], src[6] ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_abgr8888_to_rgb565
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_RGB565( name ) \
|
|
static GLboolean \
|
|
convert_##name##_rgb565( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_RGB && \
|
|
convert->type == GL_UNSIGNED_SHORT_5_6_5 ) \
|
|
{ \
|
|
tab = name##_tab_rgb565_direct; \
|
|
} \
|
|
else if ( convert->format == GL_RGB && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_bgr888_to_rgb565; \
|
|
} \
|
|
else if ( convert->format == GL_RGBA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_abgr8888_to_rgb565; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_RGB565( texsubimage2d )
|
|
CONVERT_RGB565( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* ARGB4444 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLushort
|
|
#define DST_TEXELS_PER_DWORD 2
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_4444( src[3], src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 2
|
|
|
|
#define TAG(x) x##_argb4444_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_4444( src[3], src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_4444( src[3], src[0], src[1], src[2] )) | \
|
|
(PACK_COLOR_4444( src[7], src[4], src[5], src[6] ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_rgba8888_to_argb4444
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_ARGB4444( name ) \
|
|
static GLboolean \
|
|
convert_##name##_argb4444( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_BGRA && \
|
|
convert->type == GL_UNSIGNED_SHORT_4_4_4_4_REV ) \
|
|
{ \
|
|
tab = name##_tab_argb4444_direct; \
|
|
} \
|
|
else if ( convert->format == GL_RGBA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_rgba8888_to_argb4444; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_ARGB4444( texsubimage2d )
|
|
CONVERT_ARGB4444( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* ARGB1555 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLushort
|
|
#define DST_TEXELS_PER_DWORD 2
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_1555( src[3], src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 2
|
|
|
|
#define TAG(x) x##_argb1555_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_1555( src[3], src[0], src[1], src[2] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_1555( src[3], src[0], src[1], src[2] )) | \
|
|
(PACK_COLOR_1555( src[7], src[4], src[5], src[6] ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 4
|
|
|
|
#define TAG(x) x##_rgba8888_to_argb1555
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_ARGB1555( name ) \
|
|
static GLboolean \
|
|
convert_##name##_argb1555( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_BGRA && \
|
|
convert->type == GL_UNSIGNED_SHORT_1_5_5_5_REV ) \
|
|
{ \
|
|
tab = name##_tab_argb1555_direct; \
|
|
} \
|
|
else if ( convert->format == GL_RGBA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_rgba8888_to_argb1555; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_ARGB1555( texsubimage2d )
|
|
CONVERT_ARGB1555( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* AL88 textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLushort
|
|
#define DST_TEXELS_PER_DWORD 2
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_88( src[0], src[1] )
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 2
|
|
|
|
#define TAG(x) x##_al88_direct
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_88( src[0], 0x00 )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_88( src[0], 0x00 )) | \
|
|
(PACK_COLOR_88( src[1], 0x00 ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 1
|
|
|
|
#define TAG(x) x##_a8_to_al88
|
|
#define PRESERVE_DST_TYPE
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_TEXEL( src ) \
|
|
PACK_COLOR_88( 0xff, src[0] )
|
|
|
|
#define CONVERT_TEXEL_DWORD( src ) \
|
|
((PACK_COLOR_88( 0xff, src[0] )) | \
|
|
(PACK_COLOR_88( 0xff, src[1] ) << 16))
|
|
|
|
#define SRC_TEXEL_BYTES 1
|
|
|
|
#define TAG(x) x##_l8_to_al88
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_AL88( name ) \
|
|
static GLboolean \
|
|
convert_##name##_al88( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( convert->format == GL_LUMINANCE_ALPHA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_al88_direct; \
|
|
} \
|
|
else if ( convert->format == GL_ALPHA && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_a8_to_al88; \
|
|
} \
|
|
else if ( convert->format == GL_LUMINANCE && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_l8_to_al88; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_AL88( texsubimage2d )
|
|
CONVERT_AL88( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* RGB332 textures:
|
|
*/
|
|
|
|
static GLboolean
|
|
convert_texsubimage2d_rgb332( struct gl_texture_convert *convert )
|
|
{
|
|
/* This is a placeholder for now...
|
|
*/
|
|
return GL_FALSE;
|
|
}
|
|
|
|
static GLboolean
|
|
convert_texsubimage3d_rgb332( struct gl_texture_convert *convert )
|
|
{
|
|
/* This is a placeholder for now...
|
|
*/
|
|
return GL_FALSE;
|
|
}
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* CI8 (and all other single-byte texel) textures:
|
|
*/
|
|
|
|
#define DST_TYPE GLubyte
|
|
#define DST_TEXELS_PER_DWORD 4
|
|
|
|
#define CONVERT_TEXEL( src ) src[0]
|
|
|
|
#define CONVERT_DIRECT
|
|
|
|
#define SRC_TEXEL_BYTES 1
|
|
|
|
#define TAG(x) x##_ci8_direct
|
|
#include "texutil_tmp.h"
|
|
|
|
|
|
#define CONVERT_CI8( name ) \
|
|
static GLboolean \
|
|
convert_##name##_ci8( struct gl_texture_convert *convert ) \
|
|
{ \
|
|
convert_func *tab; \
|
|
GLint index = convert->index; \
|
|
\
|
|
if ( ( convert->format == GL_ALPHA || \
|
|
convert->format == GL_LUMINANCE || \
|
|
convert->format == GL_INTENSITY || \
|
|
convert->format == GL_COLOR_INDEX ) && \
|
|
convert->type == GL_UNSIGNED_BYTE ) \
|
|
{ \
|
|
tab = name##_tab_ci8_direct; \
|
|
} \
|
|
else \
|
|
{ \
|
|
/* Can't handle this source format/type combination */ \
|
|
return GL_FALSE; \
|
|
} \
|
|
\
|
|
return tab[index]( convert ); \
|
|
}
|
|
|
|
CONVERT_CI8( texsubimage2d )
|
|
CONVERT_CI8( texsubimage3d )
|
|
|
|
|
|
|
|
/* ================================================================
|
|
* Global entry points
|
|
*/
|
|
|
|
static convert_func gl_convert_texsubimage2d_tab[] = {
|
|
convert_texsubimage2d_rgba8888,
|
|
convert_texsubimage2d_argb8888,
|
|
convert_texsubimage2d_rgb888,
|
|
convert_texsubimage2d_rgb565,
|
|
convert_texsubimage2d_argb4444,
|
|
convert_texsubimage2d_argb1555,
|
|
convert_texsubimage2d_al88,
|
|
convert_texsubimage2d_rgb332,
|
|
convert_texsubimage2d_ci8, /* These are all the same... */
|
|
convert_texsubimage2d_ci8,
|
|
convert_texsubimage2d_ci8,
|
|
convert_texsubimage2d_ci8,
|
|
};
|
|
|
|
static convert_func gl_convert_texsubimage3d_tab[] = {
|
|
convert_texsubimage3d_rgba8888,
|
|
convert_texsubimage3d_argb8888,
|
|
convert_texsubimage3d_rgb888,
|
|
convert_texsubimage3d_rgb565,
|
|
convert_texsubimage3d_argb4444,
|
|
convert_texsubimage3d_argb1555,
|
|
convert_texsubimage3d_al88,
|
|
convert_texsubimage3d_rgb332,
|
|
convert_texsubimage3d_ci8, /* These are all the same... */
|
|
convert_texsubimage3d_ci8,
|
|
convert_texsubimage3d_ci8,
|
|
convert_texsubimage3d_ci8,
|
|
};
|
|
|
|
|
|
/* See if we need to care about the pixel store attributes when we're
|
|
* converting the texture image. This should be stored as
|
|
* packing->_SomeBoolean and updated when the values change, to avoid
|
|
* testing every time...
|
|
*/
|
|
static INLINE GLboolean
|
|
convert_needs_packing( const struct gl_pixelstore_attrib *packing,
|
|
GLenum format, GLenum type )
|
|
{
|
|
if ( ( packing->Alignment == 1 ||
|
|
( packing->Alignment == 4 && /* Pick up the common Q3A case... */
|
|
format == GL_RGBA && type == GL_UNSIGNED_BYTE ) ) &&
|
|
packing->RowLength == 0 &&
|
|
packing->SkipPixels == 0 &&
|
|
packing->SkipRows == 0 &&
|
|
packing->ImageHeight == 0 &&
|
|
packing->SkipImages == 0 &&
|
|
packing->SwapBytes == GL_FALSE &&
|
|
packing->LsbFirst == GL_FALSE ) {
|
|
return GL_FALSE;
|
|
} else {
|
|
return GL_TRUE;
|
|
}
|
|
}
|
|
|
|
|
|
GLboolean
|
|
_mesa_convert_texsubimage1d( GLint mesaFormat,
|
|
GLint xoffset,
|
|
GLint width,
|
|
GLenum format, GLenum type,
|
|
const struct gl_pixelstore_attrib *packing,
|
|
const GLvoid *srcImage, GLvoid *dstImage )
|
|
{
|
|
struct gl_texture_convert convert;
|
|
|
|
ASSERT( packing );
|
|
ASSERT( srcImage );
|
|
ASSERT( dstImage );
|
|
|
|
ASSERT( mesaFormat >= MESA_FORMAT_RGBA8888 );
|
|
ASSERT( mesaFormat <= MESA_FORMAT_CI8 );
|
|
|
|
/* Make it easier to pass all the parameters around.
|
|
*/
|
|
convert.xoffset = xoffset;
|
|
convert.yoffset = 0;
|
|
convert.width = width;
|
|
convert.height = 1;
|
|
convert.format = format;
|
|
convert.type = type;
|
|
convert.packing = packing;
|
|
convert.srcImage = srcImage;
|
|
convert.dstImage = dstImage;
|
|
|
|
convert.index = 0;
|
|
|
|
if ( convert_needs_packing( packing, format, type ) )
|
|
convert.index |= CONVERT_PACKING_BIT;
|
|
|
|
return gl_convert_texsubimage2d_tab[mesaFormat]( &convert );
|
|
}
|
|
|
|
GLboolean
|
|
_mesa_convert_texsubimage2d( GLint mesaFormat,
|
|
GLint xoffset, GLint yoffset,
|
|
GLint width, GLint height,
|
|
GLint imageWidth,
|
|
GLenum format, GLenum type,
|
|
const struct gl_pixelstore_attrib *packing,
|
|
const GLvoid *srcImage, GLvoid *dstImage )
|
|
{
|
|
struct gl_texture_convert convert;
|
|
|
|
ASSERT( packing );
|
|
ASSERT( srcImage );
|
|
ASSERT( dstImage );
|
|
|
|
ASSERT( mesaFormat >= MESA_FORMAT_RGBA8888 );
|
|
ASSERT( mesaFormat <= MESA_FORMAT_CI8 );
|
|
|
|
/* Make it easier to pass all the parameters around.
|
|
*/
|
|
convert.xoffset = xoffset;
|
|
convert.yoffset = yoffset;
|
|
convert.width = width;
|
|
convert.height = height;
|
|
convert.imageWidth = imageWidth;
|
|
convert.format = format;
|
|
convert.type = type;
|
|
convert.packing = packing;
|
|
convert.srcImage = srcImage;
|
|
convert.dstImage = dstImage;
|
|
|
|
convert.index = 0;
|
|
|
|
if ( convert_needs_packing( packing, format, type ) )
|
|
convert.index |= CONVERT_PACKING_BIT;
|
|
|
|
if ( width != imageWidth )
|
|
convert.index |= CONVERT_STRIDE_BIT;
|
|
|
|
return gl_convert_texsubimage2d_tab[mesaFormat]( &convert );
|
|
}
|
|
|
|
GLboolean
|
|
_mesa_convert_texsubimage3d( GLint mesaFormat,
|
|
GLint xoffset, GLint yoffset, GLint zoffset,
|
|
GLint width, GLint height, GLint depth,
|
|
GLint imageWidth, GLint imageHeight,
|
|
GLenum format, GLenum type,
|
|
const struct gl_pixelstore_attrib *packing,
|
|
const GLvoid *srcImage, GLvoid *dstImage )
|
|
{
|
|
struct gl_texture_convert convert;
|
|
|
|
ASSERT( packing );
|
|
ASSERT( srcImage );
|
|
ASSERT( dstImage );
|
|
|
|
ASSERT( mesaFormat >= MESA_FORMAT_RGBA8888 );
|
|
ASSERT( mesaFormat <= MESA_FORMAT_CI8 );
|
|
|
|
/* Make it easier to pass all the parameters around.
|
|
*/
|
|
convert.xoffset = xoffset;
|
|
convert.yoffset = yoffset;
|
|
convert.zoffset = zoffset;
|
|
convert.width = width;
|
|
convert.height = height;
|
|
convert.depth = depth;
|
|
convert.imageWidth = imageWidth;
|
|
convert.imageHeight = imageHeight;
|
|
convert.format = format;
|
|
convert.type = type;
|
|
convert.packing = packing;
|
|
convert.srcImage = srcImage;
|
|
convert.dstImage = dstImage;
|
|
|
|
convert.index = 0;
|
|
|
|
if ( convert_needs_packing( packing, format, type ) )
|
|
convert.index |= CONVERT_PACKING_BIT;
|
|
|
|
if ( width != imageWidth || height != imageHeight )
|
|
convert.index |= CONVERT_STRIDE_BIT;
|
|
|
|
return gl_convert_texsubimage3d_tab[mesaFormat]( &convert );
|
|
}
|
|
|
|
|
|
|
|
/* Nearest filtering only (for broken hardware that can't support
|
|
* all aspect ratios). This can be made a lot faster, but I don't
|
|
* really care enough...
|
|
*/
|
|
void _mesa_rescale_teximage2d( const struct gl_texture_format *texFormat,
|
|
GLint srcWidth, GLint srcHeight,
|
|
GLint dstWidth, GLint dstHeight,
|
|
const GLvoid *srcImage, GLvoid *dstImage )
|
|
{
|
|
GLint row, col;
|
|
|
|
#define INNER_LOOP( HOP, WOP ) \
|
|
for ( row = 0 ; row < dstHeight ; row++ ) { \
|
|
GLint srcRow = row HOP hScale; \
|
|
for ( col = 0 ; col < dstWidth ; col++ ) { \
|
|
GLint srcCol = col WOP wScale; \
|
|
*dst++ = src[srcRow * srcWidth + srcCol]; \
|
|
} \
|
|
} \
|
|
|
|
#define RESCALE_IMAGE( TYPE ) \
|
|
do { \
|
|
const TYPE *src = (const TYPE *)srcImage; \
|
|
TYPE *dst = (TYPE *)dstImage; \
|
|
\
|
|
if ( srcHeight <= dstHeight ) { \
|
|
const GLint hScale = dstHeight / srcHeight; \
|
|
if ( srcWidth <= dstWidth ) { \
|
|
const GLint wScale = dstWidth / srcWidth; \
|
|
INNER_LOOP( /, / ); \
|
|
} \
|
|
else { \
|
|
const GLint wScale = srcWidth / dstWidth; \
|
|
INNER_LOOP( /, * ); \
|
|
} \
|
|
} \
|
|
else { \
|
|
const GLint hScale = srcHeight / dstHeight; \
|
|
if ( srcWidth <= dstWidth ) { \
|
|
const GLint wScale = dstWidth / srcWidth; \
|
|
INNER_LOOP( *, / ); \
|
|
} \
|
|
else { \
|
|
const GLint wScale = srcWidth / dstWidth; \
|
|
INNER_LOOP( *, * ); \
|
|
} \
|
|
} \
|
|
} while (0)
|
|
|
|
switch ( texFormat->TexelBytes ) {
|
|
case 4:
|
|
RESCALE_IMAGE( GLuint );
|
|
break;
|
|
|
|
case 2:
|
|
RESCALE_IMAGE( GLushort );
|
|
break;
|
|
|
|
case 1:
|
|
RESCALE_IMAGE( GLubyte );
|
|
break;
|
|
}
|
|
}
|