圆弧插补

空间任意三点 画圆。
测试代码
平面三点
void CCeshiDlg::OnButtonDraw() 
{
    
// TODO: Add your control notification handler code here
    CWnd *pwnd=GetDlgItem(IDC_STATIC_SHOW);
    CDC 
*pdc=pwnd->GetDC();
    POINT p1;
    POINT p2;
    POINT p3;
    
double x0=0.0,y0=0.0,z0=0.0,x2=0.0,y2=0.0,z2=0.0,x1=0.0,y1=0.0,z1=0.0;
    
double xc=0.0,yc=0.0,zc=0.0,R=0.0;
    
double G=0.0,E=0.0;
    
double u=0.0,v=0.0,w=0.0;
    
double Xi=0.0,Yi=0.0,Zi=0.0;
    
double Mi=0.0,Ni=0.0,Li=0.0;
    p1.x
=0;
    p1.y
=140;
    p2.x
=350;
    p2.y
=140;
    pdc
->MoveTo(p1);
    pdc
->LineTo(p2);
    p1.x
=175;
    p1.y
=0;
    p2.x
=175;
    p2.y
=280;
    pdc
->MoveTo(p1);
    pdc
->LineTo(p2);

    p1.x
=275;
    p1.y
=140;
    p2.x
=175;
    p2.y
=40
    p3.x
=75;
    p3.y
=140;    

    x0
=275;
    y0
=140;
    x1
=175;
    y1
=40;
    x2
=75;
    y2
=140;
    
double q[11]={0.0};
    
double Paramter[11]={0.0};
    q[
0]=x0;
    q[
1]=y0;
    q[
2]=z0;
    q[
3]=x1;
    q[
4]=y1;
    q[
5]=z1;
    q[
6]=x2;
    q[
7]=y2;
    q[
8]=z2;
    q[
9]=10;
    q[
10]=0.05;
    CircleInter(q,Paramter);
    
long N=0;
    N
=(long)(Paramter[0]/Paramter[1])+1;//插补次数    
    xc=Paramter[2];
    yc
=Paramter[3];
    zc
=Paramter[4];
    G
=Paramter[6];
    E
=Paramter[7];
    u
=Paramter[8];
    v
=Paramter[9];
    w
=Paramter[10];
    
    Xi
=(double)p1.x;
    Yi
=(double)p1.y;
    Zi
=0;
    Mi
=v*(Zi-zc)-w*(Yi-yc);
    Ni
=w*(Xi-xc)-u*(Zi-zc);
    Li
=u*(Yi-yc)-v*(Xi-xc);
    pdc
->MoveTo(p1);
    POINT pi;
    
for(int i=1;i<N;i++)
    
{
        Xi
=xc+G*(Xi+E*Mi-xc);
        Yi
=yc+G*(Yi+E*Ni-yc);
        Zi
=zc+G*(Zi+E*Li-zc);
        Mi
=v*(Zi-zc)-w*(Yi-yc);
        Ni
=w*(Xi-xc)-u*(Zi-zc);
        Li
=u*(Yi-yc)-v*(Xi-xc);
        pi.x
=(long)Xi;
        pi.y
=(long)Yi;
        pdc
->LineTo(pi);

    }

    pdc
->LineTo(p3);
             
}



