### Render Text with WriteableBitmapEx Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Demonstrates how to render filled, outlined, and anti-aliased text onto a WriteableBitmap. Ensure the WriteableBitmapEx NuGet package is installed and the necessary using statements are included. ```csharp using System.Globalization; using System.Windows; using System.Windows.Media; using System.Windows.Media.Imaging; WriteableBitmap bmp = BitmapFactory.New(500, 200); var typeface = new Typeface( new FontFamily("Segoe UI"), FontStyles.Normal, FontWeights.Bold, FontStretches.Normal); var text = new FormattedText( "Hello, WriteableBitmapEx!", CultureInfo.GetCultureInfo("en-us"), FlowDirection.LeftToRight, typeface, 48.0, Brushes.Black); using (bmp.GetBitmapContext()) { bmp.Clear(Colors.White); // Filled solid text bmp.FillText(text, x: 10, y: 20, Colors.DarkBlue); // Outlined text bmp.DrawText(text, x: 10, y: 100, Colors.Red); // Anti-aliased outlined text with stroke thickness 2 bmp.DrawTextAa(text, x: 10, y: 100, Colors.Red, thickness: 2); } ``` -------------------------------- ### Initialize and Manipulate WriteableBitmap Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Initializes a WriteableBitmap, sets it as an image source, and demonstrates basic pixel operations like setting, getting, clearing, and loading images. Ensure the image resource path is correct. ```cs // Initialize the WriteableBitmap with size 512x512 and set it as source of an Image control WriteableBitmap writeableBmp = BitmapFactory.New(512, 512); ImageControl.Source = writeableBmp; using(writeableBmp.GetBitmapContext()) { // Load an image from the calling Assembly's resources via the relative path writeableBmp = BitmapFactory.New(1, 1).FromResource("Data/flower2.png"); // Clear the WriteableBitmap with white color writeableBmp.Clear(Colors.White); // Set the pixel at P(10, 13) to black writeableBmp.SetPixel(10, 13, Colors.Black); // Get the color of the pixel at P(30, 43) Color color = writeableBmp.GetPixel(30, 43); } ``` -------------------------------- ### Draw Curves on WriteableBitmap Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Illustrates drawing a cubic Bezier curve and both filled and unfilled Cardinal splines. The Cardinal spline examples require an array of points and a tension value. ```cs // Cubic Beziér curve from P1(5, 5) to P4(20, 7) // with the control points P2(10, 15) and P3(15, 0) writeableBmp.DrawBezier(5, 5, 10, 15, 15, 0, 20, 7, Colors.Purple); // Cardinal spline with a tension of 0.5 // through the points P1(10, 5), P2(20, 40) and P3(30, 30) int[] pts = new int[] { 10, 5, 20, 40, 30, 30}; writeableBmp.DrawCurve(pts, 0.5, Colors.Yellow); // A filled Cardinal spline with a tension of 0.5 // through the points P1(10, 5), P2(20, 40) and P3(30, 30) writeableBmp.FillCurveClosed(pts, 0.5, Colors.Green); ``` -------------------------------- ### Draw Geometric Shapes on WriteableBitmap Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Demonstrates drawing a triangle, rectangle, ellipse, and polyline. The polyline example shows how to define points for a closed shape. ```cs // Black triangle with the points P1(10, 5), P2(20, 40) and P3(30, 10) writeableBmp.DrawTriangle(10, 5, 20, 40, 30, 10, Colors.Black); // Red rectangle from the point P1(2, 4) that is 10px wide and 6px high writeableBmp.DrawRectangle(2, 4, 12, 10, Colors.Red); // Filled blue ellipse with the center point P1(2, 2) that is 8px wide and 5px high writeableBmp.FillEllipseCentered(2, 2, 8, 5, Colors.Blue); // Closed green polyline with P1(10, 5), P2(20, 40), P3(30, 30) and P4(7, 8) int[] p = new int[] { 10, 5, 20, 40, 30, 30, 7, 8, 10, 5 }; writeableBmp.DrawPolyline(p, Colors.Green); ``` -------------------------------- ### Set and Get Individual Pixels Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Set or get the color of a specific pixel. For batch operations, access 'context.Pixels' directly within a 'GetBitmapContext()' block. ```csharp WriteableBitmap bmp = BitmapFactory.New(100, 100); using (bmp.GetBitmapContext()) { // Set pixel at (10, 20) to opaque red bmp.SetPixel(10, 20, Colors.Red); // Set pixel with explicit ARGB components bmp.SetPixel(15, 25, 255, 0, 128, 0); // a=255, r=0, g=128, b=0 // Set pixel with extra alpha override bmp.SetPixel(20, 30, 128, Colors.Blue); // 50% transparent blue } // Read back a pixel color Color c = bmp.GetPixel(10, 20); // c.R == 255, c.G == 0, c.B == 0, c.A == 255 byte brightness = bmp.GetBrightness(10, 20); ``` -------------------------------- ### Create NuGet Package Source: https://github.com/reneschulte/writeablebitmapex/blob/master/NUGET_PACKAGE_BUILD.md Creates the NuGet package after all libraries have been built and placed in the Build\Release\ directory. Navigate to the Nuget folder and run the pack command. This generates a .nupkg file in the Build\nuget\ directory. ```cmd cd Nuget pack.cmd ``` -------------------------------- ### Build WPF Libraries Source: https://github.com/reneschulte/writeablebitmapex/blob/master/NUGET_PACKAGE_BUILD.md Builds the WPF libraries for .NET Framework 4.0 and .NET Core 3.0. Ensure you are in the Solution directory. The output DLLs will be placed in Build\Release\. ```cmd cd Solution dotnet build WriteableBitmapEx_All.sln -c Release /p:EnableWindowsTargeting=true ``` -------------------------------- ### Crop, Resize, Rotate, and Flip WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt These methods return new WriteableBitmap instances for transformations. Resize offers 'Bilinear' and 'NearestNeighbor' interpolation. Rotate supports 90° steps. Flip can be 'Horizontal' or 'Vertical'. ```csharp WriteableBitmap source = BitmapFactory.New(400, 300); // ... draw into source ... // Crop a 200x150 region starting at (50, 25) WriteableBitmap cropped = source.Crop(50, 25, 200, 150); // Resize to 800x600 using bilinear interpolation WriteableBitmap resized = source.Resize(800, 600, WriteableBitmapExtensions.Interpolation.Bilinear); // Resize using nearest neighbor (faster, blocky) WriteableBitmap thumb = source.Resize(100, 75, WriteableBitmapExtensions.Interpolation.NearestNeighbor); // Rotate 90 degrees clockwise WriteableBitmap rotated90 = source.Rotate(90); // Rotate 270 degrees clockwise (= 90° counter-clockwise) WriteableBitmap rotated270 = source.Rotate(270); // Flip horizontally (mirror around vertical axis) WriteableBitmap flippedH = source.Flip(WriteableBitmapExtensions.FlipMode.Horizontal); // Flip vertically (mirror around horizontal axis) WriteableBitmap flippedV = source.Flip(WriteableBitmapExtensions.FlipMode.Vertical); ``` -------------------------------- ### Draw Splines and Curves on WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Demonstrates drawing cubic Bézier curves and Cardinal splines, as well as filling closed Cardinal splines. Requires specifying control points or a set of points and tension. ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 400); using (bmp.GetBitmapContext()) { // Cubic Bézier from P1(20,200) to P4(380,200) // with control points P2(100,50) and P3(300,350) bmp.DrawBezier(20, 200, 100, 50, 300, 350, 380, 200, Colors.DarkBlue); // Cardinal spline through four points, tension 0.5 int[] splinePts = new int[] { 50, 300, 150, 100, 250, 300, 350, 100 }; bmp.DrawCurve(splinePts, 0.5f, Colors.DarkGreen); // Filled closed Cardinal spline int[] closedPts = new int[] { 100, 200, 200, 50, 300, 200, 200, 350 }; bmp.FillCurveClosed(closedPts, 0.5f, Colors.Coral); } ``` -------------------------------- ### Draw Lines on WriteableBitmap Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Demonstrates drawing a standard green line and a blue anti-aliased line with a specified stroke width. The fastest draw line method is also shown, which requires direct access to the pixel array. ```cs // Green line from P1(1, 2) to P2(30, 40) writeableBmp.DrawLine(1, 2, 30, 40, Colors.Green); // Line from P1(1, 2) to P2(30, 40) using the fastest draw line method int[] pixels = writeableBmp.Pixels; int w = writeableBmp.PixelWidth; int h = writeableBmp.PixelHeight; WriteableBitmapExtensions.DrawLine(pixels, w, h, 1, 2, 30, 40, myIntColor); // Blue anti-aliased line from P1(10, 20) to P2(50, 70) with a stroke of 5 writeableBmp.DrawLineAa(10, 20, 50, 70, Colors.Blue, 5); ``` -------------------------------- ### Crop / Resize / Rotate / Flip Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt These methods return new WriteableBitmap instances that are cropped, resized (nearest neighbor or bilinear), rotated in 90° steps, or flipped along an axis. ```APIDOC ## Crop / Resize / Rotate / Flip — Transformations These methods return new `WriteableBitmap` instances that are cropped, resized (nearest neighbor or bilinear), rotated in 90° steps, or flipped along an axis. ```csharp WriteableBitmap source = BitmapFactory.New(400, 300); // ... draw into source ... // Crop a 200x150 region starting at (50, 25) WriteableBitmap cropped = source.Crop(50, 25, 200, 150); // Resize to 800x600 using bilinear interpolation WriteableBitmap resized = source.Resize(800, 600, WriteableBitmapExtensions.Interpolation.Bilinear); // Resize using nearest neighbor (faster, blocky) WriteableBitmap thumb = source.Resize(100, 75, WriteableBitmapExtensions.Interpolation.NearestNeighbor); // Rotate 90 degrees clockwise WriteableBitmap rotated90 = source.Rotate(90); // Rotate 270 degrees clockwise (= 90° counter-clockwise) WriteableBitmap rotated270 = source.Rotate(270); // Flip horizontally (mirror around vertical axis) WriteableBitmap flippedH = source.Flip(WriteableBitmapExtensions.FlipMode.Horizontal); // Flip vertically (mirror around horizontal axis) WriteableBitmap flippedV = source.Flip(WriteableBitmapExtensions.FlipMode.Vertical); ``` ``` -------------------------------- ### Create WriteableBitmap with BitmapFactory.New Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Use BitmapFactory.New to create a WriteableBitmap with the correct pixel format for WPF. It can also convert existing BitmapSources. ```csharp using System.Windows.Media.Imaging; // Create a 512x512 bitmap and bind it to a WPF Image control WriteableBitmap canvas = BitmapFactory.New(512, 512); ImageControl.Source = canvas; // Convert an existing BitmapSource to Pbgra32 format (WPF only) BitmapSource existing = /* load from file or resource */; WriteableBitmap converted = BitmapFactory.ConvertToPbgra32Format(existing); ``` -------------------------------- ### Apply Per-Pixel Functions with ForEach Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Iterate over every pixel and apply a user-supplied function to set or transform its color. Enables procedural generation and per-pixel effects in a single pass. ```csharp WriteableBitmap bmp = BitmapFactory.New(256, 256); // Generate a gradient procedurally based on coordinatesmp.ForEach((x, y) => Color.FromArgb(255, (byte)x, (byte)y, 128)); // Transform existing pixel colors (e.g., invert)mp.ForEach((x, y, oldColor) => Color.FromArgb(oldColor.A, (byte)(255 - oldColor.R), (byte)(255 - oldColor.G), (byte)(255 - oldColor.B))); ``` -------------------------------- ### BitmapFactory.New — Create a WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Factory method to create a new WriteableBitmap with the correct pixel format and DPI for WPF. It also provides a utility to convert existing BitmapSources to the Pbgra32 format. ```APIDOC ## BitmapFactory.New — Create a WriteableBitmap ### Description `BitmapFactory.New` is the recommended way to create a new `WriteableBitmap` with the correct pixel format (`Pbgra32` at 96 DPI for WPF). It ensures the bitmap is initialized with valid dimensions and is ready for use with all WriteableBitmapEx extension methods. ### Usage ```csharp using System.Windows.Media.Imaging; // Create a 512x512 bitmap and bind it to a WPF Image control WriteableBitmap canvas = BitmapFactory.New(512, 512); ImageControl.Source = canvas; // Convert an existing BitmapSource to Pbgra32 format (WPF only) BitmapSource existing = /* load from file or resource */; WriteableBitmap converted = BitmapFactory.ConvertToPbgra32Format(existing); ``` ``` -------------------------------- ### Publish NuGet Package Source: https://github.com/reneschulte/writeablebitmapex/blob/master/NUGET_PACKAGE_BUILD.md Publishes the created NuGet package to NuGet.org. This script requires manual updates to the version number and API key. Note that the script attempts to delete the old version, which might need to be commented out. ```cmd push.cmd ``` -------------------------------- ### Draw Various Line Types on WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Demonstrates drawing different types of lines including DDA, anti-aliased, Bresenham, dotted, and penned lines. Supports optional clipping rectangles. ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 400); using (bmp.GetBitmapContext()) { // Fast DDA line from (0,0) to (399,399) in green bmp.DrawLine(0, 0, 399, 399, Colors.Green); // Anti-aliased line with stroke thickness 3 bmp.DrawLineAa(10, 200, 390, 200, Colors.Red, 3); // Bresenham line clipped to a sub-region var clip = new Rect(50, 50, 300, 300); bmp.DrawLineBresenham(0, 0, 399, 399, Colors.Blue, clip); // Dotted line: 4px segments with 2px gaps bmp.DrawLineDotted(0, 100, 400, 100, dotSpace: 2, dotLength: 4, Colors.Black); // Penned line (uses a bitmap as the pen/stamp) WriteableBitmap penBmp = BitmapFactory.New(5, 5); penBmp.Clear(Colors.DarkRed); bmp.DrawLinePenned(10, 10, 200, 200, penBmp); } ``` -------------------------------- ### Test Case for DrawLine and DrawLineAa Precision Source: https://github.com/reneschulte/writeablebitmapex/blob/master/ISSUE_VALIDATION_SUMMARY.md This C# code snippet sets up a large WriteableBitmap and draws lines using both DrawLine and DrawLineAa methods to test precision. It's used to compare results before and after a precision fix. ```csharp WriteableBitmap image = new WriteableBitmap(30000, 10000, 96, 96, PixelFormats.Pbgra32, null); image.Clear(Colors.White); image.DrawLine(0, 0, 29999, 9999, Colors.Black); image.DrawLineAa(0, 0, 29999, 9999, Colors.Red); ``` -------------------------------- ### Convert WriteableBitmap to/from Byte Arrays and Streams Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Methods for serializing and deserializing pixel data. ToByteArray exports raw ARGB bytes, while FromByteArray imports them. WriteTga saves to a TGA file stream. Clone creates a fast copy. ```csharp WriteableBitmap bmp = BitmapFactory.New(64, 64); // ... draw ... // Export all pixels to a raw ARGB byte array byte[] rawBytes = bmp.ToByteArray(); // Import back from a byte array WriteableBitmap bmp2 = BitmapFactory.New(64, 64); bmp2.FromByteArray(rawBytes); // Load from an assembly resource (WPF) WriteableBitmap fromRes = BitmapFactory.New(1, 1).FromResource("Images/sprite.png"); // Save as TGA image to a file stream using (var stream = File.OpenWrite("output.tga")) { bmp.WriteTga(stream); } // Clone the bitmap (fast block-copy) WriteableBitmap cloned = bmp.Clone(); ``` -------------------------------- ### Test Output: Old vs. New DrawLine Precision Source: https://github.com/reneschulte/writeablebitmapex/blob/master/VALIDATION_REPORT.md Compares the error in DrawLine endpoint calculation between the old 8-bit precision method and the new 24-bit precision method, demonstrating the effectiveness of the fix. ```text OLD METHOD (8-bit precision only): ----------------------------------- Expected final Y: 9999 Actual final Y: 9960 Error: 39 pixels ❌ FAIL - Off by 39 pixels! NEW METHOD (24-bit precision with EXTRA_PRECISION_SHIFT): ---------------------------------------------------------- Expected final Y: 9999 Actual final Y: 9999 Error: 0 pixels ✓ PASS - Exact precision! ``` -------------------------------- ### Blit — Compositing and Blending Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt `Blit` copies (blits) pixels from a source `WriteableBitmap` onto a destination with various blend modes. `BlitRender` applies an affine transformation with bilinear interpolation during the blit. ```APIDOC ## Blit — Compositing and Blending `Blit` copies (blits) pixels from a source `WriteableBitmap` onto a destination with various blend modes: `Alpha`, `Additive`, `Subtractive`, `Multiply`, `Mask`, `ColorKeying`, or `None`. `BlitRender` applies an affine transformation with bilinear interpolation during the blit. ```csharp WriteableBitmap dest = BitmapFactory.New(512, 512); WriteableBitmap sprite = /* load sprite */; var destRect = new Rect(100, 100, sprite.PixelWidth, sprite.PixelHeight); var sourceRect = new Rect(0, 0, sprite.PixelWidth, sprite.PixelHeight); using (dest.GetBitmapContext()) { // Alpha blend sprite onto destination at position (100,100) dest.Blit(destRect, sprite, sourceRect, WriteableBitmapExtensions.BlendMode.Alpha); // Additive blend (brightens destination) dest.Blit(destRect, sprite, sourceRect, WriteableBitmapExtensions.BlendMode.Additive); // No blend — straight copy (fastest) dest.Blit(new Point(200, 200), sprite, sourceRect); // Blit with color tinting (white = no tint) dest.Blit(destRect, sprite, sourceRect, Colors.White, WriteableBitmapExtensions.BlendMode.Alpha); } ``` ``` -------------------------------- ### Draw Outlined Shapes on WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Illustrates drawing outlined geometric shapes such as polylines, triangles, rectangles, and ellipses. Anti-aliased variants and thickness options are available. ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 400); using (bmp.GetBitmapContext()) { // Closed polyline (pentagon) int[] pts = new int[] { 200, 50, 350, 180, 290, 350, 110, 350, 50, 180, 200, 50 }; bmp.DrawPolyline(pts, Colors.Purple); // Anti-aliased polyline with thickness bmp.DrawPolylineAa(pts, Colors.Orange, thickness: 2); // Triangle with three vertices bmp.DrawTriangle(100, 10, 200, 190, 10, 190, Colors.Green); // Rectangle from top-left (5,5) to bottom-right (195,195) bmp.DrawRectangle(5, 5, 195, 195, Colors.Red); // Ellipse centered at (200,200) with x-radius 80, y-radius 50 bmp.DrawEllipseCentered(200, 200, 80, 50, Colors.Blue); } ``` -------------------------------- ### Render Text on WriteableBitmap Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Renders text onto the WriteableBitmap using FormattedText. Supports various fonts, sizes, weights, and languages including Persian, Arabic, and Chinese. ```cs // Fills a text on the bitmap, Font, size, weight and almost any option is changable, all text supported with WPF is also supported here including Persian, Arabic, Chinese etc var formattedText = new FormattedText("Test String", CultureInfo.GetCultureInfo("en-us"), FlowDirection.LeftToRight, new Typeface(new FontFamily("Sans MS"), FontStyles.Normal, FontWeights.Medium, FontStretches.Normal), 80.0, System.Windows.Media.Brushes.Black); writeableBmp.FillText(formattedText, 100, 100, Colors.Blue, 5); ``` -------------------------------- ### Advanced WriteableBitmap Operations Source: https://github.com/reneschulte/writeablebitmapex/blob/master/README.md Covers advanced operations like blitting another bitmap with a specified blend mode, overriding pixels using a function, cloning, saving to a stream, cropping, rotating, flipping, and resizing. ```cs // Blit a bitmap using the additive blend mode at P1(10, 10) writeableBmp.Blit(new Point(10, 10), bitmap, sourceRect, Colors.White, WriteableBitmapExtensions.BlendMode.Additive); // Override all pixels with a function that changes the color based on the coordinate writeableBmp.ForEach((x, y, color) => Color.FromArgb(color.A, (byte)(color.R / 2), (byte)(x * y), 100)); } // Invalidate and present in the Dispose call // Take snapshot var clone = writeableBmp.Clone(); // Save to a TGA image stream (file for example) writeableBmp.WriteTga(stream); // Crops the WriteableBitmap to a region starting at P1(5, 8) and 10px wide and 10px high var cropped = writeableBmp.Crop(5, 8, 10, 10); // Rotates a copy of the WriteableBitmap 90 degress clockwise and returns the new copy var rotated = writeableBmp.Rotate(90); // Flips a copy of the WriteableBitmap around the horizontal axis and returns the new copy var flipped = writeableBmp.Flip(FlipMode.Horizontal); // Resizes the WriteableBitmap to 200px wide and 300px high using bilinear interpolation var resized = writeableBmp.Resize(200, 300, WriteableBitmapExtensions.Interpolation.Bilinear); ``` -------------------------------- ### ToByteArray / FromByteArray / FromStream / WriteTga — Conversion Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt These methods serialize and deserialize pixel data to/from byte arrays, streams, and TGA files. `FromResource` and `FromContent` load platform image files into a `WriteableBitmap` from application resources or URIs. ```APIDOC ## ToByteArray / FromByteArray / FromStream / WriteTga — Conversion These methods serialize and deserialize pixel data to/from byte arrays, streams, and TGA files. `FromResource` and `FromContent` load platform image files into a `WriteableBitmap` from application resources or URIs. ```csharp WriteableBitmap bmp = BitmapFactory.New(64, 64); // ... draw ... // Export all pixels to a raw ARGB byte array byte[] rawBytes = bmp.ToByteArray(); // Import back from a byte array WriteableBitmap bmp2 = BitmapFactory.New(64, 64); bmp2.FromByteArray(rawBytes); // Load from an assembly resource (WPF) WriteableBitmap fromRes = BitmapFactory.New(1, 1).FromResource("Images/sprite.png"); // Save as TGA image to a file stream using (var stream = File.OpenWrite("output.tga")) { bmp.WriteTga(stream); } // Clone the bitmap (fast block-copy) WriteableBitmap cloned = bmp.Clone(); ``` ``` -------------------------------- ### Efficient Pixel Access with BitmapContext Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Wrap all drawing operations within a 'using (bmp.GetBitmapContext())' block for maximum performance. The bitmap is only invalidated and presented upon context disposal. ```csharp WriteableBitmap bmp = BitmapFactory.New(256, 256); // Wrap all operations in one context for best performance using (bmp.GetBitmapContext()) { bmp.Clear(Colors.White); bmp.DrawLine(0, 0, 255, 255, Colors.Black); bmp.FillEllipseCentered(128, 128, 50, 50, Colors.Blue); } // Bitmap is invalidated/presented here ``` -------------------------------- ### Original DrawLine Precision Issue Source: https://github.com/reneschulte/writeablebitmapex/blob/master/VALIDATION_REPORT.md Illustrates the 8-bit fixed-point precision used in the original DrawLine implementation, which led to cumulative rounding errors over long distances. ```csharp int incy = (dy << 8) / dx; // Only 8 bits of fractional precision ``` -------------------------------- ### ForEach — Per-Pixel Function Application Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Applies a user-defined function to each pixel of the bitmap, enabling procedural image generation and per-pixel effects in a single pass. ```APIDOC ## ForEach — Per-Pixel Function Application ### Description `ForEach` iterates over every pixel and applies a user-supplied function to set or transform each pixel's color, enabling procedural image generation and per-pixel effects in a single pass. ### Usage ```csharp WriteableBitmap bmp = BitmapFactory.New(256, 256); // Generate a gradient procedurally based on coordinatesmp.ForEach((x, y) => Color.FromArgb(255, (byte)x, (byte)y, 128)); // Transform existing pixel colors (e.g., invert)mp.ForEach((x, y, oldColor) => Color.FromArgb(oldColor.A, (byte)(255 - oldColor.R), (byte)(255 - oldColor.G), (byte)(255 - oldColor.B))); ``` ``` -------------------------------- ### Fill Shapes on WriteableBitmap Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Shows how to fill geometric shapes including rectangles, ellipses, triangles, and polygons. Supports alpha blending for rectangles and different polygon filling rules. ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 400); using (bmp.GetBitmapContext()) { // Filled rectangle with alpha blending enabled bmp.FillRectangle(10, 10, 200, 100, Colors.LightBlue); // Filled ellipse centered at (200,200), semi-axes 80x50 bmp.FillEllipseCentered(200, 200, 80, 50, Colors.Green); // Filled triangle bmp.FillTriangle(10, 390, 200, 10, 390, 390, Colors.Yellow); // Filled arbitrary polygon (star shape) int[] starPts = new int[] { 200,50, 230,160, 350,160, 250,230, 290,360, 200,280, 110,360, 150,230, 50,160, 170,160 }; bmp.FillPolygon(starPts, Colors.Gold); } ``` -------------------------------- ### DrawLineAa Endpoint Clamping Logic Source: https://github.com/reneschulte/writeablebitmapex/blob/master/VALIDATION_REPORT.md Demonstrates the endpoint clamping mechanism in DrawLineAa, which restricts coordinates to `[1, width-2]` and `[1, height-2]` to support anti-aliasing and prevent out-of-bounds access. ```csharp if (x1 < 1) x1 = 1; if (x1 > pixelWidth - 2) x1 = pixelWidth - 2; // Similar for x2, y1, y2 ``` -------------------------------- ### DrawLine / DrawLineAa Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Draws lines on the bitmap. `DrawLine` uses an optimized DDA algorithm with Cohen-Sutherland clipping, while `DrawLineAa` draws an anti-aliased line using the Gupta-Sproull algorithm. Alternate algorithms and clipping are supported. ```APIDOC ## DrawLine / DrawLineAa ### Description Draws lines on the bitmap. `DrawLine` uses an optimized DDA algorithm with Cohen-Sutherland clipping, while `DrawLineAa` draws an anti-aliased line using the Gupta-Sproull algorithm. `DrawLineBresenham` and `DrawLineDDA` provide alternate algorithms. All support an optional `clipRect` parameter. ### Methods - `DrawLine(int x1, int y1, int x2, int y2, Color color)` - `DrawLineAa(int x1, int y1, int x2, int y2, Color color, int thickness = 1)` - `DrawLineBresenham(int x1, int y1, int x2, int y2, Color color, Rect clipRect = null)` - `DrawLineDDA(int x1, int y1, int x2, int y2, Color color, Rect clipRect = null)` - `DrawLineDotted(int x1, int y1, int x2, int y2, Color color, int dotLength = 4, int dotSpace = 4, Rect clipRect = null)` - `DrawLinePenned(int x1, int y1, int x2, int y2, WriteableBitmap pen, Rect clipRect = null)` ### Parameters - **x1, y1**: Coordinates of the starting point. - **x2, y2**: Coordinates of the ending point. - **color**: The color of the line. - **thickness**: The thickness of the anti-aliased line. - **clipRect**: An optional rectangle to clip the line to. - **dotLength**: The length of the line segments for dotted lines. - **dotSpace**: The space between line segments for dotted lines. - **pen**: A WriteableBitmap to use as a pen for `DrawLinePenned`. ``` -------------------------------- ### Clear WriteableBitmap to a Color Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Fill the entire WriteableBitmap with a solid color or clear it to transparent. Uses a fast block-copy strategy. ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 300); using (bmp.GetBitmapContext()) { // Fill with white bmp.Clear(Colors.White); // Or clear to fully transparent bmp.Clear(); } ``` -------------------------------- ### Clear — Fill Bitmap with a Color Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Fills the entire WriteableBitmap with a specified color or clears it to transparent. Uses a fast block-copy strategy for efficiency. ```APIDOC ## Clear — Fill Bitmap with a Color ### Description `Clear` fills the entire `WriteableBitmap` with a solid color using a fast doubling block-copy strategy, or clears it to transparent (zero) when called with no arguments. ### Usage ```csharp WriteableBitmap bmp = BitmapFactory.New(400, 300); using (bmp.GetBitmapContext()) { // Fill with white bmp.Clear(Colors.White); // Or clear to fully transparent bmp.Clear(); } ``` ``` -------------------------------- ### SetPixel / GetPixel — Individual Pixel Operations Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Allows setting the color of a specific pixel and retrieving the color of a pixel at given coordinates. For performance-critical batch operations, direct access to `context.Pixels` within a `GetBitmapContext()` block is recommended. ```APIDOC ## SetPixel / GetPixel — Individual Pixel Operations ### Description `SetPixel` writes a color to a specific coordinate (with optional alpha), and `GetPixel` reads it back as a `Color` struct. For batch pixel operations, access `context.Pixels` directly inside a `GetBitmapContext()` block for maximum performance. ### Usage ```csharp WriteableBitmap bmp = BitmapFactory.New(100, 100); using (bmp.GetBitmapContext()) { // Set pixel at (10, 20) to opaque red bmp.SetPixel(10, 20, Colors.Red); // Set pixel with explicit ARGB components bmp.SetPixel(15, 25, 255, 0, 128, 0); // a=255, r=0, g=128, b=0 // Set pixel with extra alpha override bmp.SetPixel(20, 30, 128, Colors.Blue); // 50% transparent blue } // Read back a pixel color Color c = bmp.GetPixel(10, 20); // c.R == 255, c.G == 0, c.B == 0, c.A == 255 byte brightness = bmp.GetBrightness(10, 20); ``` ``` -------------------------------- ### Integer Division Constraint in DrawLine Source: https://github.com/reneschulte/writeablebitmapex/blob/master/VALIDATION_REPORT.md Highlights the remaining 0-1 pixel error in DrawLine due to integer division truncation, even with increased precision. This is an inherent limitation of fixed-point arithmetic. ```csharp long incy = ((long)dy << 24) / dx; // Integer division truncates ``` -------------------------------- ### BitmapContext / GetBitmapContext — Efficient Pixel Access Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Obtain a BitmapContext for direct pixel buffer access. Wrapping drawing operations within a `using` block ensures efficient updates and presentation of the bitmap. ```APIDOC ## BitmapContext / GetBitmapContext — Efficient Pixel Access ### Description `GetBitmapContext()` returns a `BitmapContext` that provides direct access to the pixel buffer. Wrapping all drawing operations in a single `using` block is critical for performance: the bitmap is only invalidated and presented when the context is disposed, avoiding redundant redraws. ### Usage ```csharp WriteableBitmap bmp = BitmapFactory.New(256, 256); // Wrap all operations in one context for best performance using (bmp.GetBitmapContext()) { bmp.Clear(Colors.White); bmp.DrawLine(0, 0, 255, 255, Colors.Black); bmp.FillEllipseCentered(128, 128, 50, 50, Colors.Blue); } // Bitmap is invalidated/presented here ``` ``` -------------------------------- ### Apply Convolution Kernels for Image Filtering Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Convolute applies custom or pre-defined kernels (e.g., Gaussian blur, sharpen) to a bitmap. AdjustBrightness, Invert, Gray, AdjustContrast, and AdjustGamma provide direct pixel manipulations. ```csharp WriteableBitmap bmp = /* load bitmap */; // Gaussian blur with 5x5 kernel WriteableBitmap blurred = bmp.Convolute(WriteableBitmapExtensions.KernelGaussianBlur5x5); // Sharpen with 3x3 kernel WriteableBitmap sharpened = bmp.Convolute(WriteableBitmapExtensions.KernelSharpen3x3); // Custom emboss kernel int[,] emboss = { {-2,-1,0}, {-1,1,1}, {0,1,2} }; WriteableBitmap embossed = bmp.Convolute(emboss, kernelFactorSum: 1, kernelOffsetSum: 0); // Invert colors WriteableBitmap inverted = bmp.Invert(); // Convert to grayscale WriteableBitmap gray = bmp.Gray(); // Adjust brightness (+50 out of 255) WriteableBitmap bright = bmp.AdjustBrightness(50); // Adjust contrast and gamma WriteableBitmap adjusted = bmp.AdjustContrast(1.5f); WriteableBitmap gamma = bmp.AdjustGamma(2.2f); ``` -------------------------------- ### DrawLine Precision Fix Implementation Source: https://github.com/reneschulte/writeablebitmapex/blob/master/VALIDATION_REPORT.md Shows the updated DrawLine implementation using 24-bit precision for slope calculations to prevent cumulative errors. Uses `long` for intermediate calculations to avoid overflow. ```csharp const int PRECISION_SHIFT = 8; const int EXTRA_PRECISION_SHIFT = 16; // NEW: Extra 16 bits // Before: 8-bit precision // int incy = (dy << 8) / dx; // After: 24-bit precision long incy = ((long)dy << (PRECISION_SHIFT + EXTRA_PRECISION_SHIFT)) / dx; ``` -------------------------------- ### Blit Pixels Between WriteableBitmaps Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt The Blit method copies pixels from a source to a destination WriteableBitmap with various blend modes. Ensure the destination bitmap context is obtained using GetBitmapContext() for modifications. ```csharp WriteableBitmap dest = BitmapFactory.New(512, 512); WriteableBitmap sprite = /* load sprite */; var destRect = new Rect(100, 100, sprite.PixelWidth, sprite.PixelHeight); var sourceRect = new Rect(0, 0, sprite.PixelWidth, sprite.PixelHeight); using (dest.GetBitmapContext()) { // Alpha blend sprite onto destination at position (100,100) dest.Blit(destRect, sprite, sourceRect, WriteableBitmapExtensions.BlendMode.Alpha); // Additive blend (brightens destination) dest.Blit(destRect, sprite, sourceRect, WriteableBitmapExtensions.BlendMode.Additive); // No blend — straight copy (fastest) dest.Blit(new Point(200, 200), sprite, sourceRect); // Blit with color tinting (white = no tint) dest.Blit(destRect, sprite, sourceRect, Colors.White, WriteableBitmapExtensions.BlendMode.Alpha); } ``` -------------------------------- ### DrawBezier / DrawCurve / FillCurveClosed Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Draws and fills splines and curves. `DrawBezier` draws a cubic Bézier curve. `DrawCurve` draws a Cardinal spline through a set of points. `FillCurveClosed` fills a closed Cardinal spline. ```APIDOC ## DrawBezier / DrawCurve / FillCurveClosed ### Description `DrawBezier` draws a cubic Bézier curve between two points with two control points. `DrawCurve` draws a Cardinal spline through a set of points with a given tension. `FillCurveClosed` fills a closed Cardinal spline. ### Methods - `DrawBezier(int x1, int y1, int x2, int y2, int x3, int y3, int x4, int y4, Color color)` - `DrawCurve(int[] points, float tension, Color color)` - `FillCurveClosed(int[] points, float tension, Color color)` ### Parameters - **x1, y1, x2, y2, x3, y3, x4, y4**: Coordinates defining the start point, control points, and end point of the Bézier curve. - **points**: An array of integers representing the points the curve passes through (x1, y1, x2, y2, ...). - **tension**: A float value controlling the tension of the Cardinal spline. - **color**: The color of the curve or filled region. ``` -------------------------------- ### FillRectangle / FillEllipse / FillTriangle / FillPolygon Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Fills geometric shapes with a solid color. `FillRectangle` supports optional alpha blending. `FillPolygon` and `FillPolygonsEvenOdd` handle simple and complex (self-intersecting) polygons respectively. ```APIDOC ## FillRectangle / FillEllipse / FillTriangle / FillPolygon ### Description Filled shape methods paint solid regions. `FillRectangle` supports optional alpha blending. `FillPolygon` and `FillPolygonsEvenOdd` handle simple and complex (self-intersecting) polygons respectively. ### Methods - `FillRectangle(int x1, int y1, int x2, int y2, Color color)` - `FillEllipseCentered(int cx, int cy, int radiusX, int radiusY, Color color)` - `FillTriangle(int x1, int y1, int x2, int y2, int x3, int y3, Color color)` - `FillPolygon(int[] points, Color color)` - `FillPolygonsEvenOdd(int[] points, Color color)` ### Parameters - **x1, y1, x2, y2**: Coordinates of the top-left and bottom-right corners of the rectangle. - **cx, cy**: Coordinates of the center of the ellipse. - **radiusX, radiusY**: The horizontal and vertical radii of the ellipse. - **x1, y1, x2, y2, x3, y3**: Coordinates defining the vertices of the triangle. - **points**: An array of integers representing the vertices of the polygon (x1, y1, x2, y2, ...). - **color**: The color to fill the shape with. ``` -------------------------------- ### DrawPolyline / DrawTriangle / DrawRectangle / DrawEllipse Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt Draws outlined geometric shapes. Anti-aliased variants are available for polylines and ellipses. All accept either a `Color` struct or a pre-packed `int` color. ```APIDOC ## DrawPolyline / DrawTriangle / DrawRectangle / DrawEllipse ### Description These methods draw outlined geometric shapes. Anti-aliased (`Aa`) variants are available for polylines and ellipses. All accept either a `Color` struct or a pre-packed `int` color for performance. ### Methods - `DrawPolyline(int[] points, Color color)` - `DrawPolylineAa(int[] points, Color color, int thickness = 1)` - `DrawTriangle(int x1, int y1, int x2, int y2, int x3, int y3, Color color)` - `DrawRectangle(int x1, int y1, int x2, int y2, Color color)` - `DrawEllipseCentered(int cx, int cy, int radiusX, int radiusY, Color color)` ### Parameters - **points**: An array of integers representing the vertices of the polyline or polygon (x1, y1, x2, y2, ...). - **color**: The color of the shape outline. - **thickness**: The thickness of the anti-aliased polyline or ellipse outline. - **x1, y1, x2, y2, x3, y3**: Coordinates defining the vertices of the triangle. - **x1, y1, x2, y2**: Coordinates of the top-left and bottom-right corners of the rectangle. - **cx, cy**: Coordinates of the center of the ellipse. - **radiusX, radiusY**: The horizontal and vertical radii of the ellipse. ``` -------------------------------- ### Convolute / Blur / Invert / AdjustBrightness — Filtering Source: https://context7.com/reneschulte/writeablebitmapex/llms.txt `Convolute` applies a convolution kernel for effects like blur and sharpen. Pre-defined kernels are provided. Additional pixel-level adjustments include brightness, contrast, gamma, grayscale, and invert. ```APIDOC ## Convolute / Blur / Invert / AdjustBrightness — Filtering `Convolute` applies a convolution kernel to produce effects like blur and sharpen. Pre-defined kernels (`KernelGaussianBlur5x5`, `KernelGaussianBlur3x3`, `KernelSharpen3x3`) are provided. Additional pixel-level adjustments include brightness, contrast, gamma, grayscale, and invert. ```csharp WriteableBitmap bmp = /* load bitmap */; // Gaussian blur with 5x5 kernel WriteableBitmap blurred = bmp.Convolute(WriteableBitmapExtensions.KernelGaussianBlur5x5); // Sharpen with 3x3 kernel WriteableBitmap sharpened = bmp.Convolute(WriteableBitmapExtensions.KernelSharpen3x3); // Custom emboss kernel int[,] emboss = { {-2,-1,0}, {-1,1,1}, {0,1,2} }; WriteableBitmap embossed = bmp.Convolute(emboss, kernelFactorSum: 1, kernelOffsetSum: 0); // Invert colors WriteableBitmap inverted = bmp.Invert(); // Convert to grayscale WriteableBitmap gray = bmp.Gray(); // Adjust brightness (+50 out of 255) WriteableBitmap bright = bmp.AdjustBrightness(50); // Adjust contrast and gamma WriteableBitmap adjusted = bmp.AdjustContrast(1.5f); WriteableBitmap gamma = bmp.AdjustGamma(2.2f); ``` ``` -------------------------------- ### Silverlight Error Handling Source: https://github.com/reneschulte/writeablebitmapex/blob/master/Source/WriteableBitmapExFillSample.Web/WriteableBitmapExFillSampleTestPage.html Handles various errors that may occur in a Silverlight application, including image and media errors, parser errors, and runtime errors. This function is essential for robust Silverlight application development. ```javascript function onSilverlightError(sender, args) { var appSource = ""; if (sender != null && sender != 0) { appSource = sender.getHost().Source; } var errorType = args.ErrorType; var iErrorCode = args.ErrorCode; if (errorType == "ImageError" || errorType == "MediaError") { return; } var errMsg = "Unhandled Error in Silverlight Application " + appSource + "\n" ; errMsg += "Code: "+ iErrorCode + " \n"; errMsg += "Category: " + errorType + " \n"; errMsg += "Message: " + args.ErrorMessage + " \n"; if (errorType == "ParserError") { errMsg += "File: " + args.xamlFile + " \n"; errMsg += "Line: " + args.lineNumber + " \n"; errMsg += "Position: " + args.charPosition + " \n"; } else if (errorType == "RuntimeError") { if (args.lineNumber != 0) { errMsg += "Line: " + args.lineNumber + " \n"; errMsg += "Position: " + args.charPosition + " \n"; } errMsg += "MethodName: " + args.methodName + " \n"; } throw new Error(errMsg); } ```