我们正在尝试从基于 Silverlight 的图表控件转向更多无插件控件。我们喜欢 HighCharts,现在正在测试将其实现到我们现有的代码库中。我们发现 DotNet.HighCharts 可能是快速创建图表而无需解析所有 javascript 的竞争者。
我的问题是,当图表包含在数据中时,您如何传递要在图表中使用的数据DataTable
?跟随这里的答案,我已经看到 Linq 可能是要走的路。但是,我很难让代码真正构建。DotNet.HighCharts 的文档没有显示任何提取非静态数据的示例,所以那里没有运气。到目前为止,这是我的代码片段:
Dim da3 As New SqlDataAdapter(sql3, conn3)
da3.Fill(dt3)
da3.Dispose()
conn3.Close()
Dim chart3 As Highcharts = New Highcharts("chart").InitChart(New Chart() With { _
.PlotShadow = False _
}).SetTitle(New Title() With { _
.Text = "Browser market shares at a specific website, 2010" _
}).SetTooltip(New Tooltip() With { _
.Formatter = "function() { return '<b>'+ this.point.name +'</b>: '+ this.percentage +' %'; }" _
}).SetPlotOptions(New PlotOptions() With { _
.Column = New PlotOptionsColumn With { _
.AllowPointSelect = True, _
.Cursor = Cursors.Pointer, _
.DataLabels = New PlotOptionsColumnDataLabels() With { _
.Color = ColorTranslator.FromHtml("#000000"), _
.Formatter = "function() { return '<b>'+ this.point.name +'</b>: '+ this.percentage +' %'; }" _
} _
} _
}).SetSeries(New Series() With { _
.Type = ChartTypes.Column, _
.Name = "Browser share", _
.Data = New Helpers.Data(dt3.Select(Function(x) New Options.Point() With {.X = x.periodyear, .Y = x.rate}).ToArray()) _
})
ltrChart3.Text = chart3.ToHtmlString()
我正在导入以下内容:
Imports DotNet.Highcharts
Imports DotNet.Highcharts.Options
Imports System.Data
Imports System.Data.SqlClient
Imports DotNet.Highcharts.Enums
Imports System.Drawing
Imports System.Collections.Generic
Imports System.Linq
我得到的错误.Data = New Helpers.Data(dt3.Select(Function(x) New Options.Point() With {.X = x.periodyear, .Y = x.rate}).ToArray()) _
在线。我得到Lambda expression cannot be converted to 'String' because 'String' is not a delegate type
了我的错误Function....rate}
。
编辑: 第一次尝试修改现有代码
Dim chart1 As Highcharts = New DotNet.Highcharts.Highcharts("test")
Dim series As Series = New Series()
series.Name = "CO Rates"
For i As Integer = 0 To dt.Rows.Count - 1
series.Data = New Helpers.Data(New Object() {dt.Rows(i)("periodyear"), dt.Rows(i)("rate")})
Next
chart1.SetSeries(series).InitChart(New Chart() With { _
.Type = ChartTypes.Column})
这只会产生 2 列,第一列位于 x 位置 0,其值为 2011,另一列位于 x 位置 1,其值为 8.3。这非常奇怪,因为在我看来它正在获取 dataTable 中的最后一个点,然后将其 {x, y} 值 ({2011, 8.3}) 变成 2 个不同的点,其中 x 和 y 值都是 y {0, x} 和 {1, y} 之类的值。我需要得到:
- 从数据表中获取的具有 {periodyear, rate} 的单个系列。
- 将来我想为每个位置创建一个序列,其 {periodyear, rate} 取自数据表。
编辑 2:
好的,我让它将结果转换为数据字典,我让图表显示所有点。现在唯一的问题是将 转换dt.Rows(i)("periodyear")
为 DateTime 值。这是到目前为止的代码(在 PaseExact 方法上失败):
Dim series As Series = New Series()
series.Name = "CO Rates"
Dim xDate As DateTime
Dim data As New Dictionary(Of DateTime, Decimal)
For i As Integer = 0 To dt.Rows.Count - 1
xDate = DateTime.ParseExact(dt.Rows(i)("periodyear").ToString, "YYYY", Globalization.CultureInfo.InvariantCulture)
data.Add(xDate, dt.Rows(i)("rate"))
Next
Dim chartData As Object(,) = New Object(data.Count - 1, 1) {}
Dim x As Integer = 0
For Each pair As KeyValuePair(Of DateTime, Decimal) In data
chartData.SetValue(pair.Key, x, 0)
chartData.SetValue(pair.Value, x, 1)
x += 1
Next
Dim chart1 As Highcharts = New Highcharts("chart1").InitChart(New Chart() With { _
.Type = ChartTypes.Column _
}).SetTitle(New Title() With { _
.Text = "Chart 1" _
}).SetXAxis(New XAxis() With { _
.Type = AxisTypes.Linear _
}).SetSeries(New Series() With { _
.Data = New Helpers.Data(chartData) _
})
如果我将其更改为字符串值(例如 1980),然后将 x 轴的 AxisTypes 更改为线性,我会显示数据。它只是以某种方式关闭 - 1980 看起来像 1,980。婴儿步...
编辑 N: 这是最终的工作解决方案。这似乎可以使用一些清理。例如,我不确定是否需要创建一个字典来放入我的 X/Y 值,然后遍历字典以将数据添加到我的 chartData 对象。这似乎是双重工作。
Dim stfipsList = (From r In dt.AsEnumerable() Select r("stfips")).Distinct().ToList()
Dim SeriesList As New List(Of Series)(stfipsList.Count)
Dim seriesItem(stfipsList.Count) As Series
Dim xDate As DateTime
Dim fakeDate As String
Dim sX As Integer
sX = 1
For Each state In stfipsList
Dim data As New Dictionary(Of DateTime, Decimal)
Dim stateVal As String = state.ToString
Dim recCount As Integer = dt.Rows.Count - 1
For i As Integer = 0 To recCount
If dt.Rows(i)("stfips").ToString = stateVal Then
fakeDate = "1/1/" + dt.Rows(i)("periodyear").ToString
xDate = DateTime.Parse(fakeDate)
data.Add(xDate.Date, dt.Rows(i)("unemprate"))
End If
Next
Dim chartData As Object(,) = New Object(data.Count - 1, 1) {}
Dim x As Integer = 0
For Each pair As KeyValuePair(Of DateTime, Decimal) In data
chartData.SetValue(pair.Key, x, 0)
chartData.SetValue(pair.Value, x, 1)
x += 1
Next
seriesItem(sX) = New Series With {
.Name = state.ToString, _
.Data = New Helpers.Data(chartData)
}
SeriesList.Add(seriesItem(sX))
sX = sX + 1
Next
Dim chart1 As Highcharts = New Highcharts("chart1").InitChart(New Chart() With { _
.Type = ChartTypes.Line _
}).SetTitle(New Title() With { _
.Text = "Annual Unemployment Rate" _
}).SetTooltip(New Tooltip() With { _
.Formatter = "function() { return '<b>'+ this.series.name + ': ' + Highcharts.dateFormat('%Y', this.x) +'</b>: '+ this.y +' %'; }" _
}).SetXAxis(New XAxis() With { _
.Type = AxisTypes.Datetime _
}).SetYAxis(New YAxis() With { _
.Min = 0, _
.Title = New YAxisTitle() With { _
.Text = "Unemployment Rate", _
.Align = AxisTitleAligns.High _
} _
}).SetSeries(SeriesList.[Select](Function(s) New Series() With { _
.Name = s.Name, _
.Data = s.Data _
}).ToArray())
ltrChart1.Text = chart1.ToHtmlString()