图解计算机图形学三维变换算法

工程下载

http://pan.baidu.com/s/1o7OEMc6

tcddd.rar


此处为在Windows下运行的TC图形程序;使用了EasyX库;

EasyX库可参考:

http://blog.csdn.net/bcbobo21cn/article/details/51207782

http://www.easyx.cn


代码参考

http://blog.sina.com.cn/s/articlelist_1287275024_9_1.html


一 三维透视投影变换算法

#include <math.h>
#include <graphics.h>
#include <conio.h>
#include <stdio.h>

void draw(float z[][4],float xt0,float yt0,float ts0);
void matrix(float t[][4]);

#define N 22

float p[N][4]={{45,30,0,1},{27,30,0,1},{27,30,10,1},{18,30,10,1},
                  {18,30,0,1},{0,30,0,1},{0,30,15,1},{45,30,15,1},
                  {45,30,0,1},{45,0,0,1},{45,0,15,1},{45,15,27,1},
                  {0,15,27,1},{0,30,15,1},{45,30,15,1},{45,15,27,1},
                  {45,10,15,1},{45,10,5,1},{45,20,5,1},{45,20,15,1},
                  {0,0,15,1},{0,0,0,1}
                 };
int tp[]={-1,0,1,2,3,4,5,6,7,0,-1,0,7,11,10,9,0,-1,16,17,18,19,16,
-1,9,10,20,21,9,-1,10,11,12,20,10,-1,6,7,11,12,6,-1,
             5,6,12,20,21,5,-100
           };
main()
{
  static float tx[4][4];
  float b1,b2,h,e,a,l,m,n,k,d,q;
  int i;

  initgraph(640, 480);
  //int driver,mode;
  //driver=DETECT;
  //initgraph(&driver,&mode,"");

  //settextstyle(3,0,_T("宋体"));
  settextstyle(16, 0, _T("宋体"));
  setcolor(GREEN);
  outtextxy(20,20,"3D perspective drawing matrix convert");
  for(i=1;i<6;i++)
      printf("\n");
  //printf("input==>ab,bc,H,θ,α: "); /*θ、α输入法提示:Alt+233,Alt+224 */
  //scanf("%f,%f,%f,%f,%f",&b1,&b2,&h,&e,&a);
  b1=15;
  b2=10;
  h=15;
  e=233;
  a=224;
  e=e*3.14159/180.0;
  a=a*3.14159/180.0;
  l=-1*(b2*cos(e)-b1*sin(e))/2;
  m=-(b2*sin(e)+b1*cos(e));
  n=-2*h/3;
  k=b1*sin(e)+b2*cos(e)-b1*cos(e)*tan(a/2)-b2*sin(e)*tan(a/2);
  d=k/(2*tan(a/2));
  q=-1/d;
  tx[0][0]=cos(e);tx[0][3]=q*sin(e);
tx[1][0]=-sin(e);tx[1][3]=q*cos(e);
tx[2][2]=1;
tx[3][0]=1;tx[3][2]=n;tx[3][3]=m*q+1;
 
  setcolor(YELLOW);
  //matrix(tx[0]);
  matrix(tx);
  getch();
  closegraph();
}
void matrix(float t[][4])
{
  float z[N][4],xt0,yt0,ts0;
  int i,j,k;
  for(i=0;i<N;i++)
    for(j=0;j<4;j++)
    {
      z[i][j]=0;
      for(k=0;k<4;k++)
    z[i][j]=z[i][j]+p[i][k]*t[k][j];
    }
      //draw(z[0],300,200,z[3][3]);
	draw(z,300,200,z[3][3]);
}
void draw(float z[][4],float xt0,float yt0,float ts0)
{
  float x[N],y[N];
  int i;
  for(i=0;i<N;i++)
  {
    x[i]=xt0-z[i][0]/z[i][3]*ts0*4;
    y[i]=yt0-z[i][2]/z[i][3]*ts0*4;
  }
  for(i=0;i<1000;i++)
  {
    if(tp[i]==-100) break;
    if(tp[i]==-1)
    {
      i++;
      moveto(x[tp[i]],y[tp[i]]);
    }
    if(tp[i]>=0)
      lineto(x[tp[i]],y[tp[i]]);
  }
}


