• <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            隨筆-341  評論-2670  文章-0  trackbacks-0
                花了兩個小時把這個東西做好了。雖然不及[LIEN87 ; SHAN87 ; SHAN89]論文厲害,不過自己弄的這個寫起來倒是相當容易的。在這里貼出效果圖和代碼。效果圖中,我先使用藍色畫筆,用PolyBezier繪制曲線,然后使用紅色像素使用自己的算法繪制曲線。可以看見有一點點誤差,不過效果還是可以接受的。代碼仍然使用自己的那套庫開發,不過曲線掃描的方法不受庫的限制。這個算法保證非交叉部分的點不會被重復繪制。

                有了這個算法之后我就可以把貝塞爾曲線轉換成密度剛好的折線了。這才是最終目的。

              1 #include "..\..\..\..\Library\Windows\VL_WinMain.h"
              2 #include "..\..\..\..\Library\Windows\VL_WinGDI.h"
              3 
              4 using namespace vl;
              5 using namespace vl::windows;
              6 
              7 class MyForm : public VL_WinForm
              8 {
              9 protected:
             10     VL_WinDIB* FBuffer;
             11     VL_WinDC* FBufferDC;
             12     VL_WinDC* FFormDC;
             13     VL_WinPen::Ptr FGDIPen;
             14     VL_WinPen::Ptr FMyPen;
             15 
             16     POINT FControlPoints[4];
             17     VInt FMouseIndex;
             18 
             19     void Clear()
             20     {
             21         FBufferDC->FillRect(0,0,800,600);
             22     }
             23 
             24     void GetD(VDouble T , VDouble& dX , VDouble& dY)
             25     {
             26         dX=    FControlPoints[0].x*(-3*(1-T)*(1-T))+
             27             FControlPoints[1].x*(-6*T*(1-T)+3*(1-T)*(1-T))+
             28             FControlPoints[2].x*(-3*T*T+6*T*(1-T))+
             29             FControlPoints[3].x*3*T*T;
             30 
             31         dY=    FControlPoints[0].y*(-3*(1-T)*(1-T))+
             32             FControlPoints[1].y*(-6*T*(1-T)+3*(1-T)*(1-T))+
             33             FControlPoints[2].y*(-3*T*T+6*T*(1-T))+
             34             FControlPoints[3].y*3*T*T;
             35     }
             36 
             37     void GetP(VDouble T , VDouble& X , VDouble& Y)
             38     {
             39         X=    FControlPoints[0].x*(1-T)*(1-T)*(1-T)+
             40             FControlPoints[1].x*3*T*(1-T)*(1-T)+
             41             FControlPoints[2].x*3*T*T*(1-T)+
             42             FControlPoints[3].x*T*T*T;
             43 
             44         Y=    FControlPoints[0].y*(1-T)*(1-T)*(1-T)+
             45             FControlPoints[1].y*3*T*(1-T)*(1-T)+
             46             FControlPoints[2].y*3*T*T*(1-T)+
             47             FControlPoints[3].y*T*T*T;
             48     }
             49 
             50     void SetColor(VInt X , VInt Y , VInt Color)
             51     {
             52         VByte R=Color%256;
             53         VByte G=(Color>>8)%256;
             54         VByte B=(Color>>16)%256;
             55         if(X>=0 && X<FBuffer->GetWidth() && Y>=0 && Y<FBuffer->GetHeight())
             56         {
             57             ((VInt32u*)(FBuffer->ScanLines[Y]))[X]=(R<<16)+(G<<8)+B;
             58         }
             59     }
             60 
             61     void DrawCurve()
             62     {
             63         FBufferDC->MoveTo(FControlPoints[0].x,FControlPoints[0].y);
             64         VDouble T=0.0001;
             65         VBool Finished=false;
             66         VDouble OldX=FControlPoints[0].x;
             67         VDouble OldY=FControlPoints[0].y;
             68         VDouble X1,Y1;
             69         VDouble X2=FControlPoints[3].x;
             70         VDouble Y2=FControlPoints[3].y;
             71 
             72         VInt OldX1=FControlPoints[0].x;
             73         VInt OldY1=FControlPoints[0].y;
             74         VInt OldX2=0;
             75         VInt OldY2=0;
             76         VBool Old2Available=false;
             77         SetColor(OldX1,OldY1,RGB(255,0,0));
             78         while(!Finished)
             79         {
             80             /*初始步長為當前t到結束點*/
             81             VDouble dT=(1-T);
             82             VBool AtTail=true;
             83             while(true)
             84             {
             85                 /*取半步,檢查目標點與當前點的長度*/
             86                 VDouble dTHalf=dT/2;
             87                 if(dTHalf<0.00001)
             88                 {
             89                     dTHalf=dTHalf;
             90                 }
             91                 GetP(T+dT,X1,Y1);
             92                 GetP(T+dTHalf,X2,Y2);
             93                 VDouble Length=sqrt((X1-OldX)*(X1-OldX)+(Y1-OldY)*(Y1-OldY));
             94                 VDouble LengthHalf=sqrt((X2-OldX)*(X2-OldX)+(Y2-OldY)*(Y2-OldY));
             95                 /*如果半步長大于一步則取半步,繼續迭代*/
             96                 if(LengthHalf>=Length)
             97                 {
             98                     dT=dTHalf;
             99                 }
            100                 else
            101                 {
            102                     /*否則,如果全步長產生的距離<=1則繪制*/
            103                     if(Length<=1)
            104                     {
            105                         if(AtTail)
            106                         {
            107                             Finished=true;
            108                         }
            109                         break;
            110                     }
            111                     /*否則進行近似測量*/
            112                     else
            113                     {
            114                         dT*=1/Length;
            115                         GetP(T+dT,X1,Y1);
            116                     }
            117                 }
            118                 AtTail=false;
            119             }
            120             /*計算像素位置*/
            121             VInt X=Round(X1);
            122             VInt Y=Round(Y1);
            123             VInt dX_I=(OldX1-X)*(OldX1-X);
            124             VInt dY_I=(OldY1-Y)*(OldY1-Y);
            125             /*讓線條長度保持1*/
            126             if(Old2Available)
            127             {
            128                 if(dX_I==1 && dY_I==1)
            129                 {
            130                     OldX1=X;
            131                     OldY1=Y;
            132                     SetColor(OldX1,OldY1,RGB(255,0,0));
            133                 }
            134                 else
            135                 {
            136                     OldX1=X;
            137                     OldY1=Y;
            138                     SetColor(OldX1,OldY1,RGB(255,0,0));
            139                     SetColor(OldX2,OldY2,RGB(255,0,0));
            140                 }
            141                 Old2Available=false;
            142             }
            143             else
            144             {
            145                 if(dX_I==1 && dY_I==1)
            146                 {
            147                     OldX1=X;
            148                     OldY1=Y;
            149                     SetColor(OldX1,OldY1,RGB(255,0,0));
            150                 }
            151                 else if(dX_I==1 || dY_I==1)
            152                 {
            153                     OldX2=X;
            154                     OldY2=Y;
            155                     Old2Available=true;
            156                 }
            157             }
            158             OldX=X1;
            159             OldY=Y1;
            160             T+=dT;
            161         }
            162         if(Old2Available)
            163         {
            164             SetColor(OldX2,OldY2,RGB(255,0,0));
            165         }
            166     }
            167 
            168     void DrawHandles()
            169     {
            170         for(VInt i=0;i<4;i++)
            171         {
            172             POINT P=FControlPoints[i];
            173             FBufferDC->Ellipse(P.x-2,P.y-2,P.x+2,P.y+2);
            174         }
            175     }
            176 
            177     void Draw()
            178     {
            179         Clear();
            180         FBufferDC->SetPen(FGDIPen);
            181         FBufferDC->PolyBezier(FControlPoints,4);
            182         FBufferDC->SetPen(FMyPen);
            183         DrawCurve();
            184         DrawHandles();
            185         FFormDC->Draw(0,0,FBuffer);
            186     }
            187 public:
            188     MyForm():VL_WinForm(true)
            189     {
            190         FBuffer=new VL_WinDIB(800,600);
            191         FBufferDC=&FBuffer->DC;
            192         FBufferDC->SetBackTransparent(true);
            193         FFormDC=new VL_WinControlDC(GetHandle());
            194         FGDIPen=new VL_WinPen(PS_SOLID,1,RGB(0,0,255));
            195         FMyPen=new VL_WinPen(PS_SOLID,1,RGB(255,0,0));
            196         FMouseIndex=-1;
            197 
            198         FControlPoints[0].x=200;
            199         FControlPoints[0].y=400;
            200         FControlPoints[1].x=200;
            201         FControlPoints[1].y=200;
            202         FControlPoints[2].x=400;
            203         FControlPoints[2].y=200;
            204         FControlPoints[3].x=400;
            205         FControlPoints[3].y=400;
            206 
            207         OnPaint.Bind(this,&MyForm::Form_OnPaint);
            208         OnLeftButtonDown.Bind(this,&MyForm::Form_OnMouseDown);
            209         OnMouseMove.Bind(this,&MyForm::Form_OnMouseMove);
            210         OnLeftButtonUp.Bind(this,&MyForm::Form_OnMouseUp);
            211 
            212         SetMaximizeBox(false);
            213         SetMinimizeBox(false);
            214         SetBorder(vwfbSingle);
            215         SetClientWidth(800);
            216         SetClientHeight(600);
            217         SetText(L"Vczh Bezier");
            218         MoveCenter();
            219         Draw();
            220         Show();
            221     }
            222 
            223     ~MyForm()
            224     {
            225         delete FFormDC;
            226         delete FBuffer;
            227     }
            228 
            229     void Form_OnPaint(VL_Base* Sender)
            230     {
            231         FFormDC->Draw(0,0,FBuffer);
            232     }
            233 
            234     void Form_OnMouseDown(VL_Base* Sender,VLS_MouseStruct MouseStruct)
            235     {
            236         /*計算出在鼠標控制范圍內(6像素)的控制點*/
            237         for(VInt i=0;i<4;i++)
            238         {
            239             POINT P=FControlPoints[i];
            240             if((P.x-MouseStruct.X)*(P.x-MouseStruct.X)+(P.y-MouseStruct.Y)*(P.y-MouseStruct.Y)<=36)
            241             {
            242                 FMouseIndex=i;
            243                 break;
            244             }
            245         }
            246         Form_OnMouseMove(Sender,MouseStruct);
            247     }
            248 
            249     void Form_OnMouseMove(VL_Base* Sender,VLS_MouseStruct MouseStruct)
            250     {
            251         /*抓住有效控制點的話則移動*/
            252         if(FMouseIndex!=-1)
            253         {
            254             FControlPoints[FMouseIndex].x=MouseStruct.X;
            255             FControlPoints[FMouseIndex].y=MouseStruct.Y;
            256             Draw();
            257         }
            258     }
            259 
            260     void Form_OnMouseUp(VL_Base* Sender,VLS_MouseStruct MouseStruct)
            261     {
            262         /*接觸控制*/
            263         FMouseIndex=-1;
            264     }
            265 };
            266 
            267 void main()
            268 {
            269     new MyForm();
            270     GetApplication()->Run();
            271 }
            posted on 2008-06-11 21:20 陳梓瀚(vczh) 閱讀(2626) 評論(1)  編輯 收藏 引用 所屬分類: 2D

            評論:
            # re: 自適應步長Bezier曲線掃描 2008-06-13 08:17 | Gohan
            想看看博主關于自己寫的庫的介紹或者講解;)  回復  更多評論
              
            婷婷五月深深久久精品| 久久婷婷综合中文字幕| 中文无码久久精品| 久久国产免费| 欧美伊香蕉久久综合类网站| 久久精品亚洲乱码伦伦中文| 三上悠亚久久精品| 久久久久久曰本AV免费免费| 青青久久精品国产免费看| 国产精品久久久久久久久久免费| 狠狠色丁香久久婷婷综合五月| 亚洲精品无码久久久影院相关影片| 99国产欧美精品久久久蜜芽| 乱亲女H秽乱长久久久| 久久国产成人| 四虎国产精品免费久久| 精品免费久久久久久久| 亚洲伊人久久成综合人影院| 久久国产三级无码一区二区| 久久超碰97人人做人人爱| 99精品久久精品一区二区| 国产香蕉久久精品综合网| 99精品久久精品一区二区| 亚洲国产精品久久久久网站| 国产激情久久久久影院| 国产精品对白刺激久久久| 久久久久久久久66精品片| 无码人妻久久一区二区三区 | 久久热这里只有精品在线观看| 国产精品99久久久久久人| 99久久人妻无码精品系列| 久久这里只有精品18| 久久久久无码精品国产不卡| 精品久久久无码21p发布| 亚洲国产精品18久久久久久| 久久国产色av免费看| 久久久久久精品无码人妻| 午夜久久久久久禁播电影| 亚洲va久久久噜噜噜久久| 蜜臀av性久久久久蜜臀aⅴ麻豆 | 国产美女久久精品香蕉69|