一、初始的柱状图的上升效果
- D3中可用于实现图形过渡的方法有四种:
1.transition()
该 API 的功能为启动过渡效果。其前后是图形变化前后的状态,可用于形状,位置,颜色的变化。
2.duration()
该 API 的功能为指定过渡的持续时间,单位为毫秒。例如duration(1000),即1秒。
3.ease()
该API可以指定过渡的变化方式,常用的如下:
①linear:普通的线性变化;
②circle:慢慢地到达变换的最终状态;
③elastic:带有弹跳的到达最终状态;
④bounce:在最终状态处弹跳几次;
4.delay()
用于指定延迟的时间,表示一定时间后才开始转变,单位为毫秒。
- 开始的动画效果代码如下:使用.transition(),前后y的位置由svgHeight -到 svgHeight - scale(d),使用了delay(),使其按照x位置的顺序延迟矩形的动态变化。
.attr("y",function(d){
return svgHeight;
})
.attr("height", function(d){
return 0;
})
//产生上升效果
.transition()
//顺序上升
.delay(function(d,i){
return i * 200;
})
//上升速度调节
.duration(500)
//上升到指定高度
.attr('y', (d) => svgHeight - scale(d))
- 效果如下:
二、冒泡排序
- 递归实现冒泡排序的方法为:
function bullsort(arr,size){
if(size<2){return;} //递归结束条件
for(var i=0;i<size;i++){
if(arr[i-1]>arr[i]){ //比较大小,交换
var temp=arr[i];
arr[i]=arr[i-1];
arr[i-1]=temp;
}
}
bullsort(arr,size-1); //递归调用
}
- 因为需要有动画效果和时序的问题,加入时间控制修改为:
function bullsort(arr,size){
if(size<2){d3.timeout(()=>complete(1),200);return;}//递归结束条件,排序结束
var i=0;
const timer = d3.interval(() =>
{
d3.timeout(()=>complete(size),200);//将已经排好的矩形变为橘色
if (i<size-1)
{
i=i+1;
compare(i-1, i); //交换动画
}
if(i>=size-1)
{
timer.stop();
bullsort(arr,size-1); //递归调用原函数
}
},1000);
使用d3.interval(function ,time)循环定时器,会在参数二指定的时间到达时持续运行。体现为影响冒泡是两两比较交换后,进行下一个比较之间暂停的时间。
调用时:使用bullsort(data,data.length);
每递归一遍,则排好一个数,在控制台打印信息如下所示:已经排好最大的数,可以在控制台看到数组变化的情况。
三、排序的动画
compare函数的实现:
compare函数传进去两个参数key1,key2。通过选择id的方法,选择比较的数的矩形,例如:
svg
.select(`#rect${key1}`)
.transition()
.duration(100)
.style('fill', 'green');
将两两比较的矩形从初始的skyblue的颜色变为green。
比较数值的大小,若前面的数大于后面的数,则前一个矩形右移,后一个矩形左移:
if (data[key1] > data[key2]) {
// 交换值
[data[key1], data[key2]] = [data[key2], data[key1]];
move_left(key2);
move_right(key1);
min = key2;
}
记录小值min,小值恢复初始的颜色skyblue:
svg.select(`#rect${min}`).style('fill', 'skyblue');
矩形左移或者右移时,改变的是x的位置和它对应的id,需要加入.transition()产生动画效果。
对于左移的矩形,改变如下(key+1):
.transition()
.duration(600)
.attr('x', (key + 1) * (rectWidth + rectGap))
.attr('id', `rect${key + 1}`);
对于右移的矩形,改变如下(key-1):
.transition()
.duration(600)
.attr('x', (key - 1) * (rectWidth + rectGap))
.attr('id', `rect${key -1 }`);
动画效果如下所示:65>34,已经比较出结果,65的矩形将要往后移,34的矩形将要往前移。34的矩形正由绿色转为蓝色。
主要函数调用为:先对画布初始化,产生矩形效果等。再间隔一定时间后进行冒泡排序。
init();
d3.timeout(()=>bullsort(data,data.length),2500);
四、排一遍将排好的矩形变为橘色。
编写compete函数,传入id,改变其颜色:
svg.select(`#rect${key}`).style('fill', 'orange');
因为需要在每一遍结束后将排好的矩形标记,所以在比较交换之前加入d3.timeout(()=>complete(size),200);,将上一个排好的矩形改变其颜色,并产生视觉上的时序效果。
排序结束后效果如下:
如有完整代码需求,私信发邮箱号哈