Skip to content

Commit

Permalink
Add unpackColorSpace tests to tex-image-and-sub-image-2d-with-video (#…
Browse files Browse the repository at this point in the history
  • Loading branch information
ccameron-chromium committed May 17, 2022
1 parent d4d5987 commit 9361dbf
Show file tree
Hide file tree
Showing 3 changed files with 197 additions and 38 deletions.
73 changes: 36 additions & 37 deletions sdk/tests/js/tests/tex-image-and-sub-image-2d-with-video.js
Expand Up @@ -20,8 +20,6 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
var tiu = TexImageUtils;
var gl = null;
var successfullyParsed = false;
var redColor = [255, 0, 0];
var greenColor = [0, 255, 0];

// Test each format separately because many browsers implement each
// differently. Some might be GPU accelerated, some might not. Etc...
Expand All @@ -45,40 +43,26 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
return;
}

switch (gl[pixelFormat]) {
case gl.RED:
case gl.RED_INTEGER:
greenColor = [0, 0, 0];
break;
case gl.LUMINANCE:
case gl.LUMINANCE_ALPHA:
redColor = [255, 255, 255];
greenColor = [0, 0, 0];
break;
case gl.ALPHA:
redColor = [0, 0, 0];
greenColor = [0, 0, 0];
break;
default:
break;
}

gl.clearColor(0,0,0,1);
gl.clearDepth(1);

runTest();
}

function runOneIteration(videoElement, useTexSubImage2D, flipY, topColor, bottomColor, sourceSubRectangle, program, bindingTarget)
function runOneIteration(videoElement, unpackColorSpace, useTexSubImage2D, flipY, topColorName, bottomColorName, sourceSubRectangle, program, bindingTarget)
{
sourceSubRectangleString = '';
if (sourceSubRectangle) {
sourceSubRectangleString = ' sourceSubRectangle=' + sourceSubRectangle;
}
unpackColorSpaceString = '';
if (unpackColorSpace) {
unpackColorSpaceString = ' unpackColorSpace=' + unpackColorSpace;
}
debug('Testing ' + (useTexSubImage2D ? 'texSubImage2D' : 'texImage2D') +
' with flipY=' + flipY + ' bindingTarget=' +
(bindingTarget == gl.TEXTURE_2D ? 'TEXTURE_2D' : 'TEXTURE_CUBE_MAP') +
sourceSubRectangleString);
sourceSubRectangleString + unpackColorSpaceString);
gl.clear(gl.COLOR_BUFFER_BIT | gl.DEPTH_BUFFER_BIT);
// Disable any writes to the alpha channel
gl.colorMask(1, 1, 1, 0);
Expand All @@ -102,6 +86,10 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
gl.TEXTURE_CUBE_MAP_POSITIVE_Z,
gl.TEXTURE_CUBE_MAP_NEGATIVE_Z];
}
// Handle target color space.
if (unpackColorSpace) {
gl.unpackColorSpace = unpackColorSpace;
}
// Handle the source sub-rectangle if specified (WebGL 2.0 only)
if (sourceSubRectangle) {
gl.pixelStorei(gl.UNPACK_SKIP_PIXELS, sourceSubRectangle[0]);
Expand Down Expand Up @@ -165,6 +153,13 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
loc = gl.getUniformLocation(program, "face");
}