图解计算机图形学三维变换算法_第1张图片

二 三视图投影变换算法

#include <math.h>
#include <graphics.h>
#include <conio.h>
#include <stdio.h>

void draw(float z[][4],float xt0,float yt0,float ts0);
void matrix(float t[][4]);

#define N 25

float p[N][4]={{0,0,5,1},{0,0,0,1},{40,0,0,1},{40,0,5,1},
           {40,25,5,1},{0,25,5,1},{0,25,0,1},{40,25,0,1},
           {0,25,0,1},{0,0,0,1},{35,5,5,1},{35,5,35,1},
           {35,10,35,1},{35,10,30,1},{35,15,30,1},{35,20,5,1},
           {5,20,5,1},{5,5,5,1},{5,5,35,1},{35,5,35,1},
           {35,10,35,1},{5,10,35,1},{5,10,30,1},{5,15,30,1},
           {35,15,30,1}
          };
int tp[]={-1,0,1,2,3,0,5,6,1,-1,3,4,5,6,7,2,-1,4,7,-1,10,11,12,13,
      14,15,10,-1,17,18,21,22,23,16,17,-1,10,17,-1,11,18,-1,12,21,
      -1,13,22,-1,14,23,-1,15,16,-100
     };
main()
{
  static float tv[4][4],th[4][4],tw[4][4];
  //int driver,mode;
  //driver=DETECT;
  //initgraph(&driver,&mode,"");
  initgraph(640, 480);
  settextstyle(1,0,_T("宋体"));
  setcolor(RED);
  outtextxy(30,20,"3 sides view graphic matrix convert");
  tv[0][0]=1;tv[2][2]=1;tv[3][3]=1;
  th[0][0]=1;th[1][2]=-1;th[3][2]=-10;th[3][3]=1;
  tw[1][0]=-1;tw[2][2]=1;tw[3][0]=-10;tw[3][3]=1;
  setcolor(WHITE);
  //matrix(tv[0]);
  //matrix(th[0]);
  //matrix(tw[0]);
  matrix(tv);
  matrix(th);
  matrix(tw);
  getch();
  closegraph();
}
void matrix(float t[][4])
{
  float z[N][4],xt0,yt0,ts0;
  int i,j,k;
  for(i=0;i<N;i++)
    for(j=0;j<4;j++)
    {
      z[i][j]=0;
      for(k=0;k<4;k++)
    z[i][j]=z[i][j]+p[i][k]*t[k][j];
    }
      //draw(z[0],310,270,4);
	draw(z,310,270,4);
}
void draw(float z[][4],float xt0,float yt0,float ts0)
{
  float x[N],y[N];
  int i;
  for(i=0;i<N;i++)
  {
    x[i]=xt0-z[i][0]*ts0;
    y[i]=yt0-z[i][2]*ts0;
  }
  for(i=0;i<1000;i++)
  {
    if(tp[i]==-100) break;
    if(tp[i]==-1)
    {
      i++;
      moveto(x[tp[i]],y[tp[i]]);
    }
    if(tp[i]>=0)
      lineto(x[tp[i]],y[tp[i]]);
  }                                                 
}


图解计算机图形学三维变换算法_第2张图片

三 三维正轴测投影变换算法

#include <math.h>
#include <graphics.h>
#include <conio.h>
#include <stdio.h>

void draw(float z[][4],float xt0,float yt0,float ts0);
void matrix(float t[][4]);

#define N 18
float p[N][4]={{0,0,0,1},{0,40,0,1},{45,40,0,1},{45,0,0,1},
                 {45,0,8,1},{45,40,8,1},{8,40,8,1},{8,0,8,1},
                 {8,0,28,1},{8,40,28,1},{0,40,28,1},{0,0,28,1},
                 {40,24,8,1},{8,24,8,1},{8,24,24,1},{8,16,24,1},
                 {8,16,8,1},{40,16,8,1}
                 };
