【问题标题】:nvd3 linechart display date tick values on X axisnvd3 折线图在 X 轴上显示日期刻度值
【发布时间】:2014-05-01 16:00:51
【问题描述】:

我需要在我的 Web 项目中添加折线图。它需要在 x 轴上有日期值,在 y 轴上有整数。目前数据显示如下:

我需要它像这个 excel 版本一样显示:

我无法让数据与 x 轴正确对齐,也无法让 x 轴上的标签显示正确的日期。我的网页(使用 Razor 语法)设置如下:

<style>
svg {
display: block;
}

#chart1 svg{
height: 500px;
min-width: 100px;
min-height: 100px;

}
</style>
<script>

var chart;

var data2 = JSON.parse(@Html.Raw(Json.Encode(ViewBag.data)));

var data = data2[0];

nv.addGraph(function() {

  chart = nv.models.lineChart();

  chart
  .x(function(d,i) 
  {     
   return i;
    })


  chart.xAxis 
  .tickFormat(function(d) 
  {      
   return d3.time.format('%b %d')(new Date(d));
    })


  chart.yAxis
  .axisLabel('Voltage (v)')
  .tickFormat(d3.format(',.2f'));

    chart.showXAxis(true);

    d3.select('#chart1 svg')
    //.datum([]) //for testing noData
    .datum(data)
.transition().duration(500)
    .call(chart);

      nv.utils.windowResize(chart.update);


    chart.dispatch.on('stateChange', function(e) { nv.log('New State:', JSON.stringify(e)); });

      return chart;
       });

      </script>

数据以正确的格式传入。有什么想法吗?

@ViewBag.name

【问题讨论】:

    标签: javascript asp.net-mvc web nvd3.js


    【解决方案1】:

    好的,我设法修复了它,但这有点麻烦。在控制器中,我用整数索引替换了 JSON 数据中的日期。我通过找到最小日期、将其设置为 x 轴索引 0、下一个日期为 1 等来解决这些问题。 然后,我将格式化日期的 JSON 数组从控制器传递给视图,以便您可以使用索引来查找日期。 控制器代码:

     public ActionResult MileageReport(DateTime startDate, DateTime endDate)
        {
            using (EventsManager manager = new EventsManager())
            {
                IEnumerable<Event> travelEvents = manager.GetEventsWhere(t => t.Eventtype == EventType.Travel.ToString() && t.Createddt > startDate && t.Createddt < endDate);
                Dictionary<DateTime, int> mappedDates = MapDatesToIndices(travelEvents);
                var groupedEvents = travelEvents.GroupBy(e => e.Userid);
                JArray jsonArray = new JArray();
                IColourPicker colourPicker = NinjectFactory.GetNinJectKernel().Get<IColourPicker>();
                int i = 0;
    
                List<Event> events, tempEvents;
                List<DateTime> days;
                Event travelEvent;
    
                foreach (IGrouping<string, Event> group in groupedEvents)
                {
                    //we only want the last event for each day
                    events = group.ToList();
    
                    days = events.Select(e => e.Createddt.Value.Date).Distinct().OrderBy(o => o).ToList();
    
                    dynamic tEvent = new ExpandoObject();
                    tEvent.key = group.Key;
                    tEvent.color = colourPicker.GetColour(i);
    
                    JArray tEvents = new JArray();
                    foreach (DateTime day in days)
                    {
                        tempEvents = events.Where(e => e.Createddt.Value.Date == day).ToList();
                        travelEvent = tempEvents.Single(e => e.Mileage.Value == tempEvents.Select(m => m.Mileage.Value).Max());
                        object tvObj = new { x = mappedDates[travelEvent.Createddt.Value.Date], y = travelEvent.Mileage };
    
                        tEvents.Add(JObject.FromObject(tvObj));
                    }
                    tEvent.values = tEvents;
                    jsonArray.Add(JObject.FromObject(tEvent));
                    i++;
                }
    
    
    
    
                string jsonStringTemp = jsonArray.ToString();
    
                string jsonString = FormatJsonString(jsonStringTemp);
                ViewBag.xaxislabels = FormatDatesForIndices(mappedDates);
                ViewBag.data = jsonString;
                ViewBag.name = "Mileage Report";
                return PartialView("LineGraph");
    
    
            }
        }
    
        private dynamic FormatDatesForIndices(Dictionary<DateTime, int> mappedDates)
        {
            List<DateTime> dates = mappedDates.Keys.ToList();
    
            object[] items = new object[dates.Count];
    
    
            for (int i = 0; i < dates.Count; i++)
            {
                items[i] = new { date = dates[i].ToString(BaseFormats.DateDisplayFormatNoYear) };
            }
    
            JavaScriptSerializer js = new JavaScriptSerializer();
            string jsonString = js.Serialize(items);
    
    
            return jsonString;
        }
    
        private Dictionary<DateTime, int> MapDatesToIndices(IEnumerable<Event> travelEvents)
        {
            Dictionary<DateTime, int> mappedDates = new Dictionary<DateTime, int>();
    
            List<DateTime?> dts = travelEvents.Select(t => t.Createddt).ToList();
    
            dts = dts.Where(d => d != null).ToList();
    
            DateTime min = dts.Min().Value.Date;
            DateTime max = dts.Max().Value.Date;
    
            int i = 0;
    
            mappedDates.Add(min, i);
    
            min = min.AddDays(1);
    
            while (min.Date <= max.Date)
            {
                ++i;
                mappedDates.Add(min, i);
                min = min.AddDays(1);
            }
    
            return mappedDates;
        }
    

    然后在视图中我覆盖了 x 函数以返回我放入 JSON 数据的 x 值。我还覆盖了 tickformat 以返回我传递给视图的格式化日期。 查看代码:

    <style>
     svg {
     display: block;
     }
    
     #chart1 svg{
      height: 500px;
      min-width: 100px;
      min-height: 100px;
    
    }
    </style>
    <script>
    
    var chart;
    
    var data2 = JSON.parse(@Html.Raw(Json.Encode(ViewBag.data)));
    
    var data = data2[0];
    
    var m_xaxisLabels = JSON.parse(@Html.Raw(Json.Encode(ViewBag.xaxislabels)));
    
    nv.addGraph(function() {
    
     chart = nv.models.lineChart();
    
    
     chart
      .x(function(d,i) 
      {     
       return d.x;
        })
    
       chart.xAxis.tickFormat(function(d, i){
         return m_xaxisLabels[d].date;
       });
    
      chart.yAxis
      .axisLabel('Voltage (v)')
      .tickFormat(d3.format(',.2f'));
    
      chart.showXAxis(true);
    
      d3.select('#chart1 svg')
      .datum(data)
    .transition().duration(500)
      .call(chart);
    
      nv.utils.windowResize(chart.update);
    
     chart.dispatch.on('stateChange', function(e) { nv.log('New State:', JSON.stringify(e)); });
    
     return chart;
    });
    
    </script>
    
    
    <h2>@ViewBag.name</h2>
    <div id="chart1">
    <svg></svg>
    </div>
    

    现在它是一种享受!:

    【讨论】:

      猜你喜欢
      • 2014-12-24
      • 2015-03-24
      • 1970-01-01
      • 1970-01-01
      • 2022-08-04
      • 1970-01-01
      • 1970-01-01
      • 2016-03-01
      • 1970-01-01
      相关资源
      最近更新 更多