gpt4 book ai didi

c# - 在现代 UI (Metro) 图表中以编程方式 (MVVM) 添加 ChartSeries

转载 作者:行者123 更新时间:2023-11-30 22:02:14 31 4
gpt4 key购买 nike

我一直在为我的项目寻找一个好看的图表可视化解决方案,我终于找到了它 ( https://modernuicharts.codeplex.com )。我也把这个问题发到论坛上了,但是没有人回复...

我一直在研究图表,我真的很喜欢它们。非常光滑漂亮。有 1 件事我需要更多信息,那就是我如何在运行时添加 ChartSeries。

编辑:我设法在运行时添加栏,但有一些我似乎无法弄清楚的错误。让我们从一张图片开始:

Image

正如您在图像中看到的,轴上的标题是正确的,并且在我缩放窗口时缩放。这里的问题是酒吧。条形似乎具有固定宽度,不想适合屏幕。我这样做的方式如下:

在 XAML 中,我这样放置控件:

<chart:StackedColumnChart ChartTitle="Total"
ChartSubTitle="(800)"
Series="{Binding Bars}">
</chart:StackedColumnChart>

在我后面的代码中,我添加了这样的 Bars:

using System;
using System.Collections.Generic;
using De.TorstenMandelkow.MetroChart;
using System.Collections.ObjectModel;

namespace AutoShop
{
class OccupationChartGroupViewModel
{
public OccupationChartGroupViewModel()
{
List<Tuple<string, int, double>> reqProdHoursPerWeek = DbServiceSegmentRequirement.GetProdSegReq();
List<Tuple<string, int, double>> reqPlanHoursPerWeek = DbServiceSegmentRequirement.GetPlanSegReq();
List<Tuple<string, int, double>> reqRepairHoursPerWeek = DbServiceSegmentRequirement.GetRepairSegReq();

List<Tuple<string, int, double>> reqHoursPerWeek = new List<Tuple<string, int, double>>();
reqHoursPerWeek.AddRange(reqProdHoursPerWeek);
reqHoursPerWeek.AddRange(reqPlanHoursPerWeek);
reqHoursPerWeek.AddRange(reqRepairHoursPerWeek);

reqHoursPerWeek.Sort();

switch (reqHoursPerWeek[0].Item2.ToString())
{
case "0":
if (reqHoursPerWeek[1].Item2.ToString() != "1")
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 1, 0.0));
else
if (reqHoursPerWeek[1].Item1 != reqHoursPerWeek[0].Item1)
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 1, 0.0));
break;

case "1":
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 0, 0.0));
if (reqHoursPerWeek[1].Item2.ToString() != "2")
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 2, 0.0));
else
if (reqHoursPerWeek[1].Item1 != reqHoursPerWeek[0].Item1)
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 2, 0.0));
break;

case "2":
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 0, 0.0));
reqHoursPerWeek.Add(new Tuple<string, int, double>(reqHoursPerWeek[0].Item1, 1, 0.0));
break;

default: break;
}

reqHoursPerWeek.Sort();

Bars = new ObservableCollection<De.TorstenMandelkow.MetroChart.ChartSeries>();

ObservableCollection<TestClass> blocks = new ObservableCollection<TestClass>();

foreach (Tuple<string, int, double> reqHours in reqHoursPerWeek)
{
string group = reqHours.Item2.ToString() == "2" ? "Order1" : reqHours.Item2.ToString() == "1" ? "Order2" : reqHours.Item2.ToString() == "0" ? "Order3" : "Unknown";

blocks.Add(new TestClass() { Category = group, Number = reqHours.Item3 });

if (reqHoursPerWeek.IndexOf(reqHours) + 1 < reqHoursPerWeek.Count)
{
if (reqHours.Item1 != reqHoursPerWeek[reqHoursPerWeek.IndexOf(reqHours) + 1].Item1)
{
ChartSeries chartSerie = new ChartSeries();
chartSerie.SeriesTitle = reqHours.Item1;
chartSerie.DisplayMember = "Category";
chartSerie.ValueMember = "Number";
chartSerie.ItemsSource = blocks;
Bars.Add(chartSerie);

blocks = new ObservableCollection<TestClass>();
}
}
else
{
ChartSeries chartSerie = new ChartSeries();
chartSerie.SeriesTitle = reqHours.Item1;
chartSerie.DisplayMember = "Category";
chartSerie.ValueMember = "Number";
chartSerie.ItemsSource = blocks;
Bars.Add(chartSerie);
}
}
}

