Racing Bars
Code behind
using System;
using System.Linq;
using System.Threading.Tasks;
using Eto.Forms;
using LiveChartsCore.Defaults;
using LiveChartsCore.Kernel;
using LiveChartsCore.SkiaSharpView;
using LiveChartsCore.SkiaSharpView.Eto;
using LiveChartsCore.SkiaSharpView.Painting;
using LiveChartsCore.Themes;
using SkiaSharp;
namespace EtoFormsSample.Bars.Race;
public class View : Panel
{
private readonly Random _r = new();
private readonly RowSeries<PilotInfo> _series;
public View()
{
_series = new RowSeries<PilotInfo>
{
Values = Fetch(),
DataLabelsTranslate = new LiveChartsCore.Drawing.LvcPoint(-1, 0),
DataLabelsPaint = new SolidColorPaint(SKColors.Black),
DataLabelsPosition = LiveChartsCore.Measure.DataLabelsPosition.End,
DataLabelsFormatter = point => ((PilotInfo)point.Context.DataSource).Name,
};
_series.PointMeasured += OnPointMeasured;
var yAxis = new Axis { IsVisible = false };
var xAxis = new Axis { IsVisible = false };
var cartesianChart = new CartesianChart
{
Series = [_series],
YAxes = [yAxis],
TooltipPosition = LiveChartsCore.Measure.TooltipPosition.Hidden
};
Content = cartesianChart;
_ = StartRace();
UnLoad += (o, e) => Visible = false;
}
private async Task StartRace()
{
await Task.Delay(1000);
// to keep this sample simple, we run the next infinite loop
// in a real application you should stop the loop/task when the view is disposed
while (true)
{
// do a random change to the data
foreach (var item in _series.Values)
item.Value += _r.Next(0, 100);
_series.Values = [.. _series.Values.OrderBy(x => x.Value)];
await Task.Delay(100);
}
}
private void OnPointMeasured(ChartPoint point)
{
// assign the pilot color to the bar
var pilot = (PilotInfo)point.Context.DataSource;
if (point.Context.Visual is null || pilot is null) return;
point.Context.Visual.Fill = pilot.Paint;
}
private static PilotInfo[] Fetch()
{
var paints = Enumerable.Range(0, 7)
.Select(i => new SolidColorPaint(ColorPalletes.MaterialDesign500[i].AsSKColor()))
.ToArray();
return [
new PilotInfo("Tsunoda", 500, paints[0]),
new PilotInfo("Sainz", 450, paints[1]),
new PilotInfo("Riccardo", 520, paints[2]),
new PilotInfo("Bottas", 550, paints[3]),
new PilotInfo("Perez", 660, paints[4]),
new PilotInfo("Verstapen", 920, paints[5]),
new PilotInfo("Hamilton", 1000, paints[6])
];
}
public class PilotInfo : ObservableValue
{
public PilotInfo(string name, int value, SolidColorPaint paint)
{
Name = name;
Paint = paint;
Value = value;
}
public string Name { get; set; }
public SolidColorPaint Paint { get; set; }
}
}
Articles you might also find useful: