Improvements to fix for copyPixels using alpha image (resolve #1707)

This commit is contained in:
Joshua Granick
2017-09-13 16:41:36 -07:00
parent c5184e41bb
commit 411f9d0668
3 changed files with 108 additions and 44 deletions

View File

@@ -284,20 +284,20 @@ class ImageDataUtil {
var alphaData = alphaImage.buffer.data; var alphaData = alphaImage.buffer.data;
var alphaFormat = alphaImage.buffer.format; var alphaFormat = alphaImage.buffer.format;
var alphaPosition, alphaPixel:RGBA;
var alphaView = new ImageDataView (alphaImage, new Rectangle (alphaPoint.x, alphaPoint.y, alphaImage.width, alphaImage.height)); var alphaView = new ImageDataView (alphaImage, new Rectangle (alphaPoint.x, alphaPoint.y, alphaImage.width, alphaImage.height));
var alphaPosition, alphaPixel:RGBA; alphaView.offset (sourceView.x, sourceView.y);
var alphaOffsetY = alphaView.y + sourceView.y;
destView.clip (Std.int (destPoint.x), Std.int (destPoint.y), alphaView.width, alphaView.height);
if (blend) { if (blend) {
for (y in 0...destView.height) { for (y in 0...destView.height) {
if (!alphaView.hasRow (y + alphaOffsetY)) continue;
sourcePosition = sourceView.row (y); sourcePosition = sourceView.row (y);
destPosition = destView.row (y); destPosition = destView.row (y);
alphaPosition = alphaView.row (y + alphaOffsetY); alphaPosition = alphaView.row (y);
for (x in 0...destView.width) { for (x in 0...destView.width) {
@@ -334,11 +334,9 @@ class ImageDataUtil {
for (y in 0...destView.height) { for (y in 0...destView.height) {
if (!alphaView.hasRow (y + alphaOffsetY)) continue;
sourcePosition = sourceView.row (y); sourcePosition = sourceView.row (y);
destPosition = destView.row (y); destPosition = destView.row (y);
alphaPosition = alphaView.row (y + alphaOffsetY); alphaPosition = alphaView.row (y);
for (x in 0...destView.width) { for (x in 0...destView.width) {
@@ -1540,8 +1538,8 @@ private class ImageDataView {
public var height (default, null):Int; public var height (default, null):Int;
public var width (default, null):Int; public var width (default, null):Int;
private var byteOffset:Int;
private var image:Image; private var image:Image;
private var offset:Int;
private var rect:Rectangle; private var rect:Rectangle;
private var stride:Int; private var stride:Int;
@@ -1568,11 +1566,7 @@ private class ImageDataView {
stride = image.buffer.stride; stride = image.buffer.stride;
x = Math.ceil (this.rect.x); __update ();
y = Math.ceil (this.rect.y);
width = Math.floor (this.rect.width);
height = Math.floor (this.rect.height);
offset = (stride * (this.y + image.offsetY)) + ((this.x + image.offsetX) * 4);
} }
@@ -1580,12 +1574,7 @@ private class ImageDataView {
public function clip (x:Int, y:Int, width:Int, height:Int):Void { public function clip (x:Int, y:Int, width:Int, height:Int):Void {
rect.__contract (x, y, width, height); rect.__contract (x, y, width, height);
__update ();
this.x = Math.ceil (rect.x);
this.y = Math.ceil (rect.y);
this.width = Math.floor (rect.width);
this.height = Math.floor (rect.height);
offset = (stride * (this.y + image.offsetY)) + ((this.x + image.offsetX) * 4);
} }
@@ -1597,9 +1586,51 @@ private class ImageDataView {
} }
public function offset (x:Int, y:Int):Void {
if (x < 0) {
rect.x += x;
if (rect.x < 0) rect.x = 0;
} else {
rect.x += x;
rect.width -= x;
}
if (y < 0) {
rect.y += y;
if (rect.y < 0) rect.y = 0;
} else {
rect.y += y;
rect.height -= y;
}
__update ();
}
public inline function row (y:Int):Int { public inline function row (y:Int):Int {
return offset + stride * y; return byteOffset + stride * y;
}
private function __update ():Void {
this.x = Math.ceil (rect.x);
this.y = Math.ceil (rect.y);
this.width = Math.floor (rect.width);
this.height = Math.floor (rect.height);
byteOffset = (stride * (this.y + image.offsetY)) + ((this.x + image.offsetX) * 4);
} }

View File

@@ -49,6 +49,7 @@ namespace lime {
void Clip (int x, int y, int width, int height); void Clip (int x, int y, int width, int height);
bool HasRow (int y); bool HasRow (int y);
void Offset (int x, int y);
int Row (int y); int Row (int y);
int x; int x;
@@ -58,8 +59,10 @@ namespace lime {
private: private:
void __Update ();
int byteOffset;
Image* image; Image* image;
int offset;
Rectangle* rect; Rectangle* rect;
int stride; int stride;

View File

@@ -210,22 +210,22 @@ namespace lime {
uint8_t* alphaData = (uint8_t*)alphaImage->buffer->data->Data (); uint8_t* alphaData = (uint8_t*)alphaImage->buffer->data->Data ();
PixelFormat alphaFormat = alphaImage->buffer->format; PixelFormat alphaFormat = alphaImage->buffer->format;
bool alphaPremultiplied = alphaImage->buffer->premultiplied; bool alphaPremultiplied = alphaImage->buffer->premultiplied;
int alphaPosition;
RGBA alphaPixel;
Rectangle alphaRect = Rectangle (alphaPoint->x, alphaPoint->y, alphaImage->width, alphaImage->height); Rectangle alphaRect = Rectangle (alphaPoint->x, alphaPoint->y, alphaImage->width, alphaImage->height);
ImageDataView alphaView = ImageDataView (alphaImage, &alphaRect); ImageDataView alphaView = ImageDataView (alphaImage, &alphaRect);
int alphaPosition; alphaView.Offset (sourceView.x, sourceView.y);
RGBA alphaPixel;
int alphaOffsetY = alphaView.y + sourceView.y; destView.Clip (destPoint->x, destPoint->y, alphaView.width, alphaView.height);
if (blend) { if (blend) {
for (int y = 0; y < destView.height; y++) { for (int y = 0; y < destView.height; y++) {
if (!alphaView.HasRow (y + alphaOffsetY)) continue;
sourcePosition = sourceView.Row (y); sourcePosition = sourceView.Row (y);
destPosition = destView.Row (y); destPosition = destView.Row (y);
alphaPosition = alphaView.Row (y + alphaOffsetY); alphaPosition = alphaView.Row (y);
for (int x = 0; x < destView.width; x++) { for (int x = 0; x < destView.width; x++) {
@@ -262,11 +262,9 @@ namespace lime {
for (int y = 0; y < destView.height; y++) { for (int y = 0; y < destView.height; y++) {
if (!alphaView.HasRow (y + alphaOffsetY)) continue;
sourcePosition = sourceView.Row (y); sourcePosition = sourceView.Row (y);
destPosition = destView.Row (y); destPosition = destView.Row (y);
alphaPosition = alphaView.Row (y + alphaOffsetY); alphaPosition = alphaView.Row (y);
for (int x = 0; x < destView.width; x++) { for (int x = 0; x < destView.width; x++) {
@@ -826,11 +824,7 @@ namespace lime {
stride = image->buffer->Stride (); stride = image->buffer->Stride ();
x = (int) ceil (this->rect->x); __Update ();
y = (int) ceil (this->rect->y);
width = (int) floor (this->rect->width);
height = (int) floor (this->rect->height);
offset = (stride * (this->y + image->offsetY)) + ((this->x + image->offsetX) * 4);
} }
@@ -839,13 +833,7 @@ namespace lime {
void ImageDataView::Clip (int x, int y, int width, int height) { void ImageDataView::Clip (int x, int y, int width, int height) {
rect->Contract (x, y, width, height); rect->Contract (x, y, width, height);
__Update ();
this->x = (int) ceil (rect->x);
this->y = (int) ceil (rect->y);
this->width = (int) floor (rect->width);
this->height = (int) floor (rect->height);
offset = (stride * (this->y + image->offsetY)) + ((this->x + image->offsetX) * 4);
} }
@@ -857,9 +845,51 @@ namespace lime {
} }
void ImageDataView::Offset (int x, int y) {
if (x < 0) {
rect->x += x;
if (rect->x < 0) rect->x = 0;
} else {
rect->x += x;
rect->width -= x;
}
if (y < 0) {
rect->y += y;
if (rect->y < 0) rect->y = 0;
} else {
rect->y += y;
rect->height -= y;
}
__Update ();
}
inline int ImageDataView::Row (int y) { inline int ImageDataView::Row (int y) {
return offset + stride * y; return byteOffset + stride * y;
}
inline void ImageDataView::__Update () {
this->x = (int) ceil (rect->x);
this->y = (int) ceil (rect->y);
this->width = (int) floor (rect->width);
this->height = (int) floor (rect->height);
byteOffset = (stride * (this->y + image->offsetY)) + ((this->x + image->offsetX) * 4);
} }