public ObservableCollection<ChartSeries> Bars { get; private set; }
}

// class which represent a data point in the chart
public class TestClass
{
public string Category { get; set; }

public double Number { get; set; }
}
}

最后,我在设计时在 XAML 查看器中遇到的错误是:

**NullReferenceException: Object reference not set to an instance of an object.**

**Stacktrace**
at De.TorstenMandelkow.MetroChart.ChartBase.UpdateDataContextOfSeries()
at De.TorstenMandelkow.MetroChart.ChartBase.InternalDataContextChanged()
at De.TorstenMandelkow.MetroChart.ChartBase.DataContextWatcher_Changed(DependencyObject sender, DependencyPropertyChangedEventArgs args)
at System.Windows.DependencyObject.OnPropertyChanged(DependencyPropertyChangedEventArgs e)
at System.Windows.FrameworkElement.OnPropertyChanged(DependencyPropertyChangedEventArgs e)
at System.Windows.DependencyObject.NotifyPropertyChange(DependencyPropertyChangedEventArgs args)
at System.Windows.DependencyObject.UpdateEffectiveValue(EntryIndex entryIndex, DependencyProperty dp, PropertyMetadata metadata, EffectiveValueEntry oldEntry, EffectiveValueEntry& newEntry, Boolean coerceWithDeferredReference, Boolean coerceWithCurrentValue, OperationType operationType)
at System.Windows.DependencyObject.InvalidateProperty(DependencyProperty dp, Boolean preserveCurrentValue)
at System.Windows.Data.BindingExpressionBase.Invalidate(Boolean isASubPropertyChange)
at System.Windows.Data.BindingExpression.TransferValue(Object newValue, Boolean isASubPropertyChange)
at System.Windows.Data.BindingExpression.Activate(Object item)
at System.Windows.Data.BindingExpression.AttachToContext(AttachAttempt attempt)
at System.Windows.Data.BindingExpression.MS.Internal.Data.IDataBindEngineClient.AttachToContext(Boolean lastChance)
at MS.Internal.Data.DataBindEngine.Task.Run(Boolean lastChance)
at MS.Internal.Data.DataBindEngine.Run(Object arg)
at MS.Internal.Data.DataBindEngine.OnLayoutUpdated(Object sender, EventArgs e)
at System.Windows.ContextLayoutManager.fireLayoutUpdateEvent()
at System.Windows.ContextLayoutManager.UpdateLayout()
at System.Windows.UIElement.UpdateLayout()

**InnerException: None**

最佳答案

您使用的是 Series 而不是 SeriesSource 属性(我尝试使用 SeriesSource 但由于某种原因图表显示为空)。无论如何,错误实际上发生了,因为在 MVVM 调用 Series 绑定(bind)的 get 方法之前调用了上述方法,因此在 ChartBase.cs 的以下定义中将 Series 设置为 null。我希望你的解决方案中有项目,否则打开他们提供的代码,更新代码,编译并引用生成的 dll。

    private void UpdateDataContextOfSeries()
{
onApplyTemplateFinished = false;

//ADDED CODE STARTS
if(this.Series != null)
{
//ADDED CODE ENDS
foreach (var newItem in this.Series)
{
if (newItem is FrameworkElement)
{
(newItem as FrameworkElement).DataContext = this.DataContext;
}
}
onApplyTemplateFinished = true;
UpdateSeries();
//ADDED CODE STARTS
}
//ADDED CODE ENDS
}

只需要在运行循环和应用更新之前检查系列是否为空。一旦获取系列,也会调用此方法。

关于c# - 在现代 UI (Metro) 图表中以编程方式 (MVVM) 添加 ChartSeries,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27036234/

31 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com