在X轴上使用带有DateAxis和DateModel的CartesianChart

时间:2017-09-26 13:20:09

标签: c# wpf xaml livecharts

我需要绘制一个包含一系列随时间推移的值的图表。值之间的时间段是不规则的(几秒钟)。为此,我使用了LiveChart.Wpf库,跟随GitHub的Date Time tutorial和日期轴示例(DateAxisExample.xamlDateAxisExample.xaml.cs)。

这是XAML:

<UserControl x:Class="Wpf.Charts.SensorChart"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             xmlns:lvc="clr-namespace:LiveCharts.Wpf;assembly=LiveCharts.Wpf"
             mc:Ignorable="d" 
             d:DesignHeight="300" d:DesignWidth="300">
    <Grid>
        <lvc:CartesianChart Series="{Binding SeriesCollection}" LegendLocation="Left">
            <lvc:CartesianChart.AxisX>
                <lvc:DateAxis Title="Time"
                              InitialDateTime="{Binding InitialDateTime}"
                              Period="{Binding Period}"
                              SelectedWindow="{Binding SelectedWindow}"
                              LabelFormatter="{Binding Formatter}">
                </lvc:DateAxis>
            </lvc:CartesianChart.AxisX>
        </lvc:CartesianChart>
    </Grid>
</UserControl>

这是我的代码背后:

using LiveCharts;
using LiveCharts.Configurations;
using LiveCharts.Helpers;
using LiveCharts.Wpf;
using System;
using System.Windows.Controls;

namespace Wpf.Charts
{
    public partial class SensorChart : UserControl
    {
        public SeriesCollection SeriesCollection { get; set; }
        public DateTime InitialDateTime { get; set; }
        public PeriodUnits Period { get; set; }
        public IAxisWindow SelectedWindow { get; set; }
        private Func<double, string> Formatter { get; set; }

        public SensorChart()
        {
            InitializeComponent();
            this.SetChartModelValues();
            this.DataContext = this;
        }

        private void SetChartModelValues()
        {
            var dayConfig = Mappers.Xy<ChartModel>()
                   .X(dayModel => (double)dayModel.DateTime.Ticks / TimeSpan.FromSeconds(1).Ticks)
                   .Y(dayModel => dayModel.Value);

            DateTime now = DateTime.Now;
            now = new DateTime(now.Year, now.Month, now.Day, now.Hour, now.Minute, now.Second);

            this.SeriesCollection = new SeriesCollection(dayConfig)
            {
                new LineSeries()
                {
                    Values = new ChartValues<ChartModel>()
                    {
                        new ChartModel(now.AddSeconds(5), 3),
                        new ChartModel(now.AddSeconds(10), 6),
                        new ChartModel(now.AddSeconds(15), 8),
                        new ChartModel(now.AddSeconds(20), 4),
                        new ChartModel(now.AddSeconds(55), 7),
                        new ChartModel(now.AddSeconds(60), 2),
                        new ChartModel(now.AddSeconds(65), 6),
                        new ChartModel(now.AddSeconds(70), 8),
                        new ChartModel(now.AddSeconds(75), 4),
                        new ChartModel(now.AddSeconds(80), 7),
                        new ChartModel(now.AddSeconds(105), 3),
                        new ChartModel(now.AddSeconds(110), 6),
                        new ChartModel(now.AddSeconds(115), 8),
                        new ChartModel(now.AddSeconds(120), 4),
                        new ChartModel(now.AddSeconds(155), 7),
                        new ChartModel(now.AddSeconds(160), 2),
                        new ChartModel(now.AddSeconds(165), 6),
                        new ChartModel(now.AddSeconds(170), 8),
                        new ChartModel(now.AddSeconds(175), 4),
                        new ChartModel(now.AddSeconds(180), 7),
                    }
                }
            };
            //foreach ()

            this.InitialDateTime = now;
            this.Period = PeriodUnits.Seconds;
            this.SelectedWindow = new DateAxisWindows.FifteenSecondsAxisWindow();
            this.Formatter = this.DateLabelFormater;
        }

        private string DateLabelFormater(double value)
        {
            DateTime dateTime = new DateTime((long)(value * TimeSpan.FromSeconds(1).Ticks));
            return dateTime.ToString("HH:mm:ss");
        }
    }

    public class ChartModel
    {
        public DateTime DateTime { get; set; }
        public double Value { get; set; }

        public ChartModel(DateTime dateTime, double value)
        {
            this.DateTime = dateTime;
            this.Value = value;
        }
    }
}

但是当我运行应用程序时,它会显示4036年的日期。你知道发生了什么吗?

1 个答案:

答案 0 :(得分:3)

如果要显示实际值,请尝试此操作:

public partial class SensorChart : UserControl
{
    public SeriesCollection SeriesCollection { get; set; }
    public DateTime InitialDateTime { get; set; }
    public Func<double, string> Formatter { get; set; }

    public SensorChart()
    {
        InitializeComponent();
        this.SetChartModelValues();
        this.DataContext = this;
    }

    private void SetChartModelValues()
    {
        var dayConfig = Mappers.Xy<ChartModel>()
                           .X(dayModel => dayModel.DateTime.Ticks)
                           .Y(dayModel => dayModel.Value);


        DateTime now = DateTime.Now;

        this.SeriesCollection = new SeriesCollection(dayConfig)
        {
            new LineSeries()
            {
                Values = new ChartValues<ChartModel>()
                {
                    new ChartModel(now.AddSeconds(5), 3),
                    new ChartModel(now.AddSeconds(10), 6),
                    new ChartModel(now.AddSeconds(15), 8),
                    new ChartModel(now.AddSeconds(20), 4),
                    new ChartModel(now.AddSeconds(55), 7),
                    new ChartModel(now.AddSeconds(60), 2),
                    new ChartModel(now.AddSeconds(65), 6),
                    new ChartModel(now.AddSeconds(70), 8),
                    new ChartModel(now.AddSeconds(75), 4),
                    new ChartModel(now.AddSeconds(80), 7),
                    new ChartModel(now.AddSeconds(105), 3),
                    new ChartModel(now.AddSeconds(110), 6),
                    new ChartModel(now.AddSeconds(115), 8),
                    new ChartModel(now.AddSeconds(120), 4),
                    new ChartModel(now.AddSeconds(155), 7),
                    new ChartModel(now.AddSeconds(160), 2),
                    new ChartModel(now.AddSeconds(165), 6),
                    new ChartModel(now.AddSeconds(170), 8),
                    new ChartModel(now.AddSeconds(175), 4),
                    new ChartModel(now.AddSeconds(180), 7),
                }
            }
        };

        this.InitialDateTime = now;
        this.Formatter = value => new DateTime((long)value).ToString("yyyy-MM:dd HH:mm:ss");
    }
}

<强> XAML:

<lvc:CartesianChart Series="{Binding SeriesCollection}" LegendLocation="Left">
    <lvc:CartesianChart.AxisX>
        <lvc:Axis LabelFormatter="{Binding Formatter}"
                  MinValue="{Binding InitialDateTime.Ticks}">
        </lvc:Axis>
    </lvc:CartesianChart.AxisX>
</lvc:CartesianChart>

enter image description here