• 企业400电话
  • 微网小程序
  • AI电话机器人
  • 电商代运营
  • 全 部 栏 目

    企业400电话 网络优化推广 AI电话机器人 呼叫中心 网站建设 商标✡知产 微网小程序 电商运营 彩铃•短信 增值拓展业务
    HTML5 3D衣服摇摆动画特效

    这又是一款基于HTML5 Canvas的3D动画杰作,它是一个可以随风飘动的3D衣服摇摆动画特效,非常逼真。当我们将鼠标滑过衣服时,衣服将会出现摇摆的动画,点击鼠标时,衣服将会更加剧烈地摆动。

    在线演示  源码下载

    HTML代码

    XML/HTML Code复制内容到剪贴板
    1. <div style="width:500px;margin:10px auto">  
    2.  <canvas id="cv" width="480" height="300"></canvas>  
    3.  <p>"3D on 2D Canvas" demo</p>  
    4.  <p>move cursor to pan / click to swing</p>  
    5. </div>  

    P3D库JS代码,主要用来处理3D效果的

    JavaScript Code复制内容到剪贴板
    1. window.P3D = {   
    2.  texture: null,   
    3.  g: null  
    4. };   
    5.   
    6. P3D.clear = function(f, w, h) {   
    7.  var g = this.g;   
    8.  g.beginPath();   
    9.  g.fillStyle = f;   
    10.  g.fillRect(0, 0, w, h);   
    11.   
    12. }   
    13.   
    14. P3D.num_cmp = function(a,b){return a-b;}   
    15.   
    16. P3D.drawTriangle = function(poss, uvs, shade_clr) {   
    17.  var w = this.texture.width;   
    18.  var h = this.texture.height;   
    19.   
    20.  var g = this.g;   
    21.   
    22.  var vAd = [ poss[1].x - poss[0].x , poss[1].y - poss[0].y ];   
    23.  var vBd = [ poss[2].x - poss[0].x , poss[2].y - poss[0].y ];   
    24.   
    25.  var vA = [ uvs[1].u - uvs[0].u , uvs[1].v - uvs[0].v ];   
    26.  var vB = [ uvs[2].u - uvs[0].u , uvs[2].v - uvs[0].v ];   
    27.   
    28.  vA[0] *= w;   
    29.  vA[1] *= h;   
    30.   
    31.  vB[0] *= w;   
    32.  vB[1] *= h;   
    33.   
    34.  var m = new M22();   
    35.  m._11 = vA[0];   
    36.  m._12 = vA[1];   
    37.  m._21 = vB[0];   
    38.  m._22 = vB[1];   
    39.   
    40.  var im = m.getInvert();   
    41.  if (!im) return false;   
    42.   
    43.  var a = im._11 * vAd[0] + im._12 * vBd[0];   
    44.  var b = im._21 * vAd[0] + im._22 * vBd[0];   
    45.   
    46.  var c = im._11 * vAd[1] + im._12 * vBd[1];   
    47.  var d = im._21 * vAd[1] + im._22 * vBd[1];   
    48.   
    49.  var wu = uvs[0].u * w;   
    50.  var hv = uvs[0].v * h;   
    51.  var du = wu * a + hv * b;   
    52.  var dv = wu * c + hv * d;   
    53.   
    54.  g.save();   
    55.   
    56.  g.beginPath();   
    57.  g.moveTo(poss[0].x, poss[0].y);   
    58.  g.lineTo(poss[1].x, poss[1].y);   
    59.  g.lineTo(poss[2].x, poss[2].y);   
    60.  g.clip();   
    61.   
    62.  g.transform(a, c, b, d, poss[0].x - du, poss[0].y - dv);   
    63.   
    64.  // bounds   
    65.  var bx = [wu, wu+vA[0], wu+vB[0]];   
    66.  var by = [hv, hv+vA[1], hv+vB[1]];   
    67.   
    68.  bx.sort(P3D.num_cmp);   
    69.  by.sort(P3D.num_cmp);   
    70.   
    71.  var bw = bx[2] - bx[0];   
    72.  var bh = by[2] - by[0];   
    73.   
    74.  if ((bx[0]+bw) <= (w-1)) bw++;   
    75.  if ((by[0]+bh) <= (h-1)) bh++;   
    76.  if (bx[0] >= 1) {bx[0]--; bw++;}   
    77.  if (by[0] >= 1) {by[0]--; bh++;}   
    78.   
    79.  g.drawImage(this.texture, bx[0], by[0], bw, bh, bx[0], by[0], bw, bh);   
    80.   
    81.  if (shade_clr) {   
    82.   g.fillStyle = shade_clr;   
    83.   g.fillRect(bx[0], by[0], bw, bh);   
    84.  }   
    85.   
    86.  g.restore();   
    87.   
    88.  return true;   
    89. }   
    90.   
    91. P3D.drawTestByIndexBuffer = function(pos_buf, ix_buf, culling) {   
    92.  var g = this.g;   
    93.   
    94.  if ((ix_buf.length%3) != 0)   
    95.   throw "invalid index buffer length!";   
    96.   
    97.  var len = ix_buf.length/3;   
    98.   
    99.  var i, ibase, vbase;   
    100.  var poss = [{},{},{}];   
    101.  g.strokeWidth = 1;   
    102.  for (i = 0, ibase = 0;i < len;++i)   
    103.  {   
    104.   vbase = ix_buf[ibase++] << 2;   
    105.   poss[0].x = pos_buf[vbase++];   
    106.   poss[0].y = pos_buf[vbase  ];   
    107.   
    108.   vbase = ix_buf[ibase++] << 2;   
    109.   poss[1].x = pos_buf[vbase++];   
    110.   poss[1].y = pos_buf[vbase  ];   
    111.   
    112.   vbase = ix_buf[ibase++] << 2;   
    113.   poss[2].x = pos_buf[vbase++];   
    114.   poss[2].y = pos_buf[vbase  ];   
    115.   
    116.   // z component of cross product < 0 ?   
    117.   
    118.   var Ax = poss[1].x - poss[0].x;   
    119.   var Ay = poss[1].y - poss[0].y;   
    120.   var Cx = poss[2].x - poss[1].x;   
    121.   var Cy = poss[2].y - poss[1].y;   
    122.   
    123.   var cull = ( (((Ax * Cy) - (Ay * Cx))*culling) < 0);   
    124.   
    125.   g.beginPath();   
    126.   g.strokeStyle = cull ? "#592" : "#0f0";   
    127.   g.moveTo(poss[0].x, poss[0].y);   
    128.   g.lineTo(poss[1].x, poss[1].y);   
    129.   g.lineTo(poss[2].x, poss[2].y);   
    130.   g.lineTo(poss[0].x, poss[0].y);   
    131.   g.stroke();   
    132.  }   
    133. }   
    134.   
    135. P3D.drawByIndexBuffer = function(pos_buf, ix_buf, tx_buf, culling, z_clip) {   
    136.  var w, h;   
    137.  var color_polygon = !this.texture;   
    138.  if (this.texture) {   
    139.   w = this.texture.width;   
    140.   h = this.texture.height;   
    141.  }   
    142.   
    143.  var g = this.g;   
    144.  var m = new M22();   
    145.   
    146.  if (!culling) culling = 0;   
    147.   
    148.  if ((ix_buf.length%3) != 0)   
    149.   throw "invalid index buffer length!";   
    150.   
    151.  var i, ibase, vbase, tbase, poss = [{},{},{}];   
    152.  var len = ix_buf.length/3;   
    153.  var uv_0u, uv_0v, uv_1u, uv_1v, uv_2u, uv_2v;   
    154.   
    155.  for (i = 0, ibase = 0;i < len;++i)   
    156.  {   
    157.   tbase = ix_buf[ibase++] << 1   
    158.   vbase = tbase << 1;   
    159.   poss[0].x = pos_buf[vbase++]; uv_0u = tx_buf[tbase++];   
    160.   poss[0].y = pos_buf[vbase++]; uv_0v = tx_buf[tbase];   
    161.   if (z_clip && (pos_buf[vbase] < 0 || pos_buf[vbase] > 1)) {ibase += 2; continue;}   
    162.   
    163.   tbase = ix_buf[ibase++] << 1   
    164.   vbase = tbase << 1;   
    165.   poss[1].x = pos_buf[vbase++]; uv_1u = tx_buf[tbase++];   
    166.   poss[1].y = pos_buf[vbase++]; uv_1v = tx_buf[tbase];   
    167.   if (z_clip && (pos_buf[vbase] < 0 || pos_buf[vbase] > 1)) {++ibase; continue;}   
    168.   
    169.   tbase = ix_buf[ibase++] << 1   
    170.   vbase = tbase << 1;   
    171.   poss[2].x = pos_buf[vbase++]; uv_2u = tx_buf[tbase++];   
    172.   poss[2].y = pos_buf[vbase++]; uv_2v = tx_buf[tbase];   
    173.   if (z_clip && (pos_buf[vbase] < 0 || pos_buf[vbase] > 1)) {continue;}   
    174.   
    175.   var vAd = [ poss[1].x - poss[0].x , poss[1].y - poss[0].y ];   
    176.   var vBd = [ poss[2].x - poss[0].x , poss[2].y - poss[0].y ];   
    177.   
    178.   var vCd = [ poss[2].x - poss[1].x , poss[2].y - poss[1].y ];   
    179.   
    180.   // z component of cross product < 0 ?   
    181.   if( (((vAd[0] * vCd[1]) - (vAd[1] * vCd[0]))*culling) < 0)   
    182.    continue;   
    183.   
    184.   if (color_polygon) {   
    185.    g.fillStyle = uv_0u;   
    186.   
    187.    g.beginPath();   
    188.    g.moveTo(poss[0].x, poss[0].y);   
    189.    g.lineTo(poss[1].x, poss[1].y);   
    190.    g.lineTo(poss[2].x, poss[2].y);   
    191.    g.fill();   
    192.    continue;   
    193.   }   
    194.   
    195.   var vA = [ uv_1u - uv_0u , uv_1v - uv_0v ];   
    196.   var vB = [ uv_2u - uv_0u , uv_2v - uv_0v ];   
    197.   
    198.   vA[0] *= w;   
    199.   vA[1] *= h;   
    200.   
    201.   vB[0] *= w;   
    202.   vB[1] *= h;   
    203.   
    204.   m._11 = vA[0];   
    205.   m._12 = vA[1];   
    206.   m._21 = vB[0];   
    207.   m._22 = vB[1];   
    208.   
    209.   var im = m.getInvert();   
    210.   if (!im) { continue;}   
    211.   
    212.   var a = im._11 * vAd[0] + im._12 * vBd[0];   
    213.   var b = im._21 * vAd[0] + im._22 * vBd[0];   
    214.   
    215.   var c = im._11 * vAd[1] + im._12 * vBd[1];   
    216.   var d = im._21 * vAd[1] + im._22 * vBd[1];   
    217.   
    218.   var wu = uv_0u * w;   
    219.   var hv = uv_0v * h;   
    220.   var du = wu * a + hv * b;   
    221.   var dv = wu * c + hv * d;   
    222.   
    223.   g.save();   
    224.   
    225.   g.beginPath();   
    226.   g.moveTo(poss[0].x, poss[0].y);   
    227.   g.lineTo(poss[1].x, poss[1].y);   
    228.   g.lineTo(poss[2].x, poss[2].y);   
    229.   g.clip();   
    230.   g.transform(a, c, b, d, poss[0].x - du, poss[0].y - dv);   
    231.   
    232.   // bounds   
    233.   var bx = [wu, wu+vA[0], wu+vB[0]];   
    234.   var by = [hv, hv+vA[1], hv+vB[1]];   
    235.   
    236.   bx.sort(P3D.num_cmp);   
    237.   by.sort(P3D.num_cmp);   
    238.   
    239.   var bw = bx[2] - bx[0];   
    240.   var bh = by[2] - by[0];   
    241.   
    242.   if ((bx[0]+bw) <= (w-1)) bw++;   
    243.   if ((by[0]+bh) <= (h-1)) bh++;   
    244.   if (bx[0] >= 1) {bx[0]--; bw++;}   
    245.   if (by[0] >= 1) {by[0]--; bh++;}   
    246.   
    247.   g.drawImage(this.texture, bx[0], by[0], bw, bh, bx[0], by[0], bw, bh);   
    248. /*  
    249.   if (shade_clr) {  
    250.    g.fillStyle = shade_clr;  
    251.    g.fillRect(bx[0], by[0], bw, bh);  
    252.   }  
    253. */  
    254.   g.restore();   
    255.   
    256.  }   
    257.   
    258. }   
    259.   
    260. function Vec3(_x, _y, _z)   
    261. {   
    262.  this.x = _x || 0;   
    263.  this.y = _y || 0;   
    264.  this.z = _z || 0;   
    265. }   
    266.   
    267. Vec3.prototype = {   
    268.  zero: function() {   
    269.   this.x = this.y = this.z = 0;   
    270.  },   
    271.   
    272.  sub: function(v) {   
    273.   this.x -= v.x;   
    274.   this.y -= v.y;   
    275.   this.z -= v.z;   
    276.   
    277.   return this;   
    278.  },   
    279.   
    280.  add: function(v) {   
    281.   this.x += v.x;   
    282.   this.y += v.y;   
    283.   this.z += v.z;   
    284.   
    285.   return this;   
    286.  },   
    287.   
    288.  copyFrom: function(v) {   
    289.   this.x = v.x;   
    290.   this.y = v.y;   
    291.   this.z = v.z;   
    292.   
    293.   return this;   
    294.  },   
    295.   
    296.  norm:function() {   
    297.   return Math.sqrt(this.x*this.x + this.y*this.y + this.z*this.z);   
    298.  },   
    299.   
    300.  normalize: function() {   
    301.   var nrm = Math.sqrt(this.x*this.x + this.y*this.y + this.z*this.z);   
    302.   if (nrm != 0)   
    303.   {   
    304.    this.x /= nrm;   
    305.    this.y /= nrm;   
    306.    this.z /= nrm;   
    307.   }   
    308.   return this;   
    309.  },   
    310.   
    311.  smul: function(k) {   
    312.   this.x *= k;   
    313.   this.y *= k;   
    314.   this.z *= k;   
    315.   
    316.   return this;   
    317.  },   
    318.   
    319.  dpWith: function(v) {   
    320.   return this.x*v.x + this.y*v.y + this.z*v.z;   
    321.  },   
    322.   
    323.  cp: function(v, w) {   
    324.   this.x = (w.y * v.z) - (w.z * v.y);   
    325.   this.y = (w.z * v.x) - (w.x * v.z);   
    326.   this.z = (w.x * v.y) - (w.y * v.x);   
    327.   
    328.   return this;   
    329.  },   
    330.   
    331.  toString: function() {   
    332.   return this.x + ", " + this.y + "," + this.z;   
    333.  }   
    334. }   
    335.   
    336. function M44(cpy)   
    337. {   
    338.  if (cpy)   
    339.   this.copyFrom(cpy);   
    340.  else {   
    341.   this.ident();   
    342.  }   
    343. }   
    344.   
    345. M44.prototype = {   
    346.  ident: function() {   
    347.      this._12 = this._13 = this._14 = 0;   
    348.   this._21 =       this._23 = this._24 = 0;   
    349.   this._31 = this._32 =       this._34 = 0;   
    350.   this._41 = this._42 = this._43 =       0;   
    351.   
    352.   this._11 = this._22 = this._33 = this._44 = 1;   
    353.   
    354.   return this;   
    355.  },   
    356.   
    357.  copyFrom: function(m) {   
    358.   this._11 = m._11;   
    359.   this._12 = m._12;   
    360.   this._13 = m._13;   
    361.   this._14 = m._14;   
    362.   
    363.   this._21 = m._21;   
    364.   this._22 = m._22;   
    365.   this._23 = m._23;   
    366.   this._24 = m._24;   
    367.   
    368.   this._31 = m._31;   
    369.   this._32 = m._32;   
    370.   this._33 = m._33;   
    371.   this._34 = m._34;   
    372.   
    373.   this._41 = m._41;   
    374.   this._42 = m._42;   
    375.   this._43 = m._43;   
    376.   this._44 = m._44;   
    377.   
    378.   return this;   
    379.  },   
    380.   
    381.  transVec3: function(out, x, y, z) {   
    382.   out[0] = x * this._11 + y * this._21 + z * this._31 + this._41;   
    383.   out[1] = x * this._12 + y * this._22 + z * this._32 + this._42;   
    384.   out[2] = x * this._13 + y * this._23 + z * this._33 + this._43;   
    385.   out[3] = x * this._14 + y * this._24 + z * this._34 + this._44;   
    386.  },   
    387.   
    388.  transVec3Rot: function(out, x, y, z) {   
    389.   out[0] = x * this._11 + y * this._21 + z * this._31;   
    390.   out[1] = x * this._12 + y * this._22 + z * this._32;   
    391.   out[2] = x * this._13 + y * this._23 + z * this._33;   
    392.  },   
    393.   
    394.  perspectiveLH: function(vw, vh, z_near, z_far) {   
    395.   this._11 = 2.0*z_near/vw;   
    396.   this._12 = 0;   
    397.   this._13 = 0;   
    398.   this._14 = 0;   
    399.   
    400.   this._21 = 0;   
    401.   this._22 = 2*z_near/vh;   
    402.   this._23 = 0;   
    403.   this._24 = 0;   
    404.   
    405.   this._31 = 0;   
    406.   this._32 = 0;   
    407.   this._33 = z_far/(z_far-z_near);   
    408.   this._34 = 1;   
    409.   
    410.   this._41 = 0;   
    411.   this._42 = 0;   
    412.   this._43 = z_near*z_far/(z_near-z_far);   
    413.   this._44 = 0;   
    414.   
    415.   return this;   
    416.  },   
    417.   
    418.  lookAtLH: function(aUp, aFrom, aAt) {   
    419.   var aX = new Vec3();   
    420.   var aY = new Vec3();   
    421.   
    422.   var aZ = new Vec3(aAt.x, aAt.y, aAt.z);   
    423.   aZ.sub(aFrom).normalize();   
    424.   
    425.   aX.cp(aUp, aZ).normalize();   
    426.   aY.cp(aZ, aX);   
    427.   
    428.   this._11 = aX.x;  this._12 = aY.x;  this._13 = aZ.x;  this._14 = 0;   
    429.   this._21 = aX.y;  this._22 = aY.y;  this._23 = aZ.y;  this._24 = 0;   
    430.   this._31 = aX.z;  this._32 = aY.z;  this._33 = aZ.z;  this._34 = 0;   
    431.   
    432.   this._41 = -aFrom.dpWith(aX);   
    433.   this._42 = -aFrom.dpWith(aY);   
    434.   this._43 = -aFrom.dpWith(aZ);   
    435.   this._44 = 1;   
    436.   
    437.      return this;   
    438.  },   
    439.   
    440.  mul: function(A, B) {   
    441.   this._11 = A._11*B._11  +  A._12*B._21  +  A._13*B._31  +  A._14*B._41;   
    442.   this._12 = A._11*B._12  +  A._12*B._22  +  A._13*B._32  +  A._14*B._42;   
    443.   this._13 = A._11*B._13  +  A._12*B._23  +  A._13*B._33  +  A._14*B._43;   
    444.   this._14 = A._11*B._14  +  A._12*B._24  +  A._13*B._34  +  A._14*B._44;   
    445.   
    446.   this._21 = A._21*B._11  +  A._22*B._21  +  A._23*B._31  +  A._24*B._41;   
    447.   this._22 = A._21*B._12  +  A._22*B._22  +  A._23*B._32  +  A._24*B._42;   
    448.   this._23 = A._21*B._13  +  A._22*B._23  +  A._23*B._33  +  A._24*B._43;   
    449.   this._24 = A._21*B._14  +  A._22*B._24  +  A._23*B._34  +  A._24*B._44;   
    450.   
    451.   this._31 = A._31*B._11  +  A._32*B._21  +  A._33*B._31  +  A._34*B._41;   
    452.   this._32 = A._31*B._12  +  A._32*B._22  +  A._33*B._32  +  A._34*B._42;   
    453.   this._33 = A._31*B._13  +  A._32*B._23  +  A._33*B._33  +  A._34*B._43;   
    454.   this._34 = A._31*B._14  +  A._32*B._24  +  A._33*B._34  +  A._34*B._44;   
    455.   
    456.   this._41 = A._41*B._11  +  A._42*B._21  +  A._43*B._31  +  A._44*B._41;   
    457.   this._42 = A._41*B._12  +  A._42*B._22  +  A._43*B._32  +  A._44*B._42;   
    458.   this._43 = A._41*B._13  +  A._42*B._23  +  A._43*B._33  +  A._44*B._43;   
    459.   this._44 = A._41*B._14  +  A._42*B._24  +  A._43*B._34  +  A._44*B._44;   
    460.   
    461.   return this;   
    462.  },   
    463.   
    464.  translate: function(x, y, z) {   
    465.   this._11 = 1;  this._12 = 0;  this._13 = 0;  this._14 = 0;   
    466.   this._21 = 0;  this._22 = 1;  this._23 = 0;  this._24 = 0;   
    467.   this._31 = 0;  this._32 = 0;  this._33 = 1;  this._34 = 0;   
    468.   
    469.   this._41 = x;  this._42 = y;  this._43 = z;  this._44 = 1;   
    470.   return this;   
    471.  },   
    472.   
    473.  transpose33: function() {   
    474.   var t;   
    475.   
    476.   t = this._12;   
    477.   this._12 = this._21;   
    478.   this._21 = t;   
    479.   
    480.   t = this._13;   
    481.   this._13 = this._31;   
    482.   this._31 = t;   
    483.   
    484.   t = this._23;   
    485.   this._23 = this._32;   
    486.   this._32 = t;   
    487.   
    488.   return this;   
    489.  },   
    490.   
    491.  // OpenGL style rotation   
    492.  glRotate: function(angle, x, y, z) {   
    493.   var s = Math.sin( angle );   
    494.   var c = Math.cos( angle );   
    495.   
    496.   var xx = x * x;   
    497.   var yy = y * y;   
    498.   var zz = z * z;   
    499.   var xy = x * y;   
    500.   var yz = y * z;   
    501.   var zx = z * x;   
    502.   var xs = x * s;   
    503.   var ys = y * s;   
    504.   var zs = z * s;   
    505.   var one_c = 1.0 - c;   
    506. /*  
    507.   this._11 = (one_c * xx) + c;  
    508.   this._21 = (one_c * xy) - zs;  
    509.   this._31 = (one_c * zx) + ys;  
    510.   this._41 = 0;  
    511.  
    512.   this._12 = (one_c * xy) + zs;  
    513.   this._22 = (one_c * yy) + c;  
    514.   this._32 = (one_c * yz) - xs;  
    515.   this._42 = 0;  
    516.  
    517.   this._13 = (one_c * zx) - ys;  
    518.   this._23 = (one_c * yz) + xs;  
    519.   this._33 = (one_c * zz) + c;  
    520.   this._43 = 0;  
    521.  
    522.   this._14 = 0;  
    523.   this._24 = 0;  
    524.   this._34 = 0;  
    525.   this._44 = 1;  
    526. */  
    527.   
    528.   this._11 = (one_c * xx) + c;   
    529.   this._12 = (one_c * xy) - zs;   
    530.   this._13 = (one_c * zx) + ys;   
    531.   this._14 = 0;   
    532.   
    533.   this._21 = (one_c * xy) + zs;   
    534.   this._22 = (one_c * yy) + c;   
    535.   this._23 = (one_c * yz) - xs;   
    536.   this._24 = 0;   
    537.   
    538.   this._31 = (one_c * zx) - ys;   
    539.   this._32 = (one_c * yz) + xs;   
    540.   this._33 = (one_c * zz) + c;   
    541.   this._34 = 0;   
    542.   
    543.   this._41 = 0;   
    544.   this._42 = 0;   
    545.   this._43 = 0;   
    546.   this._44 = 1;   
    547.   
    548.   return this;   
    549.  }   
    550.   
    551. }   
    552.   
    553. // matrix 2x2   
    554. function M22()   
    555. {   
    556.  this._11 = 1;   
    557.  this._12 = 0;   
    558.  this._21 = 0;   
    559.  this._22 = 1;   
    560. }   
    561.   
    562. M22.prototype.getInvert = function()   
    563. {   
    564.  var out = new M22();   
    565.  var det = this._11 * this._22 - this._12 * this._21;   
    566.  if (det > -0.0001 && det < 0.0001)   
    567.   return null;   
    568.   
    569.  out._11 = this._22 / det;   
    570.  out._22 = this._11 / det;   
    571.   
    572.  out._12 = -this._12 / det;   
    573.  out._21 = -this._21 / det;   
    574.   
    575.  return out;   
    576. }   

    3D衣服动画JS代码

    JavaScript Code复制内容到剪贴板
    1. function ClothApp()   
    2. {   
    3.  this.canvas = document.getElementById("cv");   
    4.   
    5.  P3D.g = this.canvas.getContext("2d");   
    6.   
    7.  var tex = new Image();   
    8.  this.texture1 = tex;   
    9.  tex.onload = function(){ _this.start(); };   
    10.  tex.src = "20090226032826.gif";   
    11.   
    12.  tex = new Image();   
    13.  this.texture2 = tex;   
    14.  tex.onload = function(){ _this.start(); };   
    15.  tex.src = "20090226032825.png";   
    16.   
    17.  this.mLoadCount = 2;   
    18.  this.mTickCount = 0;   
    19.   
    20.  this.G = 0.53;   
    21.  this.G1 = 0.45;   
    22.  this.mProjMat  = null;   
    23.  this.mViewMat  = null;   
    24.  this.mViewFrom = new Vec3();   
    25.  this.mViewFrom.y = -150;   
    26.  this.mViewFrom.z = 1000;   
    27.  this.mViewFromA = (new Vec3()).copyFrom(this.mViewFrom);   
    28.   
    29.  this.mViewAngle = 0;   
    30.   
    31.  this.mNLen = 0;   
    32.  this.mNodes = [];   
    33.  this.mRenderTris = null;   
    34.   
    35.  this.mLTNode = null;   
    36.  this.mRTNode = null;   
    37.   
    38.  this.mLTNodeV = new Vec3();   
    39.  this.mRTNodeV = new Vec3();   
    40.   
    41.  this.mWForce = new Vec3();   
    42.  this.frate = 15;   
    43.   
    44.  var _this = this;   
    45. }   
    46.   
    47. ClothApp.zsortCmp = function(t1, t2) {   
    48.  return t2.sortKey - t1.sortKey;   
    49. }   
    50.   
    51. ClothApp.prototype = {   
    52.  start: function() {   
    53.   if (--this.mLoadCount != 0) return;   
    54.   
    55.   this.vUP = new Vec3(0,  1, 0);   
    56.   this.vAT = new Vec3(0, 80, 0);   
    57.   
    58.   this.mViewport = {};   
    59.   this.mViewport.w = 480;   
    60.   this.mViewport.h = 300;   
    61.   this.mViewport.ow = 240;   
    62.   this.mViewport.oh = 150;   
    63.   this.setupTransforms();   
    64.   
    65.   this.generateCloth(180);   
    66.   this.generateRenderTriangles();   
    67.   
    68.   var _this = this;   
    69.   this.canvas.addEventListener("mousemove"function(e){_this.onMouseMove(e);}, false);   
    70.   this.canvas.addEventListener("mousedown"function(e){_this.onClick(e);}, false);   
    71.   
    72.   window.setTimeout(function(){_this.onInterval();}, this.frate);   
    73.  },   
    74.   
    75.  onInterval: function() {   
    76.   this.mTickCount++;   
    77.   
    78.   // this.mLTNodeV.z = Math.cos(this.mTickCount*0.1) * 2;   
    79.   
    80.   this.tick();   
    81.   this.updatePosition();   
    82.   this.draw();   
    83.   
    84.   var _this = this;   
    85.   window.setTimeout(function(){_this.onInterval();}, this.frate);   
    86.  },   
    87.   
    88.  onMouseMove: function(e) {   
    89.   if (e.clientX || e.clientX == 0)   
    90.    this.mViewAngle = (e.clientX - 240) * 0.004;   
    91.   
    92.   if (e.clientY || e.clientY == 0)   
    93.    this.mViewFromA.y = 90 - (e.clientY - 0) * 0.8;   
    94.  },   
    95.   
    96.  onClick: function(e) {   
    97.   if (e.clientX || e.clientX == 0)   
    98.   {   
    99.    this.mWForce.z = -4;   
    100.    this.mWForce.x = (e.clientX - 240) * -0.03;   
    101.   }   
    102.  },   
    103.   
    104.  tick: function() {   
    105.   this.updateViewTrans(this.mViewAngle);   
    106.   
    107.   var nlen = this.mNodes.length;   
    108.   var i, nd;   
    109.   for(i = 0;i < nlen;i++)   
    110.   {   
    111.    nd = this.mNodes[i];   
    112.    nd.F.x = 0;   
    113.    nd.F.z = 0;   
    114.    if (nd.flags & 4)   
    115.     nd.F.y = -this.G1;   
    116.    else  
    117.     nd.F.y = -this.G;   
    118.   
    119.    nd.F.add(this.mWForce);   
    120.   }   
    121.   
    122.   this.mWForce.zero();   
    123.   this.applyTension();   
    124.   
    125.   for(i = 0;i < nlen;i++)   
    126.   {   
    127.    nd = this.mNodes[i];   
    128.   
    129.    if ((nd.flags&1) != 0) {   
    130.     nd.F.sub(nd.F);   
    131.    }   
    132.   
    133.    nd.velo.add(nd.F);   
    134.   }   
    135.   
    136.   this.mLTNode.velo.copyFrom(this.mLTNodeV);   
    137.   this.mRTNode.velo.copyFrom(this.mRTNodeV);   
    138.  },   
    139.   
    140.  updatePosition: function() {   
    141.   var nlen = this.mNodes.length;   
    142.   var i, nd;   
    143.   for(i = 0;i < nlen;i++)   
    144.   {   
    145.    nd = this.mNodes[i];   
    146.   
    147.    if ((nd.flags&1) != 0) {   
    148.     nd.cv.x = 0;   
    149.     nd.cv.y = 0;   
    150.     nd.cv.z = 0;   
    151.    }   
    152.   
    153.    nd.pos.add(nd.velo);   
    154.    nd.velo.sub(nd.cv);   
    155.    nd.cv.x = 0;   
    156.    nd.cv.y = 0;   
    157.    nd.cv.z = 0;   
    158.   
    159.    nd.velo.smul(0.95);   
    160.   }   
    161.  },   
    162.   
    163.  draw: function() {   
    164.   P3D.clear("#000"this.mViewport.w, this.mViewport.h);   
    165.   this.transformPolygons();   
    166.   
    167.   this.mRenderTris.sort(ClothApp.zsortCmp);   
    168.   var len = this.mRenderTris.length;   
    169.   var t, sh;   
    170.   for (var i = 0;i < len;i++) {   
    171.    t = this.mRenderTris[i];   
    172.   
    173.    if (P3D.texture != t.texture)   
    174.     P3D.texture = t.texture;   
    175.   
    176.    sh = undefined;   
    177.    if (t.lighting && t.shade > 0.01)   
    178.     sh = "rgba(0,0,0,"+t.shade+")";   
    179.    P3D.drawTriangle(t.tposs, t.uvs, sh);   
    180.   }   
    181.  },   
    182.   
    183.  applyTension: function() {   
    184.   var i, k, nd;   
    185.   var v = new Vec3();   
    186.   var nlen = this.mNodes.length;   
    187.   var naturalLen = this.mNLen;   
    188.   
    189.   for (k = 0;k < nlen;k++)   
    190.   {   
    191.    nd = this.mNodes[k];   
    192.    var F = nd.F;   
    193.   
    194.    for (i = 0;i < 4;i++)   
    195.    {   
    196.     var nbr = nd.links[i];   
    197.     if (!nbr) continue;   
    198.   
    199.     var len = v.copyFrom(nbr.pos).sub(nd.pos).norm();   
    200.     var dlen = len - naturalLen;   
    201.     if (dlen > 0) {   
    202.      v.smul(dlen * 0.5 / len);   
    203.   
    204.      F.x += v.x;   
    205.      F.y += v.y;   
    206.      F.z += v.z;   
    207.      nd.cv.add(v.smul(0.8));   
    208.     }   
    209.    }   
    210.   }    
    211.  },   
    212.   
    213.  setupTransforms: function() {   
    214.   this.mProjMat = new M44();   
    215.   this.mProjMat.perspectiveLH(24, 15, 10, 9000);   
    216.   
    217.   this.mViewMat = new M44();   
    218.   this.updateViewTrans(0);   
    219.  },   
    220.   
    221.  updateViewTrans: function(ry) {   
    222.   this.mViewFromA.z = Math.cos(ry) * 380;   
    223.   this.mViewFromA.x = Math.sin(ry) * 380;   
    224.   
    225.   this.mViewFrom.smul(0.7);   
    226.   this.mViewFrom.x += this.mViewFromA.x * 0.3;   
    227.   this.mViewFrom.y += this.mViewFromA.y * 0.3;   
    228.   this.mViewFrom.z += this.mViewFromA.z * 0.3;   
    229.   
    230.   this.mViewMat.lookAtLH(this.vUP, this.mViewFrom, this.vAT);   
    231.  },   
    232.   
    233.  generateCloth: function(base_y) {   
    234.   var cols = 9;   
    235.   var rows = 8;   
    236.   
    237.   var step   = 22;   
    238.   this.mNLen = step*0.9;   
    239.   var w = (cols-1) * step;   
    240.   
    241.   var i, k;   
    242.   for (k = 0;k < rows;k++)   
    243.   {   
    244.    for (i = 0;i < cols;i++)   
    245.    {   
    246.     var nd = new ClothNode();   
    247.     nd.pos.x = -(w/2) + i*step;   
    248.     nd.pos.y = base_y -k*step/2;   
    249.     nd.pos.z = k*16;   
    250.   
    251.     nd.uv.u = i / (cols-1);   
    252.     nd.uv.v = k / (rows-1);   
    253.   
    254.     if (i > 0) {   
    255.      var prv_nd = this.mNodes[this.mNodes.length-1];   
    256.      prv_nd.links[1] = nd;   
    257.      nd.links[0] = prv_nd;   
    258.     }   
    259.   
    260.     if (k > 0) {   
    261.      var up_nd = this.mNodes[this.mNodes.length-cols];   
    262.      up_nd.links[4] = nd;   
    263.      nd.links[3] = up_nd;   
    264.     }   
    265.   
    266.     if (i != 0 && i != 4 && i != (cols-1))   
    267.      nd.flags |= 4;   
    268.   
    269.     this.mNodes.push(nd);   
    270.    }   
    271.   }   
    272.   
    273.   // fix left-top and right-top   
    274.   this.mNodes[0     ].flags |= 1;   
    275.   this.mNodes[4     ].flags |= 1;   
    276.   this.mNodes[cols-1].flags |= 1;   
    277.   
    278.   this.mLTNode = this.mNodes[0     ];   
    279.   this.mRTNode = this.mNodes[cols-1];   
    280.  },   
    281.   
    282.  generateRenderTriangles: function()   
    283.  {   
    284.   if (!this.mRenderTris) this.mRenderTris = [];   
    285.   
    286.   var i;   
    287.   var nd;   
    288.   var nlen = this.mNodes.length;   
    289.   
    290.   for(i = 0;i < nlen;i++)   
    291.   {   
    292.    nd = this.mNodes[i];   
    293.    if (nd.links[1] && nd.links[1].links[4]) {   
    294.     var t = new RenderTriangle();   
    295.     t.texture = this.texture1;   
    296.   
    297.     t.poss[0] = nd.pos;   
    298.     t.poss[1] = nd.links[1].pos;   
    299.     t.poss[2] = nd.links[1].links[4].pos;   
    300.   
    301.     t.uvs[0]  = nd.uv;   
    302.     t.uvs[1]  = nd.links[1].uv;   
    303.     t.uvs[2]  = nd.links[1].links[4].uv;   
    304.   
    305.     this.mRenderTris.push(t);   
    306.   
    307.     t = new RenderTriangle();   
    308.     t.texture = this.texture1;   
    309.   
    310.     t.poss[0] = nd.pos;   
    311.     t.poss[1] = nd.links[1].links[4].pos;   
    312.     t.poss[2] = nd.links[4].pos;   
    313.   
    314.     t.uvs[0]  = nd.uv;   
    315.     t.uvs[1]  = nd.links[1].links[4].uv;   
    316.     t.uvs[2]  = nd.links[4].uv;   
    317.   
    318.     this.mRenderTris.push(t);   
    319.    }   
    320.   }   
    321.   
    322.   this.addBGTriangles(this.mNodes[0].pos.y);   
    323.  },   
    324.   
    325.  addBGTriangles: function(by) {   
    326.   var cols = 4;   
    327.   var t, x, y, sz = 110;   
    328.   var ox = -(cols*sz)/2;   
    329.   var oz = -(cols*sz)/2;   
    330.   
    331.   for (y = 0;y < cols;y++) {   
    332.    for (x = 0;x < cols;x++) {   
    333.     var bv = ((x+y)&1) * 0.5;   
    334.     t = new RenderTriangle();   
    335.     t.texture = this.texture2;   
    336.   
    337.     t.poss[0] = new Vec3(ox + x*sz     , by, oz + y*sz     );   
    338.     t.poss[1] = new Vec3(ox + x*sz + sz, by, oz + y*sz     );   
    339.     t.poss[2] = new Vec3(ox + x*sz     , by, oz + y*sz + sz);   
    340.   
    341.     t.uvs[0]  = {u:0  , v:bv    };   
    342.     t.uvs[1]  = {u:0.5, v:bv    };   
    343.     t.uvs[2]  = {u:0  , v:bv+0.5};   
    344.   
    345.     if ((x==1 || x==2) && (y==1 || y==2))   
    346.      this.modifyRoofUV(t, x == 2, bv);   
    347.   
    348.     t.lighting = false;   
    349.     t.zBias = 0.5;   
    350.     this.mRenderTris.push(t);   
    351.   
    352.     t = new RenderTriangle();   
    353.     t.texture = this.texture2;   
    354.   
    355.     t.poss[0] = new Vec3(ox + x*sz     , by, oz + y*sz + sz);   
    356.     t.poss[1] = new Vec3(ox + x*sz + sz, by, oz + y*sz    );   
    357.     t.poss[2] = new Vec3(ox + x*sz + sz, by, oz + y*sz + sz);   
    358.   
    359.     t.uvs[0]  = {u:0  , v:bv+0.5};   
    360.     t.uvs[1]  = {u:0.5, v:bv    };   
    361.     t.uvs[2]  = {u:0.5, v:bv+0.5};   
    362.   
    363.     if ((x==1 || x==2) && (y==1 || y==2))   
    364.      this.modifyRoofUV(t, x == 2, bv);   
    365.   
    366.     t.lighting = false;   
    367.     t.zBias = 0.5;   
    368.     this.mRenderTris.push(t);   
    369.   
    370.    }   
    371.   }   
    372.  },   
    373.   
    374.  modifyRoofUV: function(t, rv, bv) {   
    375.   if (rv) {   
    376.    t.uvs[0].u = 0.5 - t.uvs[0].u;   
    377.    t.uvs[1].u = 0.5 - t.uvs[1].u;   
    378.    t.uvs[2].u = 0.5 - t.uvs[2].u;   
    379.   }   
    380.   
    381.   t.uvs[0].u += 0.5;   
    382.   t.uvs[1].u += 0.5;   
    383.   t.uvs[2].u += 0.5;   
    384.   
    385.   if (rv) {   
    386.    t.uvs[0].v = 0.5 - t.uvs[0].v + bv + bv;   
    387.    t.uvs[1].v = 0.5 - t.uvs[1].v + bv + bv;   
    388.    t.uvs[2].v = 0.5 - t.uvs[2].v + bv + bv;   
    389.   }   
    390.   
    391.  },   
    392.   
    393.  transformPolygons: function() {   
    394.   var trans = new M44();   
    395.   trans.mul(this.mViewMat, this.mProjMat);   
    396.   
    397.   var hw = this.mViewport.ow;   
    398.   var hh = this.mViewport.oh;   
    399.   
    400.   var len = this.mRenderTris.length;   
    401.   var t;   
    402.   var spos = [0, 0, 0, 0];   
    403.   for (var i = 0;i < len;i++) {   
    404.    t = this.mRenderTris[i];   
    405.    for (var k = 0;k < 3;k++) {   
    406.     trans.transVec3(spos, t.poss[k].x, t.poss[k].y, t.poss[k].z);   
    407.   
    408.     var W = spos[3];   
    409.     spos[0] /= W;   
    410.     spos[1] /= W;   
    411.     spos[2] /= W;   
    412.   
    413.     spos[0] *= this.mViewport.w;   
    414.     spos[1] *= -this.mViewport.h;   
    415.     spos[0] += hw;   
    416.     spos[1] += hh;   
    417.   
    418.     t.tposs[k].x = spos[0];   
    419.     t.tposs[k].y = spos[1];   
    420.     t.tposs[k].z = spos[2];   
    421.    }   
    422.   
    423.    var v1 = (new Vec3()).copyFrom(t.poss[1]).sub(t.poss[0]).normalize();   
    424.    var v2 = (new Vec3()).copyFrom(t.poss[2]).sub(t.poss[1]).normalize();   
    425.    var N = (new Vec3()).cp(v1, v2);   
    426.   
    427.    trans.transVec3Rot(spos, N.x, N.y, N.z);   
    428.   
    429.    if (t.lighting) {   
    430.     if (spos[2] > 0)   
    431.      t.shade = 0.8   
    432.     else {   
    433.      t.shade = 0.1 - N.y * 0.6;   
    434.      if (t.shade < 0) t.shade = 0;   
    435.     }   
    436.    }   
    437.   
    438.    t.sortKey = Math.floor( (t.tposs[0].z + t.tposs[1].z + t.tposs[2].z + t.zBias) *1000 );   
    439.   }   
    440.  }   
    441. }   
    442.   
    443. function ClothNode()   
    444. {   
    445.  this.flags = 0;   
    446.  this.pos  = new Vec3();   
    447.  this.velo = new Vec3();   
    448.  this.cv   = new Vec3();   
    449.  this.F    = new Vec3();   
    450.  this.links = [nullnullnullnull];   
    451.  this.uv = {u:0, v:0};   
    452. }   
    453.   
    454. function RenderTriangle()   
    455. {   
    456.  this.texture = null;   
    457.  this.poss  = new Array(3);   
    458.  this.tposs = [new Vec3(), new Vec3(), new Vec3()];   
    459.  this.uvs = [{u:0, v:0}, {u:0, v:0}, {u:0, v:0}];   
    460.  this.shade = 0;   
    461.  this.lighting = true;   
    462.  this.zBias = 0;   
    463.   
    464.  this.sortKey = 0;   
    465. }   

    以上就是HTML5 3D衣服摇摆动画特效的源码介绍,需要更为深入学习的下载源代码来研究。

    上一篇:利用HTML5 Canvas制作键盘及鼠标动画的实例分享
    下一篇:HTML5 Canvas入门学习教程
  • 相关文章
  • 

    © 2016-2020 巨人网络通讯 版权所有

    《增值电信业务经营许可证》 苏ICP备15040257号-8

    HTML5 3D衣服摇摆动画特效 HTML5,衣服,摇摆,动画,特效,