/// <summary> /// fill to left side and right side of the line /// </summary> /// <param name="destBuffer"></param> /// <param name="x"></param> /// <param name="y"></param> unsafe void LinearFill(int *destBuffer, int x, int y) { int leftFillX = x; int bufferOffset = _destImgRW.GetBufferOffsetXY32(x, y); int pixelOffset = (imageWidth * y) + x; while (true) { fillRule.SetPixel(destBuffer + bufferOffset); pixelsChecked[pixelOffset] = true; leftFillX--; pixelOffset--; bufferOffset--; if (leftFillX <= 0 || (pixelsChecked[pixelOffset]) || !fillRule.CheckPixel(*(destBuffer + bufferOffset))) { break; } } leftFillX++; // int rightFillX = x; bufferOffset = _destImgRW.GetBufferOffsetXY32(x, y); pixelOffset = (imageWidth * y) + x; while (true) { fillRule.SetPixel(destBuffer + bufferOffset); pixelsChecked[pixelOffset] = true; rightFillX++; pixelOffset++; bufferOffset++; if (rightFillX >= imageWidth || pixelsChecked[pixelOffset] || !fillRule.CheckPixel(*(destBuffer + bufferOffset))) { break; } } rightFillX--; ranges.Enqueue(new Range(leftFillX, rightFillX, y)); }
public static void CopySubBufferToInt32Array(ImageReaderWriterBase buff, int mx, int my, int w, int h, int[] buffer) { //TODO: review here, //check pixel format for an image buffer before use //if mBuffer is not 32 bits ARGB => this may not correct int i = 0; int[] mBuffer = buff.raw_buffer32; for (int y = my; y < h; ++y) { //int xbufferOffset = buff.GetBufferOffsetXY(0, y); int xbuffOffset32 = buff.GetBufferOffsetXY32(0, y); for (int x = mx; x < w; ++x) { //A R G B int val = mBuffer[xbuffOffset32]; byte r = (byte)((val >> 16) & 0xff); // mBuffer[xbufferOffset + 2]; byte g = (byte)((val >> 8) & 0xff); // mBuffer[xbufferOffset + 1]; byte b = (byte)((val >> 0) & 0xff); // mBuffer[xbufferOffset]; //xbufferOffset += 4; xbuffOffset32++; // buffer[i] = b | (g << 8) | (r << 16); i++; } } //int i = 0; //byte[] mBuffer = buff.m_ByteBuffer; //for (int y = my; y < h; ++y) //{ // int xbufferOffset = buff.GetBufferOffsetXY(0, y); // for (int x = mx; x < w; ++x) // { // //A R G B // byte r = mBuffer[xbufferOffset + 2]; // byte g = mBuffer[xbufferOffset + 1]; // byte b = mBuffer[xbufferOffset]; // xbufferOffset += 4; // // // buffer[i] = b | (g << 8) | (r << 16); // i++; // } //} }
public void SetPixelHighRes(ImageReaderWriterBase sourceImage, Color[] destBuffer, int destBufferOffset, int x, int y) { int r, g, b, a; r = g = b = a = LineAA.SUBPIXEL_SCALE * LineAA.SUBPIXEL_SCALE / 2; int weight; int x_lr = x >> LineAA.SUBPIXEL_SHIFT; int y_lr = y >> LineAA.SUBPIXEL_SHIFT; x &= LineAA.SUBPIXEL_MARK; y &= LineAA.SUBPIXEL_MARK; int sourceOffset; int[] ptr = sourceImage.GetBuffer32(); sourceOffset = sourceImage.GetBufferOffsetXY32(x_lr, y_lr); weight = (LineAA.SUBPIXEL_SCALE - x) * (LineAA.SUBPIXEL_SCALE - y); // int ptr_v = ptr[sourceOffset]; r += weight * ((ptr_v >> (CO.R * 8) & 0xff)); // ptr[sourceOffset + CO.R]; g += weight * ((ptr_v >> (CO.G * 8) & 0xff)); //ptr[sourceOffset + CO.G]; b += weight * ((ptr_v >> (CO.B * 8) & 0xff)); //ptr[sourceOffset + CO.B]; a += weight * ((ptr_v >> (CO.A * 8) & 0xff)); //ptr[sourceOffset + CO.A]; // sourceOffset += 1; // sourceImage.BytesBetweenPixelsInclusive; weight = x * (LineAA.SUBPIXEL_SCALE - y); //r += weight * ptr[sourceOffset + CO.R]; //g += weight * ptr[sourceOffset + CO.G]; //b += weight * ptr[sourceOffset + CO.B]; //a += weight * ptr[sourceOffset + CO.A]; ptr_v = ptr[sourceOffset]; r += weight * ((ptr_v >> (CO.R * 8) & 0xff)); // ptr[sourceOffset + CO.R]; g += weight * ((ptr_v >> (CO.G * 8) & 0xff)); //ptr[sourceOffset + CO.G]; b += weight * ((ptr_v >> (CO.B * 8) & 0xff)); //ptr[sourceOffset + CO.B]; a += weight * ((ptr_v >> (CO.A * 8) & 0xff)); //ptr[sourceOffset + CO.A]; // sourceOffset = sourceImage.GetBufferOffsetXY32(x_lr, y_lr + 1); weight = (LineAA.SUBPIXEL_SCALE - x) * y; //r += weight * ptr[sourceOffset + CO.R]; //g += weight * ptr[sourceOffset + CO.G]; //b += weight * ptr[sourceOffset + CO.B]; //a += weight * ptr[sourceOffset + CO.A]; ptr_v = ptr[sourceOffset]; r += weight * ((ptr_v >> (CO.R * 8) & 0xff)); // ptr[sourceOffset + CO.R]; g += weight * ((ptr_v >> (CO.G * 8) & 0xff)); //ptr[sourceOffset + CO.G]; b += weight * ((ptr_v >> (CO.B * 8) & 0xff)); //ptr[sourceOffset + CO.B]; a += weight * ((ptr_v >> (CO.A * 8) & 0xff)); //ptr[sourceOffset + CO.A]; // sourceOffset += 1; // sourceImage.BytesBetweenPixelsInclusive; weight = x * y; //r += weight * ptr[sourceOffset + CO.R]; //g += weight * ptr[sourceOffset + CO.G]; //b += weight * ptr[sourceOffset + CO.B]; //a += weight * ptr[sourceOffset + CO.A]; ptr_v = ptr[sourceOffset]; r += weight * ((ptr_v >> (CO.R * 8) & 0xff)); // ptr[sourceOffset + CO.R]; g += weight * ((ptr_v >> (CO.G * 8) & 0xff)); //ptr[sourceOffset + CO.G]; b += weight * ((ptr_v >> (CO.B * 8) & 0xff)); //ptr[sourceOffset + CO.B]; a += weight * ((ptr_v >> (CO.A * 8) & 0xff)); //ptr[sourceOffset + CO.A]; //destBuffer[destBufferOffset].red = (byte)(r >> LineAA.SUBPIXEL_SHIFT * 2); //destBuffer[destBufferOffset].green = (byte)(g >> LineAA.SUBPIXEL_SHIFT * 2); //destBuffer[destBufferOffset].blue = (byte)(b >> LineAA.SUBPIXEL_SHIFT * 2); //destBuffer[destBufferOffset].alpha = (byte)(a >> LineAA.SUBPIXEL_SHIFT * 2); destBuffer[destBufferOffset] = Color.FromArgb( (byte)(a >> LineAA.SUBPIXEL_SHIFT * 2), (byte)(r >> LineAA.SUBPIXEL_SHIFT * 2), (byte)(g >> LineAA.SUBPIXEL_SHIFT * 2), (byte)(b >> LineAA.SUBPIXEL_SHIFT * 2) ); }
public void Fill(ImageReaderWriterBase bufferToFillOn, int x, int y) { y -= imageHeight; unchecked // this way we can overflow the uint on negative and get a big number { if ((uint)x >= bufferToFillOn.Width || (uint)y >= bufferToFillOn.Height) { return; } } _destImgRW = bufferToFillOn; TempMemPtr destBufferPtr = bufferToFillOn.GetBufferPtr(); unsafe { imageWidth = bufferToFillOn.Width; imageHeight = bufferToFillOn.Height; //reset new buffer, clear mem? pixelsChecked = new bool[imageWidth * imageHeight]; int *destBuffer = (int *)destBufferPtr.Ptr; int startColorBufferOffset = bufferToFillOn.GetBufferOffsetXY32(x, y); int start_color = *(destBuffer + startColorBufferOffset); fillRule.SetStartColor(Drawing.Color.FromArgb( (start_color >> 16) & 0xff, (start_color >> 8) & 0xff, (start_color) & 0xff)); LinearFill(destBuffer, x, y); while (ranges.Count > 0) { Range range = ranges.Dequeue(); int downY = range.y - 1; int upY = range.y + 1; int downPixelOffset = (imageWidth * (range.y - 1)) + range.startX; int upPixelOffset = (imageWidth * (range.y + 1)) + range.startX; for (int rangeX = range.startX; rangeX <= range.endX; rangeX++) { if (range.y > 0) { if (!pixelsChecked[downPixelOffset]) { int bufferOffset = bufferToFillOn.GetBufferOffsetXY32(rangeX, downY); if (fillRule.CheckPixel(*(destBuffer + bufferOffset))) { LinearFill(destBuffer, rangeX, downY); } } } if (range.y < (imageHeight - 1)) { if (!pixelsChecked[upPixelOffset]) { int bufferOffset = bufferToFillOn.GetBufferOffsetXY32(rangeX, upY); if (fillRule.CheckPixel(*(destBuffer + bufferOffset))) { LinearFill(destBuffer, rangeX, upY); } } } upPixelOffset++; downPixelOffset++; } } } destBufferPtr.Release(); }