patterncsharpMinor
Line rendering optimization
Viewed 0 times
optimizationrenderingline
Problem
I spent the past hour trying to optimize a block of code I wrote that renders a simple coloured line directly to a backbuffer.
I've compared it with one of the
Note, the
Running this as it is currently, will get me, on my machine, roughly 300MPixels per second, while the "default"
Is there any way I can optimize this further?
I've compared it with one of the
DrawLine method implementations of the WriteableBitmapEx project, and found that my algorithm isn't quite as fast (unless I use Parallel).public static unsafe void DrawLineVector(this IntPtr target, Line2D line, int colour, int width, int height)
{
var buf = (int*) target;
var start = line.Start;
var lineVector = line.Stop - start;
var steps = (int)lineVector.Magnitude();
var uX = lineVector.X / steps;
var uY = lineVector.Y / steps;
var col = colour;
Parallel.For(0, steps, i =>
//for (var i = 0; i != steps; ++i)
{
var x = start.X + uX * i;
var y = start.Y + uY * i;
if (x > -1 && y > -1 && x < width && y < height)
buf[(int)y * width + (int)x] = col;
//x += uX;
//y += uY;
}
);
}Note, the
Line2D object is basically just a container for two VectorD objects (which are my own implementation of vectors).Running this as it is currently, will get me, on my machine, roughly 300MPixels per second, while the "default"
DrawLine method from WriteableBitmapEx gets me around 170MPixels per second. If I use the 'serial' version of this (i.e. not use Parallel), I get around 100MPixels per second.Is there any way I can optimize this further?
Solution
Because you're comparing your performance with that of the WriteableBitmapEx project, you might like to compare your algorithm with theirs, which is here on github: WriteableBitmapShapeExtensions.cs
You say your performance isn't much slower than theirs (100 versus 170 MPixels/second).
A difference between yours and there's might be that yours is using
Their code is much longer (more lines of code) than yours, but their inner loop is something like this:
Note:
You say your performance isn't much slower than theirs (100 versus 170 MPixels/second).
A difference between yours and there's might be that yours is using
float or double arithmetic, whereas theirs is using int arithmetic.Their code is much longer (more lines of code) than yours, but their inner loop is something like this:
for (int x = x1; x > PRECISION_SHIFT;
if (y != previousY)
{
previousY = y;
index += k;
}
else
{
++index;
}
}Note:
- Only
int(notdouble)
- Few branches
- Every write is to a significant pixels (in your algorithm if you write a line at 45 degrees then you do 1.414 writes per pixels).
Code Snippets
for (int x = x1; x <= x2; ++x)
{
pixels[index] = color;
ys += incy;
y = ys >> PRECISION_SHIFT;
if (y != previousY)
{
previousY = y;
index += k;
}
else
{
++index;
}
}Context
StackExchange Code Review Q#44474, answer score: 5
Revisions (0)
No revisions yet.