_declspec(dllexport) bool CircleInter(double p[11],double *Paramter)
{

    
double a00=0.0,a01=0.0,a02=0.0,a10=0.0,a11=0.0,a12=0.0;
    
double a20=0.0,a21=0.0,a22=0.0,b0=0.0,b1=0.0,b2=0.0;
    
double x0=0.0;
    
double y0=0.0;
    
double z0=0.0;
    
double x1=0.0;
    
double y1=0.0;
    
double z1=0.0;
    
double x2=0.0;
    
double y2=0.0;
    
double z2=0.0;
    x0
=p[0];
    y0
=p[1];
    z0
=p[2];
    x1
=p[3];
    y1
=p[4];
    z1
=p[5];
    x2
=p[6];
    y2
=p[7];
    z2
=p[8];
    
double xc=0.0,yc=0.0,zc=0.0;//圆心坐标
    double R=0.0;//圆半径
    double u=0.0,v=0.0,w=0.0;
    
double u1=0.0,v1=0.0,w1=0.0;
    
double FT=0.0;
    
double G=0.0;
    
double delt=0.0;
    
double thelt=0.0;
    
double E=0.0;
    
double H=0.0;
    a00
=2*(x0-x1);a01=2*(y0-y1);a02=2*(z0-z1);
    a10
=2*(x1-x2);a11=2*(y1-y2);a12=2*(z1-z2);
    a20
=a02*(a02*a11-a01*a12)/8;
    a21
=a02*(a00*a12-a02*a10)/8;
    a22
=-(a00*(a02*a11-a01*a12)+a01*(a00*a12-a02*a10))/8;
    b0
=(x0*x0+y0*y0+z0*z0)-(x1*x1+y1*y1+z1*z1);
    b1
=(x1*x1+y1*y1+z1*z1)-(x2*x2+y2*y2+z2*z2);
    b2
=a20*x0+a21*y0+a02*z0;
    
    
if(fabs(x0-x1)<=1e-5 && fabs(x1-x2)<=1e-5)
    
{

        xc
=x0;
        yc
=(a12*b0-a02*b1)/(-a02*a11+a01*a12);    
        zc
=(a11*b0-a01*b1)/(a02*a11-a01*a12);
    }

    
else if(fabs(y0-y1)<=1e-5 && fabs(y1-y2)<=1e-5)
    
{
    
        xc
=(a12*b0-a02*b1)/(-a02*a10+a00*a12);
        yc
=y0;
        zc
=(a10*b0-a00*b1)/(a02*a10-a00*a12);        
    }

    
else if(fabs(z0-z1)<=1e-5 && fabs(z1-z2)<=1e-5)
    
{

    
        xc
=(a11*b0-a01*b1)/(-a01*a10+a00*a11);
        yc
=(a10*b0-a00*b1)/(a01*a10-a00*a11);
        zc
=z0;
    }

    
else
    
{
        xc
=(a12*a21*b0-a11*a22*b0-a02*a21*b1+a01*a22*b1+a02*a11*b2-a01*a12*b2)/(a02*a11*a20-a01*a12*a20-a02*a10*a21+a00*a12*a21+a01*a10*a22-a00*a11*a22);
        yc
=(a12*a20*b0-a10*a22*b0-a02*a20*b1+a00*a22*b1+a02*a10*b2-a00*a12*b2)/(-a02*a11*a20+a01*a12*a20+a02*a10*a21-a00*a12*a21-a01*a10*a22+a00*a11*a22);
        zc
=(a11*a20*b0-a10*a21*b0-a01*a20*b1+a00*a21*b1+a01*a10*b2-a00*a11*b2)/(a02*a11*a20-a01*a12*a20-a02*a10*a21+a00*a12*a21+a01*a10*a22-a00*a11*a22);                    
    }



    R
=sqrt((x0-xc)*(x0-xc)+(y0-yc)*(y0-yc)+(z0-zc)*(z0-zc));
    u
=(y1-y0)*(z2-z1)-(z1-z0)*(y2-y1);
    v
=(z1-z0)*(x2-x1)-(x1-x0)*(z2-z1);
    w
=(x1-x0)*(y2-y1)-(y1-y0)*(x2-x1);
    u1
=(y0-yc)*(z2-z0)-(z0-zc)*(y2-y0);
    v1
=(z0-zc)*(x2-x0)-(x0-xc)*(z2-z0);
    w1
=(x0-xc)*(y2-y0)-(y0-yc)*(x2-x0);
    FT
=p[9]*p[10];
    G
=1/sqrt(1+(FT/R)*(FT/R));
    delt
=FT/R;
    E
=FT/(R*sqrt(u*u+v*v+w*w));
    H
=u*u1+v*v1+w*w1;
    
if(H>=0)
    
{
        thelt
=2*asin(sqrt((x2-x0)*(x2-x0)+(y2-y0)*(y2-y0)+(z2-z0)*(z2-z0))/(2*R));
    }

    
else if(H<0)
    
{
        thelt
=2*pi-2*asin(sqrt((x2-x0)*(x2-x0)+(y2-y0)*(y2-y0)+(z2-z0)*(z2-z0))/(2*R));
    }

    Paramter[
0]=thelt;
    Paramter[
1]=delt;
    Paramter[
2]=xc;
    Paramter[
3]=yc;
    Paramter[
4]=zc;
    Paramter[
5]=R;
    Paramter[
6]=G;
    Paramter[
7]=E;
    Paramter[
8]=u;
    Paramter[
9]=v;
    Paramter[
10]=w;
    
    
return true;
}


原文地址:https://www.cnblogs.com/wqj1212/p/1140653.html