public void SetPixel(int x, int y, uint color) { this.ValidatePosition(x, y); int xpos = x * this.BitsPerPixel; int pos = (y * this.Stride) + (xpos >> 6); xpos &= 63; if (this.BitsPerPixel == 1) { if (color > 0) { this.Bits[pos] = BitUtils.SetBit(this.Bits[pos], xpos); } else { this.Bits[pos] = BitUtils.ResetBit(this.Bits[pos], xpos); } } else if (this.BitsPerPixel == 24 && xpos + 24 > 64) { int rem = 64 - xpos; this.Bits[pos] = BitUtils.CopyBits(this.Bits[pos], xpos, rem, color); this.Bits[pos + 1] = BitUtils.CopyBits(this.Bits[pos + 1], 0, 24 - rem, color >> rem); } else { this.Bits[pos] = BitUtils.CopyBits(this.Bits[pos], xpos, this.BitsPerPixel, color); } }
private static void CopyArea(Image dst, int xdst, int ydst, int width, int height, Image src, int xsrc, int ysrc) { ulong[] bitssrc = src.Bits; ulong[] bitsdst = dst.Bits; int stride1src = src.Stride1; int stride1dst = dst.Stride1; int offsrc = (ysrc * stride1src) + (xsrc * src.BitsPerPixel); int offdst = (ydst * stride1dst) + (xdst * src.BitsPerPixel); int count = width * src.BitsPerPixel; if (stride1src == stride1dst && xsrc == 0 && xdst == 0 && width == src.Width) { Vectors.Copy(height * src.Stride, bitssrc, ysrc * src.Stride, bitsdst, ydst * dst.Stride); } else { for (int i = 0; i < height; i++, offsrc += stride1src, offdst += stride1dst) { BitUtils.CopyBits(count, bitssrc, offsrc, bitsdst, offdst); } } }
/// <summary> /// Shears the <see cref="Image"/> by the specified amount. /// </summary> /// <param name="shearTan">Shearing force. /// Each horizontal string with Y coordinate equal to y is shifted horizontally by the <i>skew</i>*y pixels. /// </param> /// <returns> /// A new sheared <see cref="Image"/>. /// </returns> public Image Shear(double shearTan) { int maxoffset = Math.Abs((int)((shearTan * (this.Height - 1)) + 0.5)) * this.BitsPerPixel; Image dst = new Image(this.Width + maxoffset, this.Height, this); // allocate new DIB bits int widthsrc1 = this.WidthBits; int widthdst1 = dst.WidthBits; int stridesrc1 = this.Stride1; int stridedst1 = dst.Stride1; ulong[] bitssrc = this.Bits; ulong[] bitsdst = dst.Bits; for (int iy = 0, possrc = 0, posdst = 0; iy < this.Height; iy++, possrc += stridesrc1, posdst += stridedst1) { int offset = Math.Abs((int)((shearTan * iy) + 0.5)) * this.BitsPerPixel; if (offset > 0) { BitUtils.ResetBits(offset, bitsdst, posdst); } BitUtils.CopyBits(widthsrc1, bitssrc, possrc, bitsdst, posdst + offset); if (offset < maxoffset) { BitUtils.ResetBits(widthdst1 - widthsrc1 - offset, bitsdst, posdst + offset + widthsrc1); } } // TODO: add transform return(dst); }
public static void SetPixel(Bitmap bitmap, int x, int y, bool whiteOnBlack) { int bitsPerPixel; switch (bitmap.PixelFormat) { case PixelFormat.Format1bppIndexed: bitsPerPixel = 1; break; case PixelFormat.Format4bppIndexed: bitsPerPixel = 4; break; case PixelFormat.Format8bppIndexed: bitsPerPixel = 8; break; case PixelFormat.Format24bppRgb: bitsPerPixel = 24; break; case PixelFormat.Format32bppRgb: bitsPerPixel = 32; break; default: throw new NotImplementedException(); } BitmapData data = bitmap.LockBits( new Rectangle(0, 0, bitmap.Width, bitmap.Height), ImageLockMode.WriteOnly, bitmap.PixelFormat); unsafe { uint *bits = (uint *)data.Scan0; int xpos = x * bitsPerPixel; int pos = (y * data.Stride / 4) + (xpos >> 5); xpos &= 31; // convert to big-endian if (bitsPerPixel < 8) { xpos = ((xpos / 8) * 8) + (8 - bitsPerPixel) - (xpos & 7); } if (bitsPerPixel == 1) { if (whiteOnBlack) { bits[pos] = BitUtils.ResetBit(bits[pos], xpos); } else { bits[pos] = BitUtils.SetBit(bits[pos], xpos); } } else if (bitsPerPixel == 24 && xpos + bitsPerPixel > 32) { bits[pos] = BitUtils.CopyBits(bits[pos], xpos, 32 - xpos, 0); bits[pos + 1] = BitUtils.CopyBits(bits[pos + 1], 0, xpos + bitsPerPixel - 32, 0); } else { bits[pos] = BitUtils.CopyBits(bits[pos], xpos, bitsPerPixel, 0); } } bitmap.UnlockBits(data); }