// Exercise a particular combination of image format, type and internal
// texture format.
// Return true for success, false for failure.
bool
PixelFormatsTest::TestCombination(GLenum format, GLenum type, GLint intFormat)
{
	const int numComps = NumberOfComponentsInFormat(format);
	const int width = 16;
	const int height = 16;
	int colorPos[4];
	ComponentPositions(format, colorPos);

	for (int comp = 0; comp < numComps; comp++) {
		if (colorPos[comp] >= 0) {
			// make original/incoming image
			const int comp2 = colorPos[comp];
			GLubyte *image = MakeImage(width, height, format, type, comp2);

			// render with image (texture / glDrawPixels)
			bool ok = DrawImage(width, height, format, type, intFormat, image);

			if (ok) {
				// check rendering
				ok = CheckRendering(width, height, comp, format, intFormat);
			}

			delete [] image;

			if (!ok) {
				return false;
			}
		}
	}

	return true;
}
// Check if the given image format and datatype are compatible.
// Also check for types/formats defined by GL extensions here.
bool
PixelFormatsTest::CompatibleFormatAndType(GLenum format, GLenum datatype) const
{
	// Special case: GL_BGR can't be used with packed types!
	// This has to do with putting the most color bits in red and green,
	// not blue.
	if (format == GL_BGR && IsPackedType(datatype))
		return false;

	if (datatype == GL_HALF_FLOAT_ARB && !haveHalfFloat)
		return false;

	if (format == GL_ABGR_EXT && !haveABGR)
		return false;

	// Special case: GL_ABGR_EXT can't be used with packed types
	// because the packed formats specs (which were all written after the
	// GL_EXT_abgr) explicitly say that the packed formats can only be used
	// with GL_RGB, GL_BGR, GL_RGBA, or GL_BGRA and do not mention
	// GL_ABGR_EXT.
	if (format == GL_ABGR_EXT && IsPackedType(datatype))
		return false;

	if (format == GL_RG && !haveRG)
		return false;

	if (datatype == GL_UNSIGNED_INT_5_9_9_9_REV && !haveTexSharedExp)
		return false;

	const int formatComps = NumberOfComponentsInFormat(format);
	const int typeComps = NumberOfComponentsInPackedType(datatype);
	return formatComps == typeComps || typeComps == 0;
}
Beispiel #3
0
// Check if the given image format and datatype are compatible.
// Also check for types/formats defined by GL extensions here.
bool
PixelFormatsTest::CompatibleFormatAndType(GLenum format, GLenum datatype) const
{
    // Special case: GL_BGR can't be used with packed types!
    // This has to do with putting the most color bits in red and green,
    // not blue.
    if (format == GL_BGR && IsPackedType(datatype))
        return false;

#ifdef GL_ARB_half_float_pixel
    if (datatype == GL_HALF_FLOAT_ARB && !haveHalfFloat)
        return false;
#endif

#ifdef GL_EXT_abgr
    if (format == GL_ABGR_EXT && !haveABGR)
        return false;
#endif

    const int formatComps = NumberOfComponentsInFormat(format);
    const int typeComps = NumberOfComponentsInPackedType(datatype);
    return formatComps == typeComps || typeComps == 0;
}
// Create an image buffer and fill it so that a single image channel is
// the max value (1.0) while the other channels are zero.  For example,
// if fillComponent==2 and we're filling a four-component image, the
// pixels will be (0, 0, max, 0).
//
// We always leave the upper-right quadrant black/zero.  This is to help
// detect any image conversion issues related to stride, packing, etc.
static GLubyte *
MakeImage(int width, int height, GLenum format, GLenum type,
		  int fillComponent)
{
	assert(fillComponent < 4);

	if (type == GL_UNSIGNED_INT_5_9_9_9_REV) {
		GLubyte *image = new GLubyte [width * height * 4];
		int i;

		assert(format == GL_RGB);

		GLuint *ui = (GLuint *) image;
		for (i = 0; i < width * height; i++) {
			float p[3] = {0, 0, 0};

			if (!IsUpperRight(i, width, height))
				p[fillComponent] =  1;

			ui[i] = float3_to_rgb9e5(p);
		}

		return image;
	}
	else if (IsPackedType(type)) {
		const int bpp = SizeofType(type);
		GLubyte *image = new GLubyte [width * height * bpp];
		GLuint masks[4];
		int pos[4];
		int i;

		ComponentMasks(type, masks);
		ComponentPositions(format, pos);

		const GLuint value = masks[fillComponent];

		switch (bpp) {
		case 1:
			for (i = 0; i < width * height; i++) {
				if (IsUpperRight(i, width, height))
					image[i] = 0;
				else
					image[i] = (GLubyte) value;
			}
			break;
		case 2:
			{
				GLushort *image16 = (GLushort *) image;
				for (i = 0; i < width * height; i++) {
					if (IsUpperRight(i, width, height))
						image16[i] = 0;
					else
						image16[i] = (GLushort) value;
				}
			}
			break;
		case 4:
			{
				GLuint *image32 = (GLuint *) image;
				for (i = 0; i < width * height; i++) {
					if (IsUpperRight(i, width, height))
						image32[i] = 0;
					else
						image32[i] = (GLuint) value;
				}
			}
			break;
		default:
			abort();
		}

		return image;
	}
	else {
		const int comps = NumberOfComponentsInFormat(format);
		const int bpp = comps * SizeofType(type);
		assert(bpp > 0);
		GLubyte *image = new GLubyte [width * height * bpp];
		int i;

		switch (type) {
		case GL_UNSIGNED_BYTE:
			for (i = 0; i < width * height * comps; i++) {
				if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
					image[i] = 0xff;
				else
					image[i] = 0x0;
			}
			break;
		case GL_BYTE:
			{
				GLbyte *b = (GLbyte *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						b[i] = 0x7f;
					else
						b[i] = 0x0;
				}
			}
			break;
		case GL_UNSIGNED_SHORT:
			{
				GLushort *us = (GLushort *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						us[i] = 0xffff;
					else
						us[i] = 0x0;
				}
			}
			break;
		case GL_SHORT:
			{
				GLshort *s = (GLshort *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						s[i] = 0x7fff;
					else
						s[i] = 0x0;
				}
			}
			break;
		case GL_UNSIGNED_INT:
			{
				GLuint *ui = (GLuint *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						ui[i] = 0xffffffff;
					else
						ui[i] = 0x0;
				}
			}
			break;
		case GL_INT:
			{
				GLint *in = (GLint *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						in[i] = 0x7fffffff;
					else
						in[i] = 0x0;
				}
			}
			break;
		case GL_FLOAT:
			{
				GLfloat *f = (GLfloat *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						f[i] = 1.0;
					else
						f[i] = 0.0;
				}
			}
			break;
		case GL_HALF_FLOAT_ARB:
			{
				GLhalfARB *f = (GLhalfARB *) image;
				for (i = 0; i < width * height * comps; i++) {
					if (i % comps == fillComponent && !IsUpperRight(i/comps, width, height))
						f[i] = 0x3c00;  /* == 1.0 */
					else
						f[i] = 0;
				}
			}
			break;
		default:
			abort();
		}
		return image;
	}
}