基于 HT 实现锅炉火焰动画

前言

  本文介绍的是用 HT 驱动 Canvas 实现的一个锅炉的可视化模型,目的在于以一种可视化的方式随时观测炉内燃烧情况。

  
代码实现

  代码的主体部分是锅炉矢量图,锅炉火焰的数据绑定以及用 Animation 插件实现炉内火焰的动画。首先要生成数据容器和拓扑组件并将其添加到 body 中 。

dataModel = new ht.DataModel();                    
graphView = new ht.graph.GraphView(dataModel);    
view = graphView.getView();
document.body.appendChild(view);

  首先我们先来生成底部的动态火焰效果,第一步我们先注册图片信息:

var image = [];                                            // 这里加入图片的文件名
for(var i = 0; i < image.length; ++i) {
    ht.Default.setImage('fireNum' + i, image[i]);  // 这里图片和 html 在同一路径下,如不在同一路径 ,加上前缀路径名  		
}

  然后要实现静态火焰图片的动态效果,无非就是将图片连续循环播放,于是需要动态改变的就是图片的文件名了,于是火焰图片的数据绑定如下:(将这段代码加入到锅炉外观的注册代码中)

{
    type: 'image',
    name: {
     func: function(data) {return data.a('imgNum');}  // 绑定了一个方法,用以动态改变图片的 name 属性值
   },
    rect: [50, 325, 450, 280]   // 设置火焰图片的位置和大小
}

    要用 Animation 实现实现动画效果首先必须引入 ht-animation.js 文件:

<script src = "lib/ht-animation.js"></script>

    然后数据模型调用 enableAnimation(interval) 启动动画定时器,让节点实现 Animation

dataModel.enableAnimation();
node.setAnimation({
        flash: {                                     // 自定义的任意方法名
            from: 0,                                 // 表示参数的开始值,从 0 开始
            to: image.length - 1,                    // 到 image.length - 1 结束
            onUpdate: function(value) {              // 回调函数,动画的每一帧都会回调此函数。
                this.a('imgNum', 'fireNum' + value); // 改变图片的文件名    
            },
            frames: 69,        // 动画的帧数,等于参数变化范围 - 1 (获得的参数刚好是整数),使得每一张图片都会被显示
            easing: 'Linear',  // 动画的方式,这里采用线性改变(保证参数刚好是整数)
            repeat: true        // 上述过程是否重复
        },
        start: ["flash"]       // 指定要启动的动画,里只定义了一个名为 flash 的动画,事实上,你可以定义任意多个
});

 

 接下来我们把美工提供的锅炉外观信息注册成图片 fire ,并将火焰图片信息注册进锅炉外观

ht.Default.setImage('fire', {
      "width": 543,
      "height": 639,
      "comps": [
     {
     "type": "shape",
     "background": "#7f7f7f",
     "shadowColor": "#1ABC9C",
     "rotation": 3.14159,
     "points": [
       17.90813,
       17.93993,
        17.90813,
        319.18021,
        141.34629,
        415.11661,
       141.34629,
       620.42049,
       401.01413,
       620.42049,
       401.01413,
       415.11661,
       525.09187,
       319.18021,
        525.09187,
       17.93993,
       17.90813,
       17.93993,
       17.90813,
       17.93993
     ]
    },        
      {
        "type": "shape",
        "background": "#999999",
        "shadowColor": "#1ABC9C",
        "rotation": 3.14159,
        "points": [
          58.20141,
          17.93993,
          58.20141,
          319.18021,
          161.81272,
          415.11661,
          161.81272,
          620.42049,
          379.90813,
          620.42049,
          379.90813,
          415.11661,
          483.51943,
          319.18021,
          483.51943,
          17.93993,
          58.20141,
          17.93993,
          58.20141,
          17.93993
        ]
      },
      {
        "type": "shape",
        "background": "#b2b2b2",
        "shadowColor": "#1ABC9C",
        "rotation": 3.14159,
        "points": [
          127.91519,
          17.93993,
          127.91519,
          319.18021,
          197.62898,
          415.11661,
          197.62898,
          620.42049,
          346.0106,
          620.42049,
          346.0106,
          415.11661,
          415.72438,
          319.18021,
          415.72438,
          17.93993,
          127.91519,
          17.93993,
          127.91519,
          17.93993
        ]
        },
        {
          "type": "shape",
          "background": "#cccccc",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            209.78092,
            17.93993,
            209.78092,
            319.18021,
            241.12014,
            415.11661,
            241.12014,
            620.42049,
            304.43816,
            620.42049,
            304.43816,
            415.11661,
            333.85866,
            319.18021,
            333.85866,
            17.93993,
            209.78092,
            17.93993,
            209.78092,
            17.93993
          ]
        },
        {
          "type": "shape",
          "borderWidth": 1.27915,
          "borderColor": "#000000",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            17.90813,
            17.93993,
            17.90813,
            319.18021,
            141.34629,
            415.11661,
            141.34629,
            620.42049,
            401.01413,
            620.42049,
            401.01413,
            415.11661,
            525.09187,
            319.18021,
            525.09187,
            17.93993,
            17.90813,
            17.93993
          ]
        },
        {
          "type": "shape",
          "borderWidth": 1.27915,
          "borderColor": "#7f7f7f",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            141.98587,
            223.24382,
            401.65371,
            223.24382
          ]
        },
        {
          "type": "shape",
          "borderWidth": 1.27915,
          "borderColor": "#7f7f7f",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            17.90813,
            319.18021,
            525.09187,
            319.18021
          ]
        },
        {
          "type": "shape",
          "borderWidth": 1.27915,
          "borderColor": "#7f7f7f",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            264.14488,
            291.67845,
            264.14488,
            223.24382
          ]
        },
        {
          "type": "shape",
          "background": "#336666",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            31.9788,
            606.9894,
            511.66078,
            606.9894,
            511.66078,
            333.25088,
            31.9788,
            333.25088,
            31.9788,
            606.9894,
            31.9788,
            606.9894
          ]
        },
        {
          "type": "shape",
          "borderWidth": 1.27915,
          "borderColor": "#000000",
          "shadowColor": "#1ABC9C",
          "rotation": 3.14159,
          "points": [
            31.9788,
            606.9894,
            511.66078,
            606.9894,
            511.66078,
            333.25088,
            31.9788,
            333.25088,
            31.9788,
            606.9894,
            31.9788,
            606.9894
          ]
        },
        {
  			type: 'image',
   			name: {
     				func: function(data) {return data.a('imgNum');}  // 绑定了一个方法,用以动态改变图片的 name 属性值
   				},
   			rect: [50,325,450,280]   // 设置火焰图片的位置和大小
		}
});

   而后要创建一个节点将图片 fire 添加进节点,并将节点添加进数据容器:

node = new ht.Node();
node.setImage('fire');
node.a({
    'imgNum': 'fireNum0' 
});
node.setPosition(200, 200);      
dataModel.add(node);

    至此,模拟锅炉燃烧的模式就全部搭建完成,主体部分实际上是锅炉矢量图,锅炉火焰图的数据绑定以及用 Animation 插件实现炉内火焰的动画。
总结:这个 Demo 主要就是用 Animation 插件实现动画效果,其中 Animation 中有很多的参数,这里我们没有指定 property 和 accessType,因为图片名参数 imgNum 不是单纯的数字类型,    所以我们就用  onUpdate 回调函数,在动画的每一帧都动态的改变 imgNum 的值,使得其不断更换图片从而在视觉上造成一种动画的效果。
   

posted @ 2018-08-09 11:54  htxzs  阅读(506)  评论(0编辑  收藏  举报