// Compute the test colors. This test only tests RGB (not A).
const topColor = wtu.colorAsSampledWithInternalFormat(
wtu.namedColorInColorSpace(topColorName, unpackColorSpace),
internalFormat).slice(0, 3);
const bottomColor = wtu.colorAsSampledWithInternalFormat(
wtu.namedColorInColorSpace(bottomColorName, unpackColorSpace),
internalFormat).slice(0, 3);
for (var tt = 0; tt < targets.length; ++tt) {
if (bindingTarget == gl.TEXTURE_CUBE_MAP) {
gl.uniform1i(loc, targets[tt]);
Expand All @@ -173,7 +168,7 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
wtu.clearAndDrawUnitQuad(gl, [0, 0, 0, 255]);
// Check a few pixels near the top and bottom and make sure they have
// the right color.
const tolerance = 6;
const tolerance = Math.max(6, tiu.tolerance(internalFormat, pixelFormat, pixelType));
debug("Checking lower left corner");
wtu.checkCanvasRect(gl, 4, 4, 2, 2, bottomColor,
"shouldBe " + bottomColor, tolerance);
Expand All @@ -186,33 +181,36 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
function runTest(videoElement)
{
var cases = [
{ sub: false, flipY: true, topColor: redColor, bottomColor: greenColor },
{ sub: false, flipY: false, topColor: greenColor, bottomColor: redColor },
{ sub: true, flipY: true, topColor: redColor, bottomColor: greenColor },
{ sub: true, flipY: false, topColor: greenColor, bottomColor: redColor },
{ sub: false, flipY: true, topColor: 'Red', bottomColor: 'Green' },
{ sub: false, flipY: false, topColor: 'Green', bottomColor: 'Red' },
{ sub: true, flipY: true, topColor: 'Red', bottomColor: 'Green' },
{ sub: true, flipY: false, topColor: 'Green', bottomColor: 'Red' },
];

if (wtu.getDefault3DContextVersion() > 1) {
cases = cases.concat([
{ sub: false, flipY: false, topColor: redColor, bottomColor: redColor,
{ sub: false, flipY: false, topColor: 'Red', bottomColor: 'Red',
sourceSubRectangle: [20, 16, 40, 32] },
{ sub: false, flipY: true, topColor: greenColor, bottomColor: greenColor,
{ sub: false, flipY: true, topColor: 'Green', bottomColor: 'Green',
sourceSubRectangle: [20, 16, 40, 32] },
{ sub: false, flipY: false, topColor: greenColor, bottomColor: greenColor,
{ sub: false, flipY: false, topColor: 'Green', bottomColor: 'Green',
sourceSubRectangle: [20, 80, 40, 32] },
{ sub: false, flipY: true, topColor: redColor, bottomColor: redColor,
{ sub: false, flipY: true, topColor: 'Red', bottomColor: 'Red',
sourceSubRectangle: [20, 80, 40, 32] },
{ sub: true, flipY: false, topColor: redColor, bottomColor: redColor,
{ sub: true, flipY: false, topColor: 'Red', bottomColor: 'Red',
sourceSubRectangle: [20, 16, 40, 32] },
{ sub: true, flipY: true, topColor: greenColor, bottomColor: greenColor,
{ sub: true, flipY: true, topColor: 'Green', bottomColor: 'Green',
sourceSubRectangle: [20, 16, 40, 32] },
{ sub: true, flipY: false, topColor: greenColor, bottomColor: greenColor,
{ sub: true, flipY: false, topColor: 'Green', bottomColor: 'Green',
sourceSubRectangle: [20, 80, 40, 32] },
{ sub: true, flipY: true, topColor: redColor, bottomColor: redColor,
{ sub: true, flipY: true, topColor: 'Red', bottomColor: 'Red',
sourceSubRectangle: [20, 80, 40, 32] },
]);
}

cases = tiu.crossProductTestCasesWithUnpackColorSpaces(
cases, tiu.unpackColorSpacesToTest(gl));

function runTexImageTest(bindingTarget) {
var program;
if (bindingTarget == gl.TEXTURE_2D) {
Expand Down Expand Up @@ -269,8 +267,9 @@ function generateTest(internalFormat, pixelFormat, pixelType, prologue, resource
break;
}
}
runOneIteration(video, cases[i].sub, cases[i].flipY,
cases[i].topColor, cases[i].bottomColor,
runOneIteration(video, cases[i].unpackColorSpace, cases[i].sub, cases[i].flipY,
cases[i].topColor,
cases[i].bottomColor,
cases[i].sourceSubRectangle,
program, bindingTarget);
}
Expand Down
66 changes: 65 additions & 1 deletion sdk/tests/js/tests/tex-image-and-sub-image-utils.js
Expand Up @@ -791,11 +791,75 @@ var TexImageUtils = (function() {
return program;
};

/**
* Return a list of unpack color spaces to test, supported by the specified
* WebGLRenderingContext.
*/
var unpackColorSpacesToTest = function(gl)
{
if ('unpackColorSpace' in gl)
return ['srgb', 'display-p3'];
else
return [undefined];
}

/**
* For each entry in unpackColorSpaces, duplicate all of cases, adding an
* unpackColorSpace key with its value set to that entry to each case.
*/
var crossProductTestCasesWithUnpackColorSpaces = function(testCaseList, unpackColorSpaces)
{
var testCaseWithUnpackColorSpace = function(testCase, colorSpace)
{
return {...testCase, ...{unpackColorSpace:colorSpace}};
}
var listOfTestCaseLists = unpackColorSpaces.map(colorSpace =>
testCaseList.map(testCase => testCaseWithUnpackColorSpace(testCase, colorSpace)));
return listOfTestCaseLists.flat();
}

/**
* Given given an internalformat, format, and type, return the tolerance
* that should be used when comparing an input 8-bit value to one that has
* been truncated through the specified formats.
*/
var tolerance = function(internalformat, format, type) {
function typeTolerance(type) {
switch(type) {
case 'UNSIGNED_SHORT_5_6_5':
case 'UNSIGNED_SHORT_5_5_5_1':
return 255 / 31;
case 'UNSIGNED_SHORT_4_4_4_4':
return 255 / 15;
break;
default:
return 1;
}
};
function formatTolerance(format) {
switch(format) {
case 'RGB565':
case 'RGB5_A1':
return 255/31;
case 'RGBA4':
return 255/15;
default:
return 1;
}
};
return Math.max(formatTolerance(internalformat),
formatTolerance(format),
typeTolerance(type));
}

return {
setupTexturedQuad: setupTexturedQuad,
setupTexturedQuadWithCubeMap: setupTexturedQuadWithCubeMap,
setupTexturedQuadWith3D: setupTexturedQuadWith3D,
setupTexturedQuadWith2DArray: setupTexturedQuadWith2DArray
setupTexturedQuadWith2DArray: setupTexturedQuadWith2DArray,
unpackColorSpacesToTest: unpackColorSpacesToTest,
crossProductTestCasesWithUnpackColorSpaces: crossProductTestCasesWithUnpackColorSpaces,
tolerance: tolerance
};

}());
96 changes: 96 additions & 0 deletions sdk/tests/js/webgl-test-utils.js
Expand Up @@ -3296,6 +3296,98 @@ function linearChannelToSRGB(value) {
return Math.trunc(value * 255 + 0.5);
}

/**
* Return the named color in the specified color space.
* @param {string} colorName The name of the color to convert.
* Supported color names are:
* 'Red', which is the CSS color color('srgb' 1 0 0 1)
* 'Green', which is the CSS color color('srgb' 0 1 0 1)
* @param {string} colorSpace The color space to convert to. Supported
color spaces are:
* null, which is treated as sRGB
* 'srgb'
* 'display-p3'.
* Documentation on the formulas for color conversion between
* spaces can be found at
https://www.w3.org/TR/css-color-4/#predefined-to-predefined
* @return {!Array.<number>} color The color in the specified color
* space as an 8-bit RGBA array with unpremultiplied alpha.
*/
var namedColorInColorSpace = function(colorName, colorSpace) {
var result;
switch (colorSpace) {
case undefined:
case 'srgb':
switch(colorName) {
case 'Red':
return [255, 0, 0, 255];
case 'Green':
return [0, 255, 0, 255];
break;
default:
throw 'unexpected color name: ' + colorName;
};
break;
case 'display-p3':
switch(colorName) {
case 'Red':
return [234, 51, 35, 255];
break;
case 'Green':
return [117, 251, 76, 255];
break;
default:
throw 'unexpected color name: ' + colorName;
}
break;
default:
throw 'unexpected color space: ' + colorSpace;
}
}

/**
* Return the named color as it would be sampled with the specified
* internal format
* @param {!Array.<number>} color The color as an 8-bit RGBA array.
* @param {string} internalformat The internal format.
* @return {!Array.<number>} color The color, as it would be sampled by
* the specified internal format, as an 8-bit RGBA array.
*/
var colorAsSampledWithInternalFormat = function(color, internalFormat) {
switch (internalFormat) {
case 'ALPHA':
return [0, 0, 0, color[3]];
case 'LUMINANCE':
return [color[0], color[0], color[0], 255];
case 'LUMINANCE_ALPHA':
return [color[0], color[0], color[0], color[3]];
case 'SRGB8':
case 'SRGB8_ALPHA8':
return [sRGBChannelToLinear(color[0]),
sRGBChannelToLinear(color[1]),
sRGBChannelToLinear(color[2]),
color[3]];
case 'R16F':
case 'R32F':
case 'R8':
case 'R8UI':
case 'RED':
case 'RED_INTEGER':
return [result[0], 0, 0, 0];
case 'RG':
case 'RG16F':
case 'RG32F':
case 'RG8':
case 'RG8UI':
case 'RG_INTEGER':
return [color[0], color[1], 0, 0];
break;
default:
break;
}
return color;
}

function comparePixels(cmp, ref, tolerance, diff) {
if (cmp.length != ref.length) {
testFailed("invalid pixel size.");
Expand Down Expand Up @@ -3516,6 +3608,10 @@ var API = {
// fullscreen api
setupFullscreen: setupFullscreen,

// color converter API
namedColorInColorSpace: namedColorInColorSpace,
colorAsSampledWithInternalFormat: colorAsSampledWithInternalFormat,

// sRGB converter api
sRGBToLinear: sRGBToLinear,
linearToSRGB: linearToSRGB,
Expand Down

0 comments on commit 9361dbf

Please sign in to comment.