问题篇(详解):http://www.cnblogs.com/hanyinglong/p/4708337.html
1.前言
a.在系统开发过程中可能会使用到图表控件,一个好的图标控件可以使我们的网站增加很好的动态感和美感以及增加人气。那么如果我们遇到这种需求的话就需要去找寻图表控件,我在开发过程中也是用过很多的图表控件(HighCharts,Charts,ECharts等等),那么下面我就简单介绍一下这三种插件,代码实现是:Echarts。
(1):HighCharts 官网:http://www.highcharts.com/
(2):Charts 官网:http://www.telerik.com/aspnet-mvc/charts?utm_medium=listings&utm_source=VisualStudioGallery&utm_campaign=dt-MVC-jan2015
(3):ECharts 官网:http://echarts.baidu.com/
b.因为上面三个图表控件都是基于JavaScript来实现的,所以相对来说对于我们开发人员调用起来也很容易,下载引用,然后查看API,查询API就能实现需要的功能,那么为什么我这里还要写一篇博客呢,其实主要还是给大家简单介绍一下,如果开发人员没有很多时间去看的话可以直接仿照我的例子去实现,速度可以相对来说比查看API快一点,但是要深入了解还需要查看API中每个方法的属性和事件,才能真正使用的得心应手。
c.ECahrts API地址:http://echarts.baidu.com/doc/doc.html,http://echarts.baidu.com/doc/option.html。
2.准备工作
a.首先登录ECharts 官网:http://echarts.baidu.com/,在导航中可以看到下载按钮,单击下拉选择需要下载的包下载保存到电脑上。
b.创建ASP.NET MVC或者ASP.NET 项目,在Scripts文件夹下面创建echarts文件夹。
c.解压下载成功的文件夹之后选择build或者dist文件夹复制到创建的项目中的Scripts的文件夹下面的echarts文件夹下面。
d.项目创建完成之后如图所示:
3.实现功能:
a.本实例实在ASP.NET MVC下面实现的,故我们按照HTML,JS和后端的实现分离将代码贴出来,大家仔细查看即可。
b.ECharts插件依赖于Jquery,所以在引入echarts.js之前需要引入Jquery.js,请注意.
c.HTML页面代码如下:
@using System.Web.Optimization <style type="text/css">
.selectRefreshInfo {
width: 80px;
height: 28px;
margin: 2px 0;
}
</style> <!--展示监控信息-->
<div id="main" style="height: 400px;"></div>
<div id="foot_order" style="height: 30px;text-align: center">
@Html.DropDownList("Name",ViewBag.SelectList as IEnumerable<SelectListItem>,new { @class = "selectRefreshInfo",Id="dropDownId" })
<span style="color: red">(秒)设置发送时间间隔</span>
<input type="button" class="btn btn-primary" value="停止刷新" onclick="Ecarts.BtnStopRefresh()"/>
<input type="button" class="btn btn-primary" value="手动刷新" onclick="Ecarts.BtnHandRefresh()"/>
</div> @section footerJs
{
@Scripts.Render("~/Scripts/echarts/build/dist/echarts.js")
@Scripts.Render("~/Scripts/Views/orderInfoIndex.js")
}
d.JS页面代码如下:
/* 功能:实现读取数据库中的需要监控的数据在前端展示,JS操作Echarts插件
* 创建人:Kencery 创建时间:2015-7-30 */ //初始化加载信息
$(document).ready(function() {
//页面打开时候的初始化
Ecarts.EcartsReFresh();
//初始化完成之后按照第一个下拉框的时间刷新
Ecarts.SetInterval($("#dropDownId").find("option:selected").text());
//当下拉列表框改变的时候定时执行程序
Ecarts.DropDownChange();
}); var callUrl = { readDataRefreshChats: "/OrderInfo/ReadDataRefreshChats" }; //路径配置
require.config({
paths: { echarts: '/Scripts/echarts/build/dist' }
}); var lineBar = "bar"; //读取bar
var interVal; //最终删除定时执行程序
var Ecarts = {
EcartsReFresh: function() {
require([//使用线性图或者柱状图加载line和bar模块,按需加载
'echarts',
'echarts/chart/line',
'echarts/chart/bar'
], function(orderInfo) {
var myChart = orderInfo.init(document.getElementById('main')); //初始化Echarts图标信息 //选择magicType时间,读取选择的是什么图形
var ecConfig = require('echarts/config');
myChart.on(ecConfig.EVENT.MAGIC_TYPE_CHANGED, function(param) {
if (param.magicType.bar) {
lineBar = "bar";
} else {
lineBar = "line";
}
}); //发送异步请求从后台读取Option参数,赋值给Charts对象
$.getJSON(callUrl.readDataRefreshChats, { lineBar: lineBar, }, function(data) {
var option = {
title: {
text: '订单号剩余量监控',
},
tooltip: {
show: true,
trigger: 'axis'
},
toolbox: {
show: true,
feature: {
dataView: { show: true, readOnly: false },
magicType: { show: true, type: ['line', 'bar'] },
restore: { show: true },
saveAsImage: { show: true }
}
},
legend: {
data: data.Legend
},
xAxis: [
{
name: data.XName,
type: 'category',
data: data.XAxis //所有日期读取
}
],
yAxis: [{
name: '剩余量',
type: 'value',
scale: true,
precision: 2,
splitNumber: 12,
splitArea: { show: true }
}],
series: data.SeriesList
};
myChart.setOption(option); // 为echarts对象加载数据
});
});
},
SetInterval: function(dropText) { //定时执行刷新程序
interVal = window.setInterval(function() {
Ecarts.EcartsReFresh();
}, readRefreshSecond(dropText));
},
DropDownChange: function() {
//下拉列表变化刷新事件
$("#dropDownId").change(function() {
clearInterval(interVal);
Ecarts.SetInterval($(this).find("option:selected").text());
});
},
BtnHandRefresh: function() { //手动刷新
Ecarts.EcartsReFresh();
},
BtnStopRefresh: function() { //定制定时程序的执行
clearInterval(interVal);
},
}; function readRefreshSecond(dropDownId) {
return dropDownId * 1000;
}
JS实现对Echarts的操作
e.后端调用数据库代码如下:
/// <summary>
/// 返回监控业务订单数量的页面
/// 创建者:Kencery 创建时间:2015-7-31
/// </summary>
public ActionResult Index()
{
ViewBag.Title = "订单监控"; //读取刷新时间的秒数,返回到前台下拉框中显示
List<NameId> refreshTime = CommonInfo.ConvertToList(ConfigHelper.RefreshTime);
var selectList = new SelectList(refreshTime, "Id", "Name");
ViewBag.SelectList = selectList.AsEnumerable();
return View();
} /// <summary>
/// 读取数据库中的数据信息刷新图表控件,控制前端显示多少条数据(订单号数量)
/// 创建者:Kencery 创建时间:2015-7-31
/// </summary>
public ActionResult ReadDataRefreshChats(int skip = , string lineBar = "line")
{
//发送请求读取数据库中的数据,进行处理(BLL层处理业务逻辑)
var readChats = _orderMonitorDataBll.ReadDataRefreshChats(, lineBar);
return Json(readChats, JsonRequestBehavior.AllowGet);
}
控制器中的代码实现
f.实现控制器中的方法如下:
using System.Collections.Generic; namespace Ets.MonitorSystem.Model
{
/// <summary>
/// 构造返回Echarts需要的实体对象
/// 创建者:kencery 创建日期:2015-7-31
/// </summary>
public class EchartQueryInfo
{
/// <summary>
/// 头标题,显示所有的标题信息
/// </summary>
public string[] Legend { get; set; } /// <summary>
/// X轴显示的内容
/// </summary>
public string[] XAxis { get; set; } /// <summary>
/// Y轴显示的内容
/// </summary>
public string[] YAxis { get; set; } /// <summary>
/// X轴名称
/// </summary>
public string XName { get; set; } /// <summary>
/// 读取显示数据的条线信息
/// </summary>
public List<Series> SeriesList { get; set; } } /// <summary>
/// 读取集合信息
/// </summary>
public class Series
{
/// <summary>
/// 名称,Legend中的集合一一对应
/// </summary>
public string name { get; set; } /// <summary>
/// 类型,显示树状还是线性
/// </summary>
public string type { get; set; } /// <summary>
/// 线性数据的显示
/// </summary>
public int[] data { get; set; }
}
}
实体
/// <summary>
/// 读取数据库中的数据信息刷新图表控件,控制前端显示多少条数据(订单号数量)
/// 创建者:Kencery 创建时间:2015-7-31
/// </summary>
/// <param name="skip">显示多少条数量</param>
/// <param name="lineBar"></param>
/// <returns>返回构造成功的需要给前端展示的图标信息集合</returns>
public EchartQueryInfo ReadDataRefreshChats(int skip, string lineBar)
{
//从Web.Config中读取Legend信息,然后作为参数查询后面的值信息
List<NameId> listNameId = CommonInfo.ConvertToListInfo(ConfigHelper.OrderTypeInfo); //读取Chats中其它需要显示的信息
string[] xAxis;
string xName;
var listSeries = ReadDataInfo(skip, listNameId, lineBar, out xAxis, out xName); //构造实体对象,读取所有需要读取的信息,将读取数据的所有方法封装到方法外面实现
var echartQueryInfo = new EchartQueryInfo
{
Legend = listNameId.Select(c => c.Name).ToArray(),
XAxis = xAxis,
XName = xName,
SeriesList = listSeries
};
return echartQueryInfo;
} /// <summary>
/// 读取Chat中的横坐标和展示数据的信息
/// 创建者:Kencery 创建时间:2015-7-31
/// </summary>
/// <param name="skip">显示多少条数量</param>
/// <param name="nameIds">限制查询的类型</param>
/// <param name="lineBar"></param>
/// <param name="xAxis">X轴的数据</param>
/// <param name="xName">X轴坐标名称</param>
/// <returns>返回需要展示的数据(Echat图表信息)</returns>
private List<Series> ReadDataInfo(int skip, List<NameId> nameIds, string lineBar, out string[] xAxis,
out string xName)
{
//查询数据库,构造需要查询的数据展示出来
var data = _dal.ReadDataRefreshChats(skip, nameIds); //首先循环对象
var listSeries = nameIds.Select(nameId => new Series
{
name = nameId.Name,
type = lineBar,
data = data.Where(c => c.OrderType == nameId.Id).Select(c => c.OrderNumber).ToArray()
}).ToList(); //处理时间的显示YY "
xAxis = data.Where(c => c.OrderType == nameIds[].Id).Select(c => c.MonitorDate.ToString("HH:mm")).ToArray();
var dataFirst = data.FirstOrDefault();
xName = dataFirst == null
? DateTime.Now.ToString("yyyy-MM-dd")
: dataFirst.MonitorDate.ToString("yyyy-MM-dd");
return listSeries;
}
业务逻辑层代码
<!--RefreshTime 刷新时间的的限制配置-->
<add key="RefreshTime" value="2,5,7,10,20,30,40,100,200,500" />
<!--RefreshTime 监控对象-->
<add key="OrderTypeInfo" value="1:外卖,2:堂食,3:当面付,4:订台,5:排队"/>
Web.Config中appSettings下代码的设置
/// <summary>
/// 按,分隔的字符串换成List对象
/// </summary>
/// 创建者:Kencery 创建时间:2015-7-29
public static List<NameId> ConvertToList(string refreshTime, char split = ',')
{
var strSplit = refreshTime.Split(new[] {split});
List<NameId> list = strSplit.Select((t, i) => new NameId()
{
Id = i + ,
Name = t
}).ToList();
return list;
} /// <summary>
/// 转换读取Web.Config中的字符串,转换成List集合
/// 创建者:Kencery 创建时间:2015-7-29
/// </summary>
public static List<NameId> ConvertToListInfo(string str, char split = ',', char splitTwo = ':')
{
var strSplits = str.Split(new[] {split});
//循环集合添加List对象 //循环处理分隔字符串转换成Liststring
return strSplits.Select(strSplit => strSplit.Split(new[] {splitTwo})).Select(strS => new NameId
{
Id = Convert.ToInt32(strS[]),
Name = strS[]
}).ToList();
} /// <summary>
/// 读取刷新时间的的限制配置
/// </summary>
public static string RefreshTime
{
get
{
return ConfigurationManager.AppSettings["RefreshTime"] ?? "";
}
} /// <summary>
/// 读取web.Config中需要监控的对象
/// </summary>
public static string OrderTypeInfo
{
get
{
return ConfigurationManager.AppSettings["OrderTypeInfo"] ?? "1:外卖";
}
}
Common代码中对Web.Config中读取的信息的处理
/// <summary>
/// 读取数据库中的数据信息刷新图表控件,控制前端显示多少条数据(订单号数量)
/// 创建者:Kencery 创建时间:2015-7-31
/// </summary>
/// <param name="skip">显示多少条数量</param>
/// <param name="nameIds">构造SQL语句的灵活控制</param>
/// <returns>返回构造成功的需要给前端展示的图标信息集合</returns>
public List<OrderMonitorDataModel> ReadDataRefreshChats(int skip, List<NameId> nameIds)
{
//构造SQL语句
var sb = new StringBuilder();
sb.Append(
"SELECT OrderNumber,OrderType,MonitorDate FROM (SELECT TOP " + skip +
" OrderNumber,OrderType,MonitorDate FROM MonitorData_Order WHERE MonitorType=" +
(int) MonitorType.One + " AND OrderType=" + nameIds[].Id + " ORDER BY MonitorDate DESC ");
for (int i = ; i < nameIds.Count(); i++)
{
sb.Append(
"UNION ALL SELECT TOP " + skip +
" OrderNumber,OrderType,MonitorDate FROM MonitorData_Order WHERE MonitorType= " +
(int) MonitorType.One + "AND OrderType=" + nameIds[i].Id + " ORDER BY MonitorDate DESC ");
}
sb.Append(") AS TEMP"); using (_db)
{
var queryInfo = _db.Query<OrderMonitorDataModel>(sb.ToString()).ToList();
return queryInfo;
}
}
数据库操作业务代码
4.数据库和实现页面的图片展示: