Question

I'm trying to draw a waveform like the ones used on soundcloud.com in my WPF application I'm doing this by drawing multiple vertical lines

What I want is that all the lines have the same color transition (so horizontally all pixels have the same color) Because not all lines have the same length each line has a different color at the end of the line.

The LinearGradientBrush has a lot of constructors, and the one that is most suited to my needs seems to be LinearGradientBrush(GradientStopCollection, Point, Point).

Msdn article on the LinearGradientContstructor

With these points I seem to be able to set my GradientStops outside of the drawn line

The problem I have is I don't know how to use the points.

var r = new GradientStopCollection();
r.Add(new GradientStop(Colors.Black, 0));
r.Add(new GradientStop(Colors.Red, 0.5));
r.Add(new GradientStop(Colors.Black, 1));

//this would be my main gradient background for all my lines (100%)
for (int i = 0; i < 25; i++)
{
  var line = new Line { X1 = i, X2 = i, Y1 = 0, Y2 = 200, Stroke = new LinearGradientBrush(r), StrokeThickness = 1 };
  WaveformCanvas.Children.Add(line);
}
//this would be an actual value of the waveform, points 0,0 and 1,1 seem to indicate that the gradientstops are exactly on the y1/y2
for (int i = 25; i < 50; i++)
{
  var line = new Line { X1 = i, X2 = i, Y1 = 50, Y2 = 150, Stroke = new LinearGradientBrush(r, new Point(0, 0), new Point(1, 1)), StrokeThickness = 1 };
  WaveformCanvas.Children.Add(line);
}
//these point values seem to be about correct for the current line length
//I came to these values by trial and error
for (int i = 50; i < 75; i++)
{
  var line = new Line { X1 = i, X2 = i, Y1 = 50, Y2 = 150, Stroke = new LinearGradientBrush(r, new Point(-0.5, -0.5), new Point(1.5, 1.5)), StrokeThickness = 1 };
  WaveformCanvas.Children.Add(line);
}

I'm puzzled by why the points are 2d coordinates because the gradient with points -0.5,-0.5 does not seem to have an different angle than the drawn line

So I need to understand how to place the points relative to my "main 100% gradient"

Or maybe an easier way all together is to draw the lines in a solid colour and afterwards use some kind of colour select to replace the black pixels with a rectangular gradient as the background.

Was it helpful?

Solution

Take a look at the GradientBrush.MappingMode Property.

LinearGradientBrush(GradientStopCollection, Point, Point) will initialize the brush with BrushMappingMode.RelativeToBoundingBox but I think you need BrushMappingMode.Absolute. There is no constructor overload for this. So you have to set this property by your own.

LinearGradientBrush brush = new LinearGradientBrush(r, new Point(0, 0), new Point(0, 200));
brush.MappingMode = BrushMappingMode.Absolute;
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top