html绘制⽢特图,基于JS简单⽢特图
最近同事求助到⼀个⼩⼩的需求,写⼀个时间⽢特图,主要想表现⼀个车在⼀天的不同的时间点⾥,停靠的站点,
先来看⼀下效果吧,这⾥的需求是从早上的5点为开始时间,到第⼆天到凌晨5点
前期准备
其实⽹上有很多⽢特图的实现⽅式,但是他们都只能具象到天,不能具体到某个时间点,⽽且每⼀个具体的时间段中的描述是不能⾃定义的,所以准备⾃⼰写⼀下了。
实现逻辑
我们可以先模拟⼀些demo数据,这⾥⾯最为主要的数据为每个时间点,我们要实现上⾯的效果,需要对每个时间点进⾏拆分。
var demoData: [
{
carNum: '川A09384',
innerData: [
{
start: '2019/1/21 6:23',
end: '2019/1/21 7:45',
value: 'A站点',
bg: 'green'
},
{
start: '2019/1/21 12:23',
end: '2019/1/21 16:45',
value: 'B站点',
bg: 'yellow'
},
{
start: '2019/1/21 20:00',
end: '2019/1/21 23:25',
value: 'C站点',
bg: 'blue'
}
]
},
{ carNum: '川A04384',
innerData: [
{
start: '2019/1/21 5:23',
end: '2019/1/21 6:05',
value: 'A站点',
bg: 'blue'
},
{
start: '2019/1/21 10:23',
end: '2019/1/21 13:45',
value: 'B站点',
bg: 'green'
},
{
start: '2019/1/21 21:00',
end: '2019/1/22 3:35',
value: 'C站点',
bg: 'yellow'
},
]
}]
复制代码
⾸先创建时间
// 创建时间
createHours: function(){
var startHour = 5;
var endHour = 11;
var html = '';
for (let i = startHour; i< 24; i++) { html += `
${i < 10 ? `0${i}` : i}:00
`
}
for (let i = 0; i< endHour; i++) { html += `
${i < 10 ? `0${i}` : i}:00
`
}
},
复制代码
根据数据绘制⽢特图
我们将 1H = 60px;这样去定宽,即 1px = 1M;
绘制第⼀个时间段 start:'2019/1/21 6:23'; end: '2019/1/21 7:45';
var start = new Date('2019/1/21 6:23'),
end = new Date('2019/1/21 7:45'),
start_h = Hours(), // 开始时间
start_m = Minutes(), // 开始分钟
end_h = Hours(), // 结束时间
end_m = Minutes(), // 结束分钟
left_offset = 0;
_left_offset = 0;
width = '';
// 获取时间段⽢特图的开始位置(我们从5点开始,所以-5);
left_offset = (start_h - 5) * 60 + start_m;
/
/ 获取每⼀段⽢特图的宽度,
// 先计算出结束时间的位置,然后在减去开始时间的左边距;
width = ((end_h - 5) * 60 + end_m) - left_offset;
// 使⽤现有的左边距减去前⼀个时间的左边距
_left_offset = left_offset - allLeft;
// 因为存在多个时间段,所以在绘制下⼀个时间断时,left_offset
// 使⽤allLeft存储上⼀个时间断距离左边的距离。
allLeft = left_offset + width;
// 将其添加到DOM中
html += `${innerData[i].value}`;
复制代码
⾸先需要到时间段中开始时间的开始位置,
计算出时间的width,遵循1px = 1M的规则。
在设置margin-left时,记得减去上⼀个时间段⽢特图的margin-left(重点)。没绘制⼀条后,存储其margin-left,⽅便下⼀个时间段使⽤。
关于跨天怎么计算
当我们的时间段是属于跨天的怎么计算他的开始和结束位置,以及他的宽度呢?直接贴代码了哈,createData: function() {
var data = this.demoData;
var today = new Date().getDate(); // 今天的⽇期
for (let m = 0; m< data.length; m++) {
var innerData = data[m].innerData;
var html = '';
var allLeft = 0;
for (let i = 0; i< innerData.length; i++) {
var start = new Date(innerData[i].start),
end = new Date(innerData[i].end),
start_d = Date(),
end_d = Date(),
start_h = Hours(),
start_m = Minutes(),
end_h = Hours(),
end_m = Minutes(),
left_offset = 0;
_left_offset = 0;
width = '';
if (start_d === (today + 1)) {
left_offset = ((23 - 5) * 60) + ((start_h + 1) * 60) + start_m;
_left_offset = left_offset - allLeft;
width = (((23 + (end_h + 1)) - 5) * 60 + end_m) - left_offset;
} else if (end_d === (today + 1)) {
left_offset = ((start_h - 5) * 60) + start_m;
_left_offset = left_offset - allLeft;
width = (((24 + end_h) - 5) * 60 + end_m) - left_offset;
} else {
left_offset = (start_h - 5) * 60 + start_m;
_left_offset = left_offset - allLeft;
width = ((end_h - 5) * 60 + end_m) - left_offset;
}
allLeft = left_offset + width;
html += `${innerData[i].value}`;
}
${html}
`;
}
}
复制代码
这个地⽅就不详细解说了,有什么不懂的地⽅欢迎⼤家留⾔。代码很简洁,主要⽤于实现⼀个⽐较简单的⽢特图。不需要下载什么插件之类的。
这⾥把代码贴出来哈,⼤家可以⼀起交流,或许你有更好的实现⽅式呢。
测试demo
#container {
width: 100%;
overflow: scroll;
height: calc(100vh - 0px);
box sizing
width: 1900px;
}
.carNum {
float:left;
width:100px;
text-align: center;
}
#hour {
width: 1800px;
overflow: scroll;
}
#hour div{
width: 60px;
float: left;
border-left: 1px solid #ddd;
background: #ccc;
text-align: center;
box-sizing: border-box;
}

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。