乡下人产国偷v产偷v自拍,国产午夜片在线观看,婷婷成人亚洲综合国产麻豆,久久综合给合久久狠狠狠9

  • <output id="e9wm2"></output>
    <s id="e9wm2"><nobr id="e9wm2"><ins id="e9wm2"></ins></nobr></s>

    • 分享

      基于HTML5 Canvas實現(xiàn)工控2D葉輪旋轉(zhuǎn)

       昵稱10504424 2015-10-10

      之前在拓?fù)?/a>上的應(yīng)用都是些靜態(tài)的圖元,今天我們將在拓?fù)渖显O(shè)計一個會動的圖元——葉輪旋轉(zhuǎn)。

      http://www./guide/guide/core/serialization/examples/example_exportimport.html

      我們先來看下這個葉輪模型長什么樣

       

      從模型上看,這個葉輪模型有三個葉片,每一個葉片都是不規(guī)則圖形,顯然無法用上我們HT for Web的基礎(chǔ)圖形來拼接,那么我們該怎么做呢?很簡單,在HT for Web中提供了自定義圖形的方案,我們可以通過自定義圖形來繪制像葉片這種不規(guī)則圖形。

      在繪制葉片之前,我們得先來了解下HT for Web的自定義圖形繪制的基本知識:

      繪制自定義圖形需要制定矢量類型為shape,并通過points的Array數(shù)組指定每個點信息, points以[x1, y1, x2, y2, x3, y3, ...]的方式存儲點坐標(biāo)。曲線的多邊形可通過segments的Array數(shù)組來描述, segment以[1, 2, 1, 3 ...]的方式描述每個線段:

      1: moveTo,占用1個點信息,代表一個新路徑的起點

      2: lineTo,占用1個點信息,代表從上次最后點連接到該點

      3: quadraticCurveTo,占用2個點信息,第一個點作為曲線控制點,第二個點作為曲線結(jié)束點

      4: bezierCurveTo,占用3個點信息,第一和第二個點作為曲線控制點,第三個點作為曲線結(jié)束點

       

      5: closePath,不占用點信息,代表本次路徑繪制結(jié)束,并閉合到路徑的起始點

      對比閉合多邊形除了設(shè)置segments參數(shù)外,還可以設(shè)置closePath屬性: * closePath獲取和設(shè)置多邊形是否閉合,默認(rèn)為false,對閉合直線采用這種方式,無需設(shè)置segments參數(shù)。

      好了,那么接下來我們開始設(shè)計葉片了

       

      復(fù)制代碼
      ht.Default.setImage('vane', {
          width: 97,
          height: 106,
          comps: [
              {
                  type: 'shape',
                  points: [
                      92, 67,
                      62, 7,
                      0, 70,
                      60, 98
                  ],
                  segments: [
                      1, 2, 2, 2
                  ],
                  background : 'red'
              }
          ]
      });
      復(fù)制代碼

      我們在矢量中定義了4個頂點,并且將這4個頂點通過直線勾勒出葉片的大致形狀,雖然有些抽象,但是,接下來將會通過增加控制點和改變segment參數(shù)來讓這個葉片發(fā)生蛻變。

      首先我們通過bezierCurveTo方式向第一個和第二個頂點之間的線段添加兩個控制點,從而繪制出曲線,以下是points及segments屬性:

      復(fù)制代碼
      points: [
          92, 67,
          93, 35, 78, 0, 62, 7,
          0, 70,
          60, 98
      ],
      segments: [
          1, 4, 2, 2
      ]
      復(fù)制代碼

      這時候與上一個圖相比較,有一條邊一件有些弧度了,那么接下來就來處理第二條邊和第三條邊

                    

      復(fù)制代碼
      points: [
          92, 67,
          93, 35, 78, 0, 62, 7,
          29, 13, 4, 46, 0, 70,
          28, 53, 68, 60, 60, 98
      ],
      segments: [
          1, 4, 4, 4
      ]
      復(fù)制代碼

      看吧,現(xiàn)在是不是有模有樣了,現(xiàn)在葉片已經(jīng)有了,那么接下來要做的就是使用三個這樣的葉片拼接成一個葉輪。

      將已有的資源拼接在一起需要用到矢量中的image類型類定義新的矢量,具體的使用方法如下:

      復(fù)制代碼
      ht.Default.setImage('impeller', {
          width: 166,
          height: 180.666,
          comps : [
              {
                  type: 'image',
                  name: 'vane',
                  rect: [0, 0, 97, 106]
              },
              {
                  type: 'image',
                  name: 'vane',
                  rect: [87.45, 26.95, 97, 106],
                  rotation: 2 * Math.PI / 3
              },
              {
                  type: 'image',
                  name: 'vane',
                  rect: [20.45, 89.2, 97, 106],
                  rotation: 2 * Math.PI / 3 * 2
              }
          ]
      });
      復(fù)制代碼

      在代碼中,我們定義了三個葉片,并且對第二個和第三個葉片做了旋轉(zhuǎn)和定位的處理,讓這三個葉片排布組合成一個葉輪來,但是怎么能讓葉輪中間空出一個三角形呢,這個問題解決起來不難,我們只需要在葉片的points屬性上再多加一個頂點,就可以填充這個三角形了,代碼如下:

      復(fù)制代碼
      points: [
          92, 67,
          93, 35, 78, 0, 62, 7,
          29, 13, 4, 46, 0, 70,
          28, 53, 68, 60, 60, 98,
          97, 106
      ],
      segments: [
          1, 4, 4, 4, 2
      ]
      復(fù)制代碼

       

      在points屬性上添加了一個頂點后,別忘了在segments數(shù)組的最后面添加一個描述,再來看看最終的效果:

      到這個葉輪的資源就做好了,那么接下來就是要讓這個葉輪旋轉(zhuǎn)起來了,我們先來分析下:

      要讓葉輪旋轉(zhuǎn)起來,其實原理很簡單,我們只需要設(shè)置rotation屬性就可以實現(xiàn)了,但是這個rotation屬性只有在不斷的變化中,才會讓葉輪旋轉(zhuǎn)起來,所以這個時候就需要用到定時器了,通過定時器來不斷地設(shè)置rotation屬性,讓葉輪動起來。

      恩,好像就是這樣子的,那么我們來實現(xiàn)一下:

      首先是創(chuàng)建一個節(jié)點,并設(shè)置其引用的image為impeller,再將其添加到DataModel,令節(jié)點在拓?fù)渲酗@示出來:

      var node = new ht.Node();
      node.setSize(166, 181);
      node.setPosition(400, 400);
      node.setImage('impeller');
      dataModel.add(node);

      接下來就是添加一個定時器了:

      復(fù)制代碼
      window.setInterval(function() {
          var rotation = node.getRotation() + Math.PI / 10;
          if (rotation > Math.PI * 2) {
              rotation -= Math.PI * 2;
          }
          node.setRotation(rotation);
      }, 40);
      復(fù)制代碼

      OK了,好像就是這個效果,但是當(dāng)你選中這個節(jié)點的時候,你會發(fā)現(xiàn)這個節(jié)點的邊框在不停的閃動,看起來并不是那么的舒服,為什么會出現(xiàn)這種情況呢?原因很簡單,當(dāng)設(shè)置了節(jié)點的rotation屬性后,節(jié)點的顯示區(qū)域就會發(fā)生變化,這個時候節(jié)點的寬高自然就發(fā)生的變化,其邊框也自然跟著改變。

      還有,在很多情況下,節(jié)點的rotation屬性及寬高屬性會被當(dāng)成業(yè)務(wù)屬性來處理,不太適合被實時改變,那么我們該如何處理,才能在不不改變節(jié)點的rotation屬性的前提下令葉輪轉(zhuǎn)動起來呢?

      矢量中,好像有數(shù)據(jù)綁定的功能,在手冊中是這么介紹的:

      綁定的格式很簡單,只需將以前的參數(shù)值用一個帶func屬性的對象替換即可,func的內(nèi)容有以下幾種類型:

      1. function類型,直接調(diào)用該函數(shù),并傳入相關(guān)Data和view對象,由函數(shù)返回值決定參數(shù)值,即func(data, view);調(diào)用。

      2. string類型:

          2.1 style@***開頭,則返回data.getStyle(***)值,其中***代表style的屬性名。

          2.2 attr@***開頭,則返回data.getAttr(***)值,其中***代表attr的屬性名。

          2.3 field@***開頭,則返回data.***值,其中***代表data的屬性名。

          2.4 如果不匹配以上情況,則直接將string類型作為data對象的函數(shù)名調(diào)用data.***(view),返回值作為參數(shù)值。

      除了func屬性外,還可設(shè)置value屬性作為默認(rèn)值,如果對應(yīng)的func取得的值為undefined或null時,則會采用value屬性定義的默認(rèn)值。 例如以下代碼,如果對應(yīng)的Data對象的attr屬性stateColor為undefined或null時,則會采用yellow顏色:

      color: {
          func: 'attr@stateColor',
          value: 'yellow'
      }

      數(shù)據(jù)綁定的用法已經(jīng)介紹得很清楚了,我們不妨先試試綁定葉片的背景色吧,看下好不好使。在矢量vane中的background屬性設(shè)置成數(shù)據(jù)綁定的形式,代碼如下:

      background : {
          value : 'red',
          func : 'attr@vane_background'
      }

      在沒有設(shè)置vane_background屬性的時候,令其去red為默認(rèn)值,那么接下來我們來定義下vane_background屬性為blue,看看葉輪會不會變成藍(lán)色:

      node.setAttr('vane_background', ‘blue');

      看下效果:

      果然生效了,這下好了,我們就可以讓葉輪旋轉(zhuǎn)變得更加完美了,來看看具體該這么做。

      首先,我們先在節(jié)點上定義一個自定義屬性,名字為:impeller_rotation

      node.setAttr('impeller_rotation', 0);

      然后再定義一個名字為rotate_impeller的矢量,并將rotation屬性綁定到節(jié)點的impeller_rotation上:

      復(fù)制代碼
      ht.Default.setImage('rotate_impeller', {
          width : 220,
          height : 220,
          comps : [
              {
                  type : 'image',
                  name : 'impeller',
                  rect : [27, 20, 166, 180.666],
                  rotation : {
                      func : function(data) { 
                          return data.getAttr('impeller_rotation'); 
                      }
                  }
              }
          ]
      });
      復(fù)制代碼

      這時候我們在定時器中修改節(jié)點的rotation屬性改成修改自定義屬性impeller_rotation就可以讓節(jié)點中的葉輪旋轉(zhuǎn)起來,并且不會影響到節(jié)點自身的屬性,這就是我們想要的效果。

      在2D上可以實現(xiàn),在3D上一樣可以實現(xiàn),下一章我們就來講講葉輪旋轉(zhuǎn)在3D上的應(yīng)用,今天就先到這里,下面附上今天Demo的源碼,有什么問題歡迎大家咨詢。

      http://www./guide/guide/core/serialization/examples/example_exportimport.html

       

      復(fù)制代碼
      ht.Default.setImage('vane', {
          width : 97,
          height : 106,
          comps : [
              {
                  type : 'shape',
                  points : [
                      92, 67,
                      93, 35, 78, 0, 62, 7,
                      29, 13, 4, 46, 0, 70,
                      28, 53, 68, 60, 60, 98,
                      97, 106
                  ],
                  segments : [
                      1, 4, 4, 4, 2
                  ],
                  background : {
                      value : 'red',
                      func : 'attr@vane_background'
                  }
              }
          ]
      });
      
      ht.Default.setImage('impeller', {
          width : 166,
          height : 180.666,
          comps : [
              {
                  type : 'image',
                  name : 'vane',
                  rect : [0, 0, 97, 106]
              },
              {
                  type : 'image',
                  name : 'vane',
                  rect : [87.45, 26.95, 97, 106],
                  rotation : 2 * Math.PI / 3
              },
              {
                  type : 'image',
                  name : 'vane',
                  rect : [20.45, 89.2, 97, 106],
                  rotation : 2 * Math.PI / 3 * 2
              }
          ]
      });
      
      ht.Default.setImage('rotate_impeller', {
          width : 220,
          height : 220,
          comps : [
              {
                  type : 'image',
                  name : 'impeller',
                  rect : [27, 20, 166, 180.666],
                  rotation : {
                      func : function(data) {
                          return data.getAttr('impeller_rotation');
                      }
                  }
              }
          ]
      });
      
      function init() {
          var dataModel = new ht.DataModel();
      
          var graphView = new ht.graph.GraphView(dataModel);
          var view = graphView.getView();
          view.className = "view";
          document.body.appendChild(view);
      
          var node = new ht.Node();
          node.setSize(220, 220);
          node.setPosition(200, 400);
          node.setImage('rotate_impeller');
          node.setAttr('impeller_rotation', 0);
          node.setAttr('vane_background', 'blue');
          dataModel.add(node);
      
          var node1 = new ht.Node();
          node1.setSize(166, 181);
          node1.setPosition(500, 400);
          node1.setImage('impeller');
          dataModel.add(node1);
      
          window.setInterval(function() {
              var rotation = node.a('impeller_rotation') + Math.PI / 10;
              if (rotation > Math.PI * 2) {
                  rotation -= Math.PI * 2;
              }
              node.a('impeller_rotation', rotation);
              node1.setRotation(rotation);
      
          }, 40);
      }
      復(fù)制代碼

       

        本站是提供個人知識管理的網(wǎng)絡(luò)存儲空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點。請注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點擊一鍵舉報。
        轉(zhuǎn)藏 分享 獻(xiàn)花(0

        0條評論

        發(fā)表

        請遵守用戶 評論公約

        類似文章 更多