summaryrefslogtreecommitdiffstats
path: root/o3d
diff options
context:
space:
mode:
authorluchen@chromium.org <luchen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-08-12 23:16:12 +0000
committerluchen@chromium.org <luchen@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2010-08-12 23:16:12 +0000
commit49bb96e224996a647ab1694d02323b542721bb94 (patch)
tree515aac5cee6ab3149725c53408b330ef9f59f105 /o3d
parent7e31031a2561298495796cd986f9e31947c32363 (diff)
downloadchromium_src-49bb96e224996a647ab1694d02323b542721bb94.zip
chromium_src-49bb96e224996a647ab1694d02323b542721bb94.tar.gz
chromium_src-49bb96e224996a647ab1694d02323b542721bb94.tar.bz2
Adding implementations to two methods in texture.js and fixing a small typo/bug.
I hacked two of the existing demos as a test to ensure the two new methods work (adding a small chunk of new code to them). Should these be included as brand new demos, or added to the existing demo (with a var doExtra = true/false switch), or should I try to make a brand new demo that exercises these methods? Review URL: http://codereview.chromium.org/3129010 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@55954 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'o3d')
-rw-r--r--o3d/samples/o3d-webgl/texture.js128
1 files changed, 96 insertions, 32 deletions
diff --git a/o3d/samples/o3d-webgl/texture.js b/o3d/samples/o3d-webgl/texture.js
index 176ca0e..be991bd 100644
--- a/o3d/samples/o3d-webgl/texture.js
+++ b/o3d/samples/o3d-webgl/texture.js
@@ -206,7 +206,8 @@ o3d.Texture.prototype.getGLTextureFormat_ = function() {
case o3d.Texture.DXT1:
case o3d.Texture.DXT3:
case o3d.Texture.DXT5:
- notImplemented();
+ default:
+ o3d.notImplemented();
return 0;
}
}
@@ -265,44 +266,18 @@ o3d.Texture.prototype.setFromCanvas_ =
/**
* Sets the values of the data stored in the texture.
*
- * It is not recommend that you call this for large textures but it is useful
- * for making simple ramps or noise textures for shaders.
- *
- * NOTE: the number of values must equal the size of the texture * the number
- * of elements. In other words, for a XRGB8 texture there must be
- * width * height * 3 values. For an ARGB8, ABGR16F or ABGR32F texture there
- * must be width * height * 4 values. For an R32F texture there must be
- * width * height values.
- *
- * NOTE: the order of channels is R G B for XRGB8 textures and R G B A
- * for ARGB8, ABGR16F and ABGR32F textures so for example for XRGB8 textures
- *
- * [1, 0, 0] = a red pixel
- * [0, 0, 1] = a blue pixel
- *
- * For ARGB8, ABGR16F, ABGR32F textures
- *
- * [1, 0, 0, 0] = a red pixel with zero alpha
- * [1, 0, 0, 1] = a red pixel with one alpha
- * [0, 0, 1, 1] = a blue pixel with one alpha
- *
+ * @param {number} target The target to bind this texture to.
* @param {number} level the mip level to update.
* @param {number} values Values to be stored in the buffer.
+ * @private
*/
-o3d.Texture.prototype.set =
- function(level, values) {
- var target = this.texture_target_;
- if (target == this.gl.TEXTURE_CUBE_MAP) {
- target = this.gl.TEXTURE_CUBE_MAP_POSITIVE_X + face;
- }
-
+o3d.Texture.prototype.setValues_ = function(target, level, values) {
var pixels = new WebGLUnsignedByteArray(values.length);
for (var i = 0; i < values.length; ++i) {
pixels[i] = Math.min(255, Math.max(0, values[i] * 256.0));
}
var format = this.getGLTextureFormat_();
-
this.gl.bindTexture(target, this.texture_);
this.gl.texSubImage2D(
target, level, 0, 0, this.texture_width_, this.texture_height_,
@@ -405,6 +380,40 @@ o3d.Texture2D.prototype.getRenderSurface =
/**
+ * Sets the values of the data stored in the texture.
+ *
+ * It is not recommend that you call this for large textures but it is useful
+ * for making simple ramps or noise textures for shaders.
+ *
+ * NOTE: the number of values must equal the size of the texture * the number
+ * of elements. In other words, for a XRGB8 texture there must be
+ * width * height * 3 values. For an ARGB8, ABGR16F or ABGR32F texture there
+ * must be width * height * 4 values. For an R32F texture there must be
+ * width * height values.
+ *
+ * NOTE: the order of channels is R G B for XRGB8 textures and R G B A
+ * for ARGB8, ABGR16F and ABGR32F textures so for example for XRGB8 textures
+ *
+ * [1, 0, 0] = a red pixel
+ * [0, 0, 1] = a blue pixel
+ *
+ * For ARGB8, ABGR16F, ABGR32F textures
+ *
+ * [1, 0, 0, 0] = a red pixel with zero alpha
+ * [1, 0, 0, 1] = a red pixel with one alpha
+ * [0, 0, 1, 1] = a blue pixel with one alpha
+ *
+ * @param {number} level the mip level to update.
+ * @param {values} values Values to be stored in the buffer.
+ */
+o3d.Texture2D.prototype.set =
+ function(level, values) {
+ var target = this.texture_target_;
+ this.setValues_(target, level, values);
+};
+
+
+/**
* Sets a rectangular area of values in a texture.
*
* Does clipping. In other words if you pass in a 10x10 pixel array
@@ -425,7 +434,59 @@ o3d.Texture2D.prototype.getRenderSurface =
*/
o3d.Texture2D.prototype.setRect =
function(level, destination_x, destination_y, source_width, values) {
- o3d.notImplemented();
+ var format = this.getGLTextureFormat_();
+ var numChannels = (format == this.gl.RGB ? 3 : 4);
+ var source_height = (values.length / numChannels) / source_width;
+ var target = this.texture_target_;
+
+ // If completely clipped off, do nothing and return.
+ if (destination_x > this.width || destination_y > this.height ||
+ destination_x + source_width < 0 || destination_y + source_height < 0) {
+ return;
+ }
+
+ // Size of the unclipped, remaining rectangle.
+ var size_x = source_width;
+ if (destination_x < 0) {
+ size_x += destination_x;
+ }
+ if (destination_x + source_width > this.width) {
+ size_x -= (destination_x + source_width) - this.width;
+ }
+
+ var size_y = source_height;
+ if (destination_y < 0) {
+ size_y += destination_y;
+ }
+ if (destination_y + source_height > this.height) {
+ size_y -= (destination_y + source_height) - this.height;
+ }
+
+ // The upper left corner of the rectangle that is not clipped and will be
+ // copied into the texture.
+ var start_x = (destination_x < 0) ? Math.abs(destination_x) : 0;
+ var start_y = (destination_y < 0) ? Math.abs(destination_y) : 0;
+
+ var keptPixels = new WebGLUnsignedByteArray(size_x * size_y * numChannels);
+ var count = 0;
+ for (var y = 0; y < size_y; ++y) {
+ for (var x = 0; x < size_x; ++x) {
+ var t = (((start_y + y) * source_width) + (start_x + x)) * numChannels;
+ keptPixels[count++] = Math.min(255, Math.max(0, values[t] * 256.0));
+ keptPixels[count++] = Math.min(255, Math.max(0, values[t + 1] * 256.0));
+ keptPixels[count++] = Math.min(255, Math.max(0, values[t + 2] * 256.0));
+ keptPixels[count++] = Math.min(255, Math.max(0, values[t + 3] * 256.0));
+ }
+ }
+
+ // The (x, y) at which to begin drawing the rectangle on the original texture,
+ // measured from the *BOTTOM* left hand corner.
+ var where_x = Math.max(destination_x, 0);
+ var where_y = this.height - (Math.max(destination_y, 0) + size_y);
+
+ this.gl.bindTexture(target, this.texture_);
+ this.gl.texSubImage2D(target, level, where_x, where_y, size_x, size_y,
+ format, this.gl.UNSIGNED_BYTE, keptPixels);
};
@@ -594,6 +655,7 @@ o3d.TextureCUBE.prototype.init_ =
this.texture_target_ = this.gl.TEXTURE_CUBE_MAP;
this.texture_width_ = edgeLength;
this.texture_height_ = edgeLength;
+ this.format = format;
this.gl.bindTexture(this.gl.TEXTURE_CUBE_MAP, this.texture_);
// TODO(petersont): remove this allocation once Firefox supports
@@ -641,7 +703,9 @@ o3d.TextureCUBE.prototype.getRenderSurface =
*/
o3d.TextureCUBE.prototype.set =
function(face, level, values) {
- o3d.notImplemented();
+ var target = this.gl.TEXTURE_CUBE_MAP_POSITIVE_X + face;
+ this.setValues_(target, level, values);
+ this.faces_set_[face] = true;
};