使用HighCharts和DotNet.HighCharts来“播放”多个系列 [英] Using HighCharts and DotNet.HighCharts to "Play" Multiple Series
问题描述
我有一套使用VB.NET和DotNet.HighCharts创建的系列:
Dim SeriesList4As新列表(系列)(stfipsList4.Count)
我想要发生的事情类似于 http://jsfiddle.net/8M2fF/ 。 / p>
创建上述示例的VB代码如下:
Dim stfipsList4 =(From r In dt4.AsEnumerable()Select r(areaname))。Distinct()。ToList()
Dim SeriesList4 As New List(Of Series)(stfipsList4.Count)
Dim seriesItem4(stfipsList4.Count)As Series
Dim xDate4 As DateTime
Dim fakeDate4 As String
Dim sX4 As Integer
sX4 = 1
For Each state在stfipsList4
中Dim data As New Dictionary(Of DateTime,Decimal)
D im stateVal As String = state.ToString
Dim recCount As Integer = dt4.Rows.Count - 1
Dim seriesPointCount As Integer = dt4.Compute(Count(population),areaname ='+ stateVal +')
Dim xData As As Object(,)= New Object(seriesPointCount - 1,1){}
Dim x As Integer = 0
For i As Integer = 0 To recCount
如果dt4.Rows(i)(areaname)。ToString = stateVal Then
fakeDate4 =1/1 /+ dt4.Rows(i)(periodyear)。ToString
xDate4 = DateTime.Parse(fakeDate4)
chartData.SetValue(xDate4.Date,x,0)
chartData.SetValue(dt4.Rows(i)(population),x,1)
x + = 1
结束如果
下一个
seriesItem4(sX4)=新系列With {
.Name = state.ToString, _
.Data =新助手.Data(chartData)
}
SeriesList4.Add(seriesItem4(sX4))
sX4 = sX4 + 1
Next
Dim iterateData As String = JsonSerializer.Serialize(seriesItem4(1))
Dim chart4 As Highcharts = New Highcharts(chart4)。SetOptions(New Helpers.GlobalOptions()With {_
。[Global] = New [Global]()With {_
.UseUTC = False _
} _
})。InitChart(New Chart()With {_
.DefaultSeriesType = ChartTypes.Column,_
.MarginRight = 10,_
.Events = New ChartEvents()With {_
.Load =ChartEventsLoad_
} ($ _
.Text =Population_
})。SetTooltip(New Tooltip()With {_
.Formatter =function(){r eturn'< b>'+ this.series.name +'< br />'+ Highcharts.dateFormat('%Y',this.x)+'< / b>'+ Highcharts.numberFormat this.y,0,','); SetXAxis(New XAxis()With {_
.Type = AxisTypes.Datetime,_
.TickPixelInterval = 150 _
}}。SetYAxis(New YAxis()With {_
.Min = 0,_
.Title = New YAxisTitle()With {_
.Text =Population,_
.Align = AxisTitleAligns (New Series()with {_
.Data = New Helpers.Data(New Object(){})_
}。 )_
.SetOptions(New Helpers.GlobalOptions()With {_
.Colors = palette_colors _
})_
.AddJavascripVariable(iterated,iterateData.ToString)_
.AddJavascripFunction(ChartEventsLoad,//设置每秒更新图表& vbCr& vbLf& _
var result = iterated.data;& vbCr& vbLf& _
var counter = 0; &安培; vbCr& vbLf& _
var series = this.series [0]; &安培; vbCr& vbLf& _
var loopseries = function(){& vbCr& vbLf& _
if(counter< = result.length){& vbCr& vbLf& _
var p = String(result [counter]); &安培; vbCr& vbLf& _
var splitp = p.split(,); &安培; vbCr& vbLf& _
var x = Number(splitp [0]); &安培; vbCr& vbLf& _
var y = Number(splitp [1]); &安培; vbCr& vbLf& _
series.addPoint([x,y],true,series.points.length> 10,true); &安培; vbCr& vbLf& _
counter ++; &安培; vbCr& vbLf& _
} else {& vbCr& vbLf& _
clearInterval(loopseries); &安培; vbCr& vbLf& _
}}; &安培; vbCr& vbLf& _
setInterval(loopseries,300);)
ltrChart4.Text = chart4.ToHtmlString()
这仅适用于单个系列。我想通过一个列表(系列)。
需要参与的事情:
创建n个系列
为每个系列添加点数
为每个系列命名
我可以处理这些物品,它只是通过我无法完成的主要系列清单。
编辑:
似乎有一些混淆我在问什么。我可以通过DotNet.HighCharts API将N个系列传递给HighCharts。我目前无法做到的是将这一系列相同的系列文件传递给javascript函数以循环播放该系列文件。请参阅:
.AddJavascripVariable(iterated,iterateData.ToString)_
.AddJavascripFunction(ChartEventsLoad, //设置每秒更新图表& vbCr& vbLf& _
var result = iterated.data;& vbCr& vbLf& _
var计数器= 0;& vbCr& vbLf& _
var series = this.series [0];& vbCr& vbLf& _
var loopseries = function() {& vbCr& vbLf& _
if(counter< = result.length){& vbCr& vbLf& _
var p = String(result [counter ]);& vbCr& vbLf& _
var splitp = p.split(,);& vbCr& vbLf& _
var x = Number(splitp [0]);& vbCr &安培; vbLf& _
var y = Number(splitp [1]); &安培; vbCr& vbLf& _
series.addPoint([x,y],true,series.points.length> 10,true); &安培; vbCr& vbLf& _
counter ++; &安培; vbCr& vbLf& _
} else {& vbCr& vbLf& _
clearInterval(loopseries); &安培; vbCr& vbLf& _
}}; &安培; vbCr& vbLf& _
setInterval(loopseries,300);)
.AddJavaScriptVariable需要一个字符串并在内部代码给我无效的对象引用。
我实际上使用DotNet.Highcharts来创建一个图表,未定义数量的系列。为此,我使用linq查询需要添加到图表的数据。我使用对象[]的列表来创建单个点,然后我将该列表添加到系列列表中。我遍历循环的次数达到了我需要的所有系列。然后为SetSeries分配系列列表中包含的内容。代码是用C#编写的,但我相信你可以将它改为VB.NET。这是我用来创建图表的整个ActionResult:
public ActionResult CombinerBarToday(DateTime?utcStartingDate = null,
DateTime?utcEndingDate = null)
{
//获取指定日期时间的生成读数
var firstQ = from db.PowerCombinerHistorys
在db.PowerCombiners中加入u s.combiner_id等于u.id
其中s.recordTime> = utcStartingDate
其中s.recordTime< = utcEndingDate
选择新的
{
CombinerID = u。名称,
Current = s.current,
RecordTime = s.recordTime,
电压= s.voltage,
Watts =(s.current * s.voltage)
};
//获取包含在QUERY中的组合列表
var secondQ =(从firstQ
中选择新的
{
Combiner = s .CombinerID
})。Distinct();
/ *此系列清单将用于动态地添加许多系列
*至所需的高级版本,而无需创建每个系列的个人资料* /
列出<系列> allSeries =新列表< Series>();
TimeZoneInfo easternZone = TimeZoneInfo.FindSystemTimeZoneById(东部标准时间);
//通过每个组合器创建系列并创建系列
foreach(secondQ中的var distinctCombiner)
{
var combinerDetail = from db2.PowerCombinerHistorys
加入你在db2.PowerCombiners上的s.combiner_id等于u.id
其中u.name == distinctCombiner.Combiner
其中s.recordTime> = utcStartingDate
其中s.recordTime< = utcEndingDate
选择新的
{
CombinerID = u.name,
Current = s.current,
RecordTime = s.recordTime,
电压= s。电压,
Watts =(sCurrent * s.voltage)/ 1000d
};
var results = new List< object []>();
foreach(combinerCombiner in combinerDetail)
{
results.Add(new object [] {
TimeZoneInfo.ConvertTimeFromUtc(detailCombiner.RecordTime,easternZone),
detailCombiner.Watts});
allSeries.Add(新系列
{
名称= distinctCombiner.Combiner,
// Data = new Data(myData)
Data = new Data(results.ToArray())
});
}
Highcharts chart = new Highcharts(chart)
.InitChart(新图表{DefaultSeriesType = ChartTypes.Spline,ZoomType = ZoomTypes.X})
.SetTitle(新标题{Text =组合历史})
.SetSubtitle(新Subtitle {文本=单击并拖动绘图区以放大})
.SetOptions(new GlobalOptions { Global = new Global {UseUTC = false}})
.SetPlotOptions(new PlotOptions
{
Spline = new PlotOptionsSpline
{
LineWidth = 2,
States = new PlotOptionsSplineStates {Hover = new PlotOptionsSplineStatesHover {LineWidth = 3}},
Marker = new PlotOptionsSplineMarker
{
Enabled = false,
States = new PlotOptionsSplineMarkerStates
{
Hover = new PlotOptionsSplineMarkerStatesHover
{
Enabled = tru e,
Radius = 5,
LineWidth = 1
}
}
}
}
})
.SetXAxis新的XAxis
{
Type = AxisTypes.Datetime,
Labels = new XAxisLabels
{
Rotation = -45,
Align = HorizontalAligns.Right,
Style =font:'normal 10px Verdana,sans-serif'
},
Title = new XAxisTitle {Text =Time(Hour)},
})
。SetYAxis(new YAxis
{
Title = new YAxisTitle {Text =Kilowatt}
})
.SetSeries(allSeries.Select(s => new Series {Name = s.Name,Data = s.Data})。ToArray());
返回PartialView(图表);
}
I have a set of series that I have created using VB.NET and DotNet.HighCharts:
Dim SeriesList4As New List(Of Series)(stfipsList4.Count)
What I want to have happen is something similar to http://jsfiddle.net/8M2fF/ except I want to be able to pass in multiple series without knowing before hand how many I have.
The VB code that created that example above is this:
Dim stfipsList4 = (From r In dt4.AsEnumerable() Select r("areaname")).Distinct().ToList()
Dim SeriesList4 As New List(Of Series)(stfipsList4.Count)
Dim seriesItem4(stfipsList4.Count) As Series
Dim xDate4 As DateTime
Dim fakeDate4 As String
Dim sX4 As Integer
sX4 = 1
For Each state In stfipsList4
Dim data As New Dictionary(Of DateTime, Decimal)
Dim stateVal As String = state.ToString
Dim recCount As Integer = dt4.Rows.Count - 1
Dim seriesPointCount As Integer = dt4.Compute("Count(population)", "areaname = '" + stateVal + "'")
Dim chartData As Object(,) = New Object(seriesPointCount - 1, 1) {}
Dim x As Integer = 0
For i As Integer = 0 To recCount
If dt4.Rows(i)("areaname").ToString = stateVal Then
fakeDate4 = "1/1/" + dt4.Rows(i)("periodyear").ToString
xDate4 = DateTime.Parse(fakeDate4)
chartData.SetValue(xDate4.Date, x, 0)
chartData.SetValue(dt4.Rows(i)("population"), x, 1)
x += 1
End If
Next
seriesItem4(sX4) = New Series With {
.Name = state.ToString, _
.Data = New Helpers.Data(chartData)
}
SeriesList4.Add(seriesItem4(sX4))
sX4 = sX4 + 1
Next
Dim iterateData As String = JsonSerializer.Serialize(seriesItem4(1))
Dim chart4 As Highcharts = New Highcharts("chart4").SetOptions(New Helpers.GlobalOptions() With { _
.[Global] = New [Global]() With { _
.UseUTC = False _
} _
}).InitChart(New Chart() With { _
.DefaultSeriesType = ChartTypes.Column, _
.MarginRight = 10, _
.Events = New ChartEvents() With { _
.Load = "ChartEventsLoad" _
} _
}).SetTitle(New Title() With { _
.Text = "Population" _
}).SetTooltip(New Tooltip() With { _
.Formatter = "function() { return '<b>' + this.series.name + '<br/>' + Highcharts.dateFormat('%Y', this.x) +'</b>: '+ Highcharts.numberFormat(this.y, 0, ','); }" _
}).SetXAxis(New XAxis() With { _
.Type = AxisTypes.Datetime, _
.TickPixelInterval = 150 _
}).SetYAxis(New YAxis() With { _
.Min = 0, _
.Title = New YAxisTitle() With { _
.Text = "Population", _
.Align = AxisTitleAligns.High _
} _
}).SetSeries(New Series() With { _
.Data = New Helpers.Data(New Object() {}) _
}) _
.SetOptions(New Helpers.GlobalOptions() With { _
.Colors = palette_colors _
}) _
.AddJavascripVariable("iterated", iterateData.ToString) _
.AddJavascripFunction("ChartEventsLoad", "// set up the updating of the chart each second" & vbCr & vbLf & _
" var result = iterated.data;" & vbCr & vbLf & _
" var counter = 0;" & vbCr & vbLf & _
" var series = this.series[0];" & vbCr & vbLf & _
" var loopseries = function() {" & vbCr & vbLf & _
" if (counter <= result.length) {" & vbCr & vbLf & _
" var p = String(result[counter]);" & vbCr & vbLf & _
" var splitp = p.split("","");" & vbCr & vbLf & _
" var x = Number(splitp[0]);" & vbCr & vbLf & _
" var y = Number(splitp[1]);" & vbCr & vbLf & _
" series.addPoint([x, y], true, series.points.length > 10, true);" & vbCr & vbLf & _
" counter++;" & vbCr & vbLf & _
" } else {" & vbCr & vbLf & _
" clearInterval(loopseries);" & vbCr & vbLf & _
" }};" & vbCr & vbLf & _
" setInterval(loopseries, 300);")
ltrChart4.Text = chart4.ToHtmlString()
This is just for a single series. I would like to pass in a List(Of Series). Things that need to be involved: Creating n number of series Adding points to each series Naming each series
I can handle those items it is just passing in the master series "list" that I cannot accomplish.
EDIT: There seems to be some confusion on what I am asking. I am able to pass N number of series to HighCharts via the DotNet.HighCharts API. What I am not currently able to do is pass this same set of series to the javascript function to loop through and "play" the series. Please see:
.AddJavascripVariable("iterated", iterateData.ToString) _
.AddJavascripFunction("ChartEventsLoad", "// set up the updating of the chart each second" & vbCr & vbLf & _
" var result = iterated.data;" & vbCr & vbLf & _
" var counter = 0;" & vbCr & vbLf & _
" var series = this.series[0];" & vbCr & vbLf & _
" var loopseries = function() {" & vbCr & vbLf & _
" if (counter <= result.length) {" & vbCr & vbLf & _
" var p = String(result[counter]);" & vbCr & vbLf & _
" var splitp = p.split("","");" & vbCr & vbLf & _
" var x = Number(splitp[0]);" & vbCr & vbLf & _
" var y = Number(splitp[1]);" & vbCr & vbLf & _
" series.addPoint([x, y], true, series.points.length > 10, true);" & vbCr & vbLf & _
" counter++;" & vbCr & vbLf & _
" } else {" & vbCr & vbLf & _
" clearInterval(loopseries);" & vbCr & vbLf & _
" }};" & vbCr & vbLf & _
" setInterval(loopseries, 300);")
The .AddJavaScriptVariable expects a string and in-lining the code is giving me invalid object references.
I actually use DotNet.Highcharts to create a chart that has an undefined number of series. To do this I query for the data I need to add to the chart using linq. I use a list of object[] to create the individual points then I take that list and add it to a list of Series. I iterate through the loop as many times as I need to get all of the Series. Then for SetSeries I assign what was contained in the Series list. The code is written in C# but I am sure you can change it to VB.NET. Here is the entire ActionResult I use for creating the chart:
public ActionResult CombinerBarToday(DateTime? utcStartingDate = null,
DateTime? utcEndingDate = null)
{
//GET THE GENERATED POWER READINGS FOR THE SPECIFIED DATETIME
var firstQ = from s in db.PowerCombinerHistorys
join u in db.PowerCombiners on s.combiner_id equals u.id
where s.recordTime >= utcStartingDate
where s.recordTime <= utcEndingDate
select new
{
CombinerID = u.name,
Current = s.current,
RecordTime = s.recordTime,
Voltage = s.voltage,
Watts = (s.current * s.voltage)
};
//GET A LIST OF THE COMBINERS CONTAINED IN THE QUERY
var secondQ = (from s in firstQ
select new
{
Combiner = s.CombinerID
}).Distinct();
/* THIS LIST OF SERIES WILL BE USED TO DYNAMICALLY ADD AS MANY SERIES
* TO THE HIGHCHARTS AS NEEDED WITHOUT HAVING TO CREATE EACH SERIES INDIVIUALY */
List<Series> allSeries = new List<Series>();
TimeZoneInfo easternZone = TimeZoneInfo.FindSystemTimeZoneById("Eastern Standard Time");
//LOOP THROUGH EACH COMBINER AND CREATE SERIES
foreach (var distinctCombiner in secondQ)
{
var combinerDetail = from s in db2.PowerCombinerHistorys
join u in db2.PowerCombiners on s.combiner_id equals u.id
where u.name == distinctCombiner.Combiner
where s.recordTime >= utcStartingDate
where s.recordTime <= utcEndingDate
select new
{
CombinerID = u.name,
Current = s.current,
RecordTime = s.recordTime,
Voltage = s.voltage,
Watts = (s.current * s.voltage) / 1000d
};
var results = new List<object[]>();
foreach (var detailCombiner in combinerDetail)
{
results.Add(new object[] {
TimeZoneInfo.ConvertTimeFromUtc(detailCombiner.RecordTime, easternZone),
detailCombiner.Watts });
}
allSeries.Add(new Series
{
Name = distinctCombiner.Combiner,
//Data = new Data(myData)
Data = new Data(results.ToArray())
});
}
Highcharts chart = new Highcharts("chart")
.InitChart(new Chart { DefaultSeriesType = ChartTypes.Spline, ZoomType = ZoomTypes.X})
.SetTitle(new Title { Text = "Combiner History" })
.SetSubtitle(new Subtitle { Text = "Click and drag in the plot area to zoom in" })
.SetOptions(new GlobalOptions { Global = new Global { UseUTC = false } })
.SetPlotOptions(new PlotOptions
{
Spline = new PlotOptionsSpline
{
LineWidth = 2,
States = new PlotOptionsSplineStates { Hover = new PlotOptionsSplineStatesHover { LineWidth = 3 } },
Marker = new PlotOptionsSplineMarker
{
Enabled = false,
States = new PlotOptionsSplineMarkerStates
{
Hover = new PlotOptionsSplineMarkerStatesHover
{
Enabled = true,
Radius = 5,
LineWidth = 1
}
}
}
}
})
.SetXAxis(new XAxis
{
Type = AxisTypes.Datetime,
Labels = new XAxisLabels
{
Rotation = -45,
Align = HorizontalAligns.Right,
Style = "font: 'normal 10px Verdana, sans-serif'"
},
Title = new XAxisTitle { Text = "Time(Hour)" },
})
.SetYAxis(new YAxis
{
Title = new YAxisTitle { Text = "Kilowatt" }
})
.SetSeries(allSeries.Select(s => new Series {Name = s.Name, Data = s.Data }).ToArray());
return PartialView(chart);
}
这篇关于使用HighCharts和DotNet.HighCharts来“播放”多个系列的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!