@@ -83,9 +83,9 @@ Phaser.BitmapData = function (game, key, width, height) {
8383 this . data = this . imageData . data ;
8484
8585 /**
86- * @property {Uint32Array } pixels - A Uint32Array view into BitmapData.buffer.
86+ * @property {Int32Array } pixels - An Int32Array view into BitmapData.buffer.
8787 */
88- this . pixels = new Uint32Array ( this . buffer ) ;
88+ this . pixels = new Int32Array ( this . buffer ) ;
8989
9090 /**
9191 * @property {PIXI.BaseTexture } baseTexture - The PIXI.BaseTexture.
@@ -221,7 +221,7 @@ Phaser.BitmapData.prototype = {
221221
222222 /**
223223 * This re-creates the BitmapData.imageData from the current context.
224- * It then re-builds the ArrayBuffer, the data Uint8ClampedArray reference and the pixels Uint32Array .
224+ * It then re-builds the ArrayBuffer, the data Uint8ClampedArray reference and the pixels Int32Array .
225225 * If not given the dimensions defaults to the full size of the context.
226226 *
227227 * @method Phaser.BitmapData#update
@@ -233,7 +233,7 @@ Phaser.BitmapData.prototype = {
233233
234234 /**
235235 * This re-creates the BitmapData.imageData from the current context.
236- * It then re-builds the ArrayBuffer, the data Uint8ClampedArray reference and the pixels Uint32Array .
236+ * It then re-builds the ArrayBuffer, the data Uint8ClampedArray reference and the pixels Int32Array .
237237 * If not given the dimensions defaults to the full size of the context.
238238 *
239239 * @method Phaser.BitmapData#refreshBuffer
@@ -261,64 +261,127 @@ Phaser.BitmapData.prototype = {
261261 }
262262
263263 this . data = this . imageData . data ;
264- this . pixels = new Uint32Array ( this . buffer ) ;
264+ this . pixels = new Int32Array ( this . buffer ) ;
265265
266266 } ,
267267
268268 /**
269- * Sets the color of the given pixel to the specified red, green, blue and alpha values.
269+ * Scans through the area specified in this BitmapData and sends a color object for every pixel to the given callback.
270+ * The callback will be sent a single object with 6 properties: `{ r: number, g: number, b: number, a: number, color: number, rgba: string }`.
271+ * Where r, g, b and a are integers between 0 and 255 representing the color component values for red, green, blue and alpha.
272+ * The `color` property is an Int32 of the full color. Note the endianess of this will change per system.
273+ * The `rgba` property is a CSS style rgba() string which can be used with context.fillStyle calls, among others.
274+ * The callback must return either `false`, in which case no change will be made to the pixel, or a new color object.
275+ * If a new color object is returned the pixel will be set to the r, g, b and a color values given within it.
270276 *
271- * @method Phaser.BitmapData#replaceRGB
272- * @param {number } x - The X coordinate of the pixel to be set .
273- * @param {number } y - The Y coordinate of the pixel to be set .
274- * @param {number } red - The red color value, between 0 and 0xFF (255) .
275- * @param {number } green - The green color value, between 0 and 0xFF (255) .
276- * @param {number } blue - The blue color value, between 0 and 0xFF (255) .
277- * @param {number } alpha - The alpha color value, between 0 and 0xFF (255) .
277+ * @method Phaser.BitmapData#processPixelRGB
278+ * @param {function } callback - The callback that will be sent each pixel color object to be processed .
279+ * @param {object } callbackContext - The context under which the callback will be called .
280+ * @param {number } [x=0] - The x coordinate of the top-left of the region to process from .
281+ * @param {number } [y=0] - The y coordinate of the top-left of the region to process from .
282+ * @param {number } [width] - The width of the region to process .
283+ * @param {number } [height] - The height of the region to process .
278284 */
279- replaceRGB : function ( sourceR , sourceG , sourceB , sourceA , destR , destG , destB , destA , region ) {
285+ processPixelRGB : function ( callback , callbackContext , x , y , width , height ) {
280286
281- var tx = 0 ;
282- var ty = 0 ;
283- var w = this . width ;
284- var h = this . height ;
287+ if ( typeof x === 'undefined' ) { x = 0 ; }
288+ if ( typeof y === 'undefined' ) { y = 0 ; }
289+ if ( typeof width === 'undefined' ) { width = this . width ; }
290+ if ( typeof height === 'undefined' ) { height = this . height ; }
285291
286- if ( region instanceof Phaser . Rectangle )
292+ var w = x + width ;
293+ var h = y + height ;
294+ var pixel = { r : 0 , g : 0 , b : 0 , a : 0 , rgba : '' } ;
295+ var result = { r : 0 , g : 0 , b : 0 , a : 0 } ;
296+ var color = 0 ;
297+ var dirty = false ;
298+
299+ for ( var ty = y ; ty < h ; ty ++ )
287300 {
288- tx = region . x ;
289- ty = region . y ;
290- w = region . width ;
291- h = region . height ;
292- }
301+ for ( var tx = x ; tx < w ; tx ++ )
302+ {
303+ color = this . getPixel32 ( tx , ty ) ;
304+ this . unpackPixel ( color , pixel ) ;
305+ result = callback . call ( callbackContext , pixel , color ) ;
293306
294- // for (var x = tx; x < w)
307+ if ( result !== false && result !== null )
308+ {
309+ this . setPixel32 ( tx , ty , result . r , result . g , result . b , result . a , false ) ;
310+ dirty = true ;
311+ }
312+ }
313+ }
295314
296- if ( x >= 0 && x <= this . width && y >= 0 && y <= this . height )
315+ if ( dirty )
297316 {
298- this . pixels [ y * this . width + x ] = ( alpha << 24 ) | ( blue << 16 ) | ( green << 8 ) | red ;
317+ this . context . putImageData ( this . imageData , 0 , 0 ) ;
318+ this . dirty = true ;
319+ }
299320
321+ } ,
300322
301- // this.imageData.data.set(this.data8);
323+ /**
324+ * Replaces all pixels matching the given RGBA values with the new RGBA values in the given region,
325+ * or the whole BitmapData if no region provided.
326+ *
327+ * @method Phaser.BitmapData#replaceRGB
328+ * @param {number } r1 - The red color value to be replaced. Between 0 and 255.
329+ * @param {number } g1 - The green color value to be replaced. Between 0 and 255.
330+ * @param {number } b1 - The blue color value to be replaced. Between 0 and 255.
331+ * @param {number } a1 - The alpha color value to be replaced. Between 0 and 255.
332+ * @param {number } r2 - The red color value that is the replacement color. Between 0 and 255.
333+ * @param {number } g2 - The green color value that is the replacement color. Between 0 and 255.
334+ * @param {number } b2 - The blue color value that is the replacement color. Between 0 and 255.
335+ * @param {number } a2 - The alpha color value that is the replacement color. Between 0 and 255.
336+ * @param {Phaser.Rectangle } [region] - The area to perform the search over. If not given it will replace over the whole BitmapData.
337+ */
338+ replaceRGB : function ( r1 , g1 , b1 , a1 , r2 , g2 , b2 , a2 , region ) {
339+
340+ var sx = 0 ;
341+ var sy = 0 ;
342+ var w = this . width ;
343+ var h = this . height ;
344+ var source = this . packPixel ( r1 , g1 , b1 , a1 ) ;
302345
303- this . context . putImageData ( this . imageData , 0 , 0 ) ;
346+ if ( region !== undefined && region instanceof Phaser . Rectangle )
347+ {
348+ sx = region . x ;
349+ sy = region . y ;
350+ w = region . width ;
351+ h = region . height ;
352+ }
304353
305- this . dirty = true ;
354+ for ( var y = 0 ; y < h ; y ++ )
355+ {
356+ for ( var x = 0 ; x < w ; x ++ )
357+ {
358+ if ( this . getPixel32 ( sx + x , sy + y ) === source )
359+ {
360+ this . setPixel32 ( sx + x , sy + y , r2 , g2 , b2 , a2 , false ) ;
361+ }
362+ }
306363 }
307364
365+ this . context . putImageData ( this . imageData , 0 , 0 ) ;
366+ this . dirty = true ;
367+
308368 } ,
309369
310370 /**
311371 * Sets the color of the given pixel to the specified red, green, blue and alpha values.
312372 *
313373 * @method Phaser.BitmapData#setPixel32
314- * @param {number } x - The X coordinate of the pixel to be set.
315- * @param {number } y - The Y coordinate of the pixel to be set.
374+ * @param {number } x - The x coordinate of the pixel to be set. Must lay within the dimensions of this BitmapData .
375+ * @param {number } y - The y coordinate of the pixel to be set. Must lay within the dimensions of this BitmapData .
316376 * @param {number } red - The red color value, between 0 and 0xFF (255).
317377 * @param {number } green - The green color value, between 0 and 0xFF (255).
318378 * @param {number } blue - The blue color value, between 0 and 0xFF (255).
319379 * @param {number } alpha - The alpha color value, between 0 and 0xFF (255).
380+ * @param {boolean } [immediate=true] - If `true` the context.putImageData will be called and the dirty flag set.
320381 */
321- setPixel32 : function ( x , y , red , green , blue , alpha ) {
382+ setPixel32 : function ( x , y , red , green , blue , alpha , immediate ) {
383+
384+ if ( typeof immediate === 'undefined' ) { immediate = true ; }
322385
323386 if ( x >= 0 && x <= this . width && y >= 0 && y <= this . height )
324387 {
@@ -331,9 +394,11 @@ Phaser.BitmapData.prototype = {
331394 this . pixels [ y * this . width + x ] = ( red << 24 ) | ( green << 16 ) | ( blue << 8 ) | alpha ;
332395 }
333396
334- this . context . putImageData ( this . imageData , 0 , 0 ) ;
335-
336- this . dirty = true ;
397+ if ( immediate )
398+ {
399+ this . context . putImageData ( this . imageData , 0 , 0 ) ;
400+ this . dirty = true ;
401+ }
337402 }
338403
339404 } ,
@@ -342,15 +407,17 @@ Phaser.BitmapData.prototype = {
342407 * Sets the color of the given pixel to the specified red, green and blue values.
343408 *
344409 * @method Phaser.BitmapData#setPixel
345- * @param {number } x - The X coordinate of the pixel to be set.
346- * @param {number } y - The Y coordinate of the pixel to be set.
347- * @param {number } red - The red color value (between 0 and 255)
348- * @param {number } green - The green color value (between 0 and 255)
349- * @param {number } blue - The blue color value (between 0 and 255)
410+ * @param {number } x - The x coordinate of the pixel to be set. Must lay within the dimensions of this BitmapData.
411+ * @param {number } y - The y coordinate of the pixel to be set. Must lay within the dimensions of this BitmapData.
412+ * @param {number } red - The red color value, between 0 and 0xFF (255).
413+ * @param {number } green - The green color value, between 0 and 0xFF (255).
414+ * @param {number } blue - The blue color value, between 0 and 0xFF (255).
415+ * @param {number } alpha - The alpha color value, between 0 and 0xFF (255).
416+ * @param {boolean } [immediate=true] - If `true` the context.putImageData will be called and the dirty flag set.
350417 */
351- setPixel : function ( x , y , red , green , blue ) {
418+ setPixel : function ( x , y , red , green , blue , immediate ) {
352419
353- this . setPixel32 ( x , y , red , green , blue , 255 ) ;
420+ this . setPixel32 ( x , y , red , green , blue , 255 , immediate ) ;
354421
355422 } ,
356423
@@ -410,10 +477,7 @@ Phaser.BitmapData.prototype = {
410477 */
411478 getPixelRGB : function ( x , y ) {
412479
413- if ( x >= 0 && x <= this . width && y >= 0 && y <= this . height )
414- {
415- return this . unpackPixel ( this . pixels [ y * this . width + x ] ) ;
416- }
480+ return this . unpackPixel ( this . getPixel32 ( x , y ) ) ;
417481
418482 } ,
419483
@@ -468,14 +532,14 @@ Phaser.BitmapData.prototype = {
468532 * @author Matt DesLauriers (@mattdesl)
469533 * @method Phaser.BitmapData#unpackPixel
470534 * @param {number } rgba - The integer, packed in endian order by packPixel.
471- * @param {object } out - The color object with `r, g, b, a` properties, or null.
472- * @return {object } A color representing the pixel at that location .
535+ * @param {object } out - The color object with `r, g, b, a, rgba and color ` properties, or null.
536+ * @return {object } A color object .
473537 */
474538 unpackPixel : function ( rgba , out ) {
475539
476540 if ( ! out )
477541 {
478- out = { r : 0 , g : 0 , b : 0 , a : 0 , rgba : '' } ;
542+ out = { r : 0 , g : 0 , b : 0 , a : 0 , color : 0 , rgba : '' } ;
479543 }
480544
481545 if ( this . littleEndian )
@@ -493,6 +557,7 @@ Phaser.BitmapData.prototype = {
493557 out . a = ( ( rgba & 0x000000ff ) ) ;
494558 }
495559
560+ out . color = rgba ;
496561 out . rgba = 'rgba(' + out . r + ',' + out . g + ',' + out . b + ',' + out . a + ')' ;
497562
498563 return out ;
0 commit comments