WriteableBitmap
Written by Administrator   
Thursday, 31 December 2009
Article Index
WriteableBitmap
A practical example
Extending WriteableBitmap

Banner

Extending WriteableBitmap

The backbuffer uses the pixel format you sepecified when creating the WriteableBitmap and there is a BackBufferStride property that you can use to create a suitable storage mapping function.

It is easy enough to add some methods to set and get pixels in a particular case by way of two new extension methods defined in a static class created just to host the extension methods:

 public static class bitmapextensions
{

The setPixel method first checks that the x and y co-ordinates are in the correct range and that the format is Brga32 (you can extend the method to deal with other formats):

 public static void setPixel(
this WriteableBitmap wbm,
int x, int y, Color c)
{
if (y > wbm.PixelHeight - 1 ||
x > wbm.PixelWidth - 1) return;
if (y < 0 || x < 0) return;
if (!wbm.Format.Equals(
PixelFormats.Bgra32))return;

It then gets the backbuffer details:

 wbm.Lock();
IntPtr buff = wbm.BackBuffer;
int Stride = wbm.BackBufferStride;

Then it computes the storage mapping function to access the pixel at that x,y location and stores the specified colour split into the four bytes corresponding to the pixel format:

 unsafe
{
byte* pbuff = (byte*)buff.ToPointer();
int loc=y *Stride  + x*4;
pbuff[ loc]=c.B;
pbuff[loc+1]=c.G;
pbuff[loc+2]=c.R;
pbuff[loc+3]=c.A;
}

Finally we mark the pixel dirty and unlock the WriteableBitmap:

 wbm.AddDirtyRect(
new Int32Rect(x,y,1,1));
wbm.Unlock();
}

The getPixel method is very similar, only it assembles and returns a Color struct:

public static Color getPixel(
this WriteableBitmap wbm, int x, int y)
{
if (y > wbm.PixelHeight - 1 ||
x > wbm.PixelWidth - 1)
return Color.FromArgb(0, 0, 0, 0);
if (y < 0 || x < 0)
return Color.FromArgb(0, 0, 0, 0);
if (!wbm.Format.Equals(
PixelFormats.Bgra32)) 
return Color.FromArgb(0, 0, 0, 0);;
IntPtr buff = wbm.BackBuffer;
int Stride = wbm.BackBufferStride;
Color c;
unsafe
{
byte* pbuff = (byte*)buff.ToPointer();
int loc = y * Stride + x * 4;
c=Color.FromArgb(pbuff[loc+3],
pbuff[loc+2],pbuff[loc+1],
pbuff[loc]);
}
return c;
}

Notice that as we are only accessing the bits and not changing them there is no need to lock or mark an area as dirty.

These two extension methods are easy to use but you might want to think about using more direct methods if you are going to manipulate a lot of pixels. Direct access via the Pixel property, and assigning pre-computed integer colour values, is always going to be faster than using general methods and objects.

With these extension methods defined we can now give an example of accessing pixels:

  wbmap.setPixel(5,10 , Colors.Red);
Color c= wbmap.getPixel(5, 10);

Finally, as an example of a dynamic image, the following plots a range of colours which depend on the position of the pixel according to a simple formula:

private void button1_Click(
object sender, RoutedEventArgs e)
{
WriteableBitmap wbmap =
new WriteableBitmap(256, 256,
300, 300, PixelFormats.Bgra32, null);
for (int x = 0; x < 256; x++)
{
for (int y = 0; y < 256; y++)
{
wbmap.setPixel(
x,y,Color.FromArgb(255,
(byte) (x*x+y),
(byte) (y*y+x),(byte)(x+y)));
}
}
image1.Source = wbmap;
}

pattern

 

Banner


WPF .NET Core - Creating Objects With XAML

If you've never encountered WPF (Windows Presentation Foundation) you are missing a versatile tool. This article is part of a series devoted to it. XAML can be confusing - especially if you think it i [ ... ]



Drawing Bitmaps – DrawingImage and DrawingVisual

 

WPF provides multiple ways to convert vector drawings to bitmaps. Find out how DrawingImage and DrawingVisual work and when to use which. On the way we look at how to create 2D vector drawings.



ISupportInitialize and XAML

For a class to be instantiated by XAML it has to have a parameter-less constructor. This means that properties that might be essential to creating the instance can be initialized in any order and this [ ... ]



Custom Bitmap Effects - HLSL

In the article Custom Bitmap Effects - Getting started we discovered how to work with HLSL in WPF. Now we are in a position to write more sophisticated shaders and  this means learning some more  [ ... ]



Custom Shape

Creating a custom Shape isn't difficult but it does have some hidden gotchas. We take a look at how best to do the job.


Other Articles

<ASIN:0672329859>

<ASIN:0735623945>

<ASIN:0979372518>

<ASIN:1430224819>




Last Updated ( Friday, 19 March 2010 )