使用同一数据集的不同维度,屏幕上有三个dc.js折线图。
当用户点击任何lineChart上的数据点时,我希望找到并返回所有其他图表(包括点击的图表)中相应点的数据值。
我也尝试(在鼠标悬停时)将圆形填充颜色更改为正在悬停的数据点的红色,以及所有其他图表的相应数据点(相同的“x”值)。
我正在使用'Imports System.Linq.Enumerable
'Imports System.Runtime.CompilerServices ' for extensions
Public Class clsField
Public idx As String
Public name As String
Public weight As Long
Public Sub New(Optional i As String = vbNullString, Optional n As String = vbNullString, Optional w As Long = vbNullString)
idx = i : name = n : weight = w
End Sub
End Class
Public Class Container
Public fields As clsField()
' returns a list sorted by clsField.weight preserving order for elements with same 'weight' value
Public Function getFields() As List(Of KeyValuePair(Of String, clsField))
Dim auxList As List(Of KeyValuePair(Of String, clsField))
If (fields Is Nothing) OrElse (fields.Count < 1) Then Return New List(Of KeyValuePair(Of String, clsField))
' .ToList to transform IEnumerable to the return type
auxList = Array.ConvertAll(fields, New Converter(Of clsField, KeyValuePair(Of String, clsField))(AddressOf FieldToPair)).ToList
Return auxList.OrderBy(Function(x) x.Value.weight).ToList()
End Function
Public Shared Function FieldToPair(fld As clsField) As KeyValuePair(Of String, clsField)
Return New KeyValuePair(Of String, clsField)(fld.idx, fld)
End Function
End Class
Public Class Consumer
Public cont As Container
Public Sub New()
cont = New Container
cont.fields.Add(New clsField("ffq", "foo30004", 33))
cont.fields.Add(New clsField("ffc", "foo9997", 55))
cont.fields.Add(New clsField("ffp", "foo9908", 55))
cont.fields.Add(New clsField("ffo", "foo100001", 22))
cont.fields.Add(New clsField("ffx", "foo8885", 33))
cont.fields.Add(New clsField("ffz", "foo70002", 22))
cont.fields.Add(New clsField("ffy", "foo8806", 33))
cont.fields.Add(New clsField("ffa", "foo9009", 55))
cont.fields.Add(New clsField("ffb", "foo8000", 55))
cont.fields.Add(New clsField("ffn", "foo7003", 22))
End Sub
Public Sub printSortedFields()
Dim aux As List(Of KeyValuePair(Of String, clsField))
aux = cont.getFields()
For Each pair As KeyValuePair(Of String, clsField) In aux
Console.WriteLine(pair.Value.name)
With pair.Value
Debug.Print("name: " & .name & " || idx: " & .idx & " || weight: " & .weight)
End With
Next
End Sub
Public Sub Main()
printSortedFields()
End Sub
End Class
Module ArrayExtension ' custom method for array
<Extension()>
Public Sub Add(Of T)(ByRef arr As T(), item As T)
If arr IsNot Nothing Then
Array.Resize(arr, arr.Length + 1)
arr(arr.Length - 1) = item
Else
ReDim arr(0)
arr(0) = item
End If
End Sub
End Module
方法但未成功获取所需数据。错误消息为:name: foo100001 || idx: ffo || weight: 22
name: foo70002 || idx: ffz || weight: 22
name: foo7003 || idx: ffn || weight: 22
name: foo30004 || idx: ffq || weight: 33
name: foo8885 || idx: ffx || weight: 33
name: foo8806 || idx: ffy || weight: 33
name: foo9997 || idx: ffc || weight: 55
name: foo9908 || idx: ffp || weight: 55
name: foo9009 || idx: ffa || weight: 55
name: foo8000 || idx: ffb || weight: 55
.filter()
答案 0 :(得分:10)
myCSV
包含所有三个数据点,因此我不认为需要独立遍历三个图表 - findAllPoints
将为所有三个数据系列找到相同的数组条目反正。
您遇到的主要问题是,如果日期对象具有相同的值,则它们不会相等。这是因为如果操作数是对象,==
(和===
)会评估对象标识:
> var d1 = new Date(), d2 = new Date(d1)
undefined
> d1
Mon Feb 13 2017 09:03:53 GMT-0500 (EST)
> d2
Mon Feb 13 2017 09:03:53 GMT-0500 (EST)
> d1==d2
false
> d1.getTime()===d2.getTime()
true
有两种方法可以解决这个问题。
如果所有图表中的项目逐项匹配,则只需使用索引。
所有d3回调都传递了基准和索引。所以你可以修改你的回调:
allDots1.on('click', function(d,i) {
// ...
allDots2.filter((d,j)=> j===i).attr('fill','red').style('fill-opacity', 1);
alert(JSON.stringify(myCSV[i]));
});
http://jsfiddle.net/gordonwoodhull/drbtmL77/7/
如果不同的图表可能具有不同的数据索引,您可能希望按日期进行比较,但使用Date.getTime()
获取可与===
进行比较的整数:
allDots1.on('click', function(d) {
var d2find = d.x;
// ...
allDots2.filter(d=> d.x.getTime()===d2find.getTime()).attr('fill','red').style('fill-opacity', 1);
var row = myCSV.filter(r=>r.date.getTime()===d2find.getTime())
alert(JSON.stringify(row));
});
http://jsfiddle.net/gordonwoodhull/drbtmL77/10/
请注意,在任何一种情况下,您都需要更改其他图表中点的不透明度,因为否则它们不会显示,直到它们被悬停。
不确定何时要重置此功能 - 我想在mouseover
上显示相应的点并将其隐藏在mouseout
上可能会更有意义。希望这足以让你入门!