纳金网

标题: [as3基础应用]三次贝塞尔曲线绘制算法(优化过)—续 [打印本页]

作者: .    时间: 2013-3-20 08:57
标题: [as3基础应用]三次贝塞尔曲线绘制算法(优化过)—续
/*初始化计算的一些准备数据*/
                     btInit();
                     /*默认进行第一次定位和绘制*/
                     ct0.x = 100;
                     ct0.y = 100;
                     ct1.x = 700;
                     ct1.y = 100;
                     ct2.x = 700;
                     ct2.y = 500;
                     ct3.x = 100;
                     ct3.y = 500;
                     lin.graphics.lineStyle(0, 0x000000);
                     lin.graphics.moveTo(ct0.x, ct0.y);
                     lin.graphics.lineTo(ct1.x, ct1.y);
                     lin.graphics.lineTo(ct2.x, ct2.y);
                     lin.graphics.lineTo(ct3.x, ct3.y);
                     drawBezier3(new Point(ct0.x, ct0.y), new Point(ct1.x, ct1.y), new Point(ct2.x, ct2.y), new Point(ct3.x, ct3.y));
              }
              /*按钮按下便开始可以拖动点*/
              private function mouseDown(e:MouseEvent):void
              {
                     e.target.startDrag();
                     stage.addEventListener(MouseEvent.MOUSE_MOVE, mouseMove);
              }
              /*鼠标移动便不断绘制曲线*/
              private function mouseMove(e:MouseEvent):void
              {
                     /*绘制连接四个点的直线*/
                     lin.graphics.clear();
                     lin.graphics.lineStyle(0, 0x000000);
                     lin.graphics.moveTo(ct0.x, ct0.y);
                     lin.graphics.lineTo(ct1.x, ct1.y);
                     lin.graphics.lineTo(ct2.x, ct2.y);
                     lin.graphics.lineTo(ct3.x, ct3.y);
                     /*绘制曲线*/
                     data.fillRect(new Rectangle(0, 0, 800, 600), 0xffffffff);
                     drawBezier3(new Point(ct0.x, ct0.y), new Point(ct1.x, ct1.y), new Point(ct2.x, ct2.y), new Point(ct3.x, ct3.y));
              }
              /*释放按钮停止拖动*/
              private function mouseUp(e:MouseEvent):void
              {
                     var n:int;
                     e.target.stopDrag();
                     stage.removeEventListener(MouseEvent.MOUSE_MOVE, mouseMove);
              }
              /***********算法部分**********/
              
              /*初始化计算所需数据,主要是btC30到btC33*/
              private function btInit():void
              {
                     var add:Number;
                     /*由于t的值域为[0,1],要绘制LENGTH个点,则必须计算出每次t的增量*/
                     add = 1.0 / (LENGTH - 1.0);
                     /*三次白赛尔曲线Ri的权重公式为:C3i * pow( t - 1 , 3 - i ) * pow( t , i )
                      *前三次t的值分别为0,add,add*2
                      *则代入公式就能求出R0 R1 R2 R3的前三次的权重值
                      * */
                     btC30[0] = 1;
                     btC30[1] = C30 * Math.pow(1 - add, 3);
                     btC30[2] = C30 * Math.pow(1 - add * 2, 3);
                     btC31[0] = 0;
                     btC31[1] = C31 * Math.pow(1 - add, 2) * add;
                     btC31[2] = C31 * Math.pow(1 - add * 2, 2) * add * 2;
                     btC32[0] = 0;
                     btC32[1] = C32 * (Math.pow(add, 2) - Math.pow(add, 3));
                     btC32[2] = C32 * (Math.pow(add * 2, 2) - Math.pow(add * 2, 3));
                     btC33[0] = 0;
                     btC33[1] = C33 * Math.pow(add, 3);
                     btC33[2] = C33 * Math.pow(add * 2, 3);
              }
              /*利用准备好的初始数据,通过递推方法求出四个点对应的贝塞尔曲线上每个点的坐标,并绘制
               *计算中用到多项式批量计算优化策略,上一篇博文中有提及具体的方法和思想
               * */
              private function drawBezier3(p0oint,p1oint,p2oint,p3oint):void
              {
                     /*qun_x和qun_x本别为x坐标和y坐标的临时数据数组*/
                     var qun_x:Vector.<Number> = new Vector.<Number>(3);
                     var qun_y:Vector.<Number> = new Vector.<Number>(3);
                     /*dd_x和dd_y分别为x坐标的多项式和y坐标式求导三次后得到的常数*/
                     var dd_x:Number;
                     var dd_y:Number;
                     var n:int;
                     /*计算前三次种子数据*/
                     dd_x = 6 * (3 * p1.x - 3 * p2.x - p0.x + p3.x) / Math.pow(LENGTH - 1.0, 3);
                     qun_x[0] = p0.x * btC30[0] + p1.x * btC31[0] + p2.x * btC32[0] + p3.x * btC33[0];
                     dd_y = 6 * (3 * p1.y - 3 * p2.y - p0.y + p3.y) / Math.pow(LENGTH - 1.0, 3);
                     qun_y[0] = p0.y * btC30[0] + p1.y * btC31[0] + p2.y * btC32[0] + p3.y * btC33[0];
                     data.setPixel(qun_x[0], qun_y[0], 0x000000);
                     qun_x[1] = p0.x * btC30[1] + p1.x * btC31[1] + p2.x * btC32[1] + p3.x * btC33[1];
                     qun_x[0] = qun_x[1] - qun_x[0];
                     qun_y[1] = p0.y * btC30[1] + p1.y * btC31[1] + p2.y * btC32[1] + p3.y * btC33[1];
                     qun_y[0] = qun_y[1] - qun_y[0];
                     data.setPixel(qun_x[1], qun_y[1], 0x000000);
                     qun_x[2] = p0.x * btC30[2] + p1.x * btC31[2] + p2.x * btC32[2] + p3.x * btC33[2];
                     qun_x[1] = qun_x[2] - qun_x[1];
                     qun_x[0] = qun_x[1] - qun_x[0];
                     qun_y[2] = p0.y * btC30[2] + p1.y * btC31[2] + p2.y * btC32[2] + p3.y * btC33[2];
                     qun_y[1] = qun_y[2] - qun_y[1];
                     qun_y[0] = qun_y[1] - qun_y[0];
                     data.setPixel(qun_x[2], qun_y[2], 0x000000);
                     /*进行递推计算的循环*/
                     for (n = 3; n < LENGTH; n++)
                     {
                            qun_x[0] += dd_x;
                            qun_x[1] += qun_x[0];
                            qun_x[2] += qun_x[1];
                            qun_y[0] += dd_y;
                            qun_y[1] += qun_y[0];
                            qun_y[2] += qun_y[1];
                            data.setPixel(qun_x[2], qun_y[2], 0x000000);
                     }
              }
       }
      
}   【来源:互联网】
更多精彩教程,尽在web3D纳金网http://www.narkii.com/college/




欢迎光临 纳金网 (http://c-www.narkii.com/club/) Powered by Discuz! X2.5