int tp []={-1,0,1,2,3,0,5,6,1,-1,3,4,5,6,7,2,-1,4,7,-1,10,11,12,
13,14,15,10,-1,17,18,21,22,23,16,17,-1,10,17,-1,11,18,-1,
12,21,-1,13,22,-1,14,23,-1,15,16,-100};

main()
{
  static float tx[4][4];
  float beta,cita;
  //int driver,mode;
  //driver=DETECT;
  //initgraph(&driver,&mode,"");
  initgraph(640, 480);
  //settextstyle(1,0,_T("宋体"));
  settextstyle(16, 0, _T("宋体"));
  setcolor(BROWN);
  outtextxy(140,20,"3D graphic matrix convert");
  //printf("input==>β, θ: ");  /*β和θ的输入法分别为:Alt+225, Alt +233*/
  //scanf("%f,%f",&beta,&cita);
  beta=225;
  cita=233;
  beta=beta*3.14159/180.0;
  cita=cita*3.14159/180.0;
  tx[0][0]=cos(beta);tx[0][2]=-sin(beta)*sin(cita);
tx[1][0]=-sin(beta);
  tx[1][2]=-cos(beta)*sin(cita);tx[2][2]=cos(cita);
tx[3][3]=1;
  setcolor(CYAN);
  //matrix(tx[0]);
  matrix(tx);
  getch();
  closegraph();
}
void matrix(float t[][4])
{
  float z[N][4],xt0,yt0,ts0;
  int i,j,k;
  for(i=0;i<N;i++)
    for(j=0;j<4;j++)
    {
      z[i][j]=0;
      for(k=0;k<4;k++)
      z[i][j]=z[i][j]+p[i][k]*t[k][j];
    }
    //draw(z[0],300,200,4);
	draw(z,300,200,4);
}
void draw(float z[][4],float xt0,float yt0,float ts0)
{
  float x[N],y[N];
  int i;
  for(i=0;i<N;i++)
  {
    x[i]=xt0-z[i][0]*ts0;
    y[i]=yt0-z[i][2]*ts0;
  }
  for(i=0;i<1000;i++)
  {
    if(tp[i]==-100) break;
    if(tp[i]==-1)
    {
      i++;
      moveto(x[tp[i]],y[tp[i]]);
    }
    if(tp[i]>=0)
      lineto(x[tp[i]],y[tp[i]]);
  }
}


图解计算机图形学三维变换算法_第3张图片


四 相关编程问题

1 二维数组做函数参数

上面三个程序使用了二维数组做函数参数;看一个 二维数组做函数参数 的例子;

 #include <stdio.h>
  
  void print_array(int *array, int len)
  {
      int i = 0;
      for ( ; i < len; i++) {
          printf("%d ",array[i]);
      }
      putchar('\n');
 }
 
 void func(int array[3][10])
 {
     print_array(array[0], 10);
     print_array(array[1], 10);
     print_array(array[2], 10);
     print_array(array[3], 10);
     print_array(array[4], 10);
 }
 
 int main()
 {
     int array[5][10] = {
         {0,1,2,3,4,5,6,7,8,9},
         {10,11,12,13,14,15,16,17,18,19},
         {20,21,22,23,24,25,26,27,28,29},
         {30,31,32,33,34,35,36,37,38,39},
         {40,41,42,43,44,45,46,47,48,49}
     };
     func(array);
     return 0;
 }

图解计算机图形学三维变换算法_第4张图片


2 easyX库对TC函数的改进

settextstyle(1,0,4);

需要改为

settextstyle(16, 0, _T("宋体"));
以及其他改进,参见

easyx帮助手册和

http://www.easyx.cn/skills/View.aspx?id=89



你可能感兴趣的:(三维,计算机图形学,三维透视投影)