计算机图形学(循环菱形、循环嵌套矩形)

实验要求及实现目标:

       

      实验1:(1)观察实验要求可以发现,最外层正方形的相邻两点的横纵坐标分别相加再除以2就得到内层正方形的坐标。

                    (2)通过for循环,利用上层正方形的四个坐标来求下层正方形的坐标,并利用for循环,每循环一次就改变输出图形的颜色。为了避免无限循环,当最内层的正方边                              长小于预先设定的值时,就退出循环。

      实验2:(1)实验所要求的图形由菱形组成,但是红色菱形与绿色菱形的边长相等,夹角可能不同,但二者夹角和为90度。

                     (2)通过预先设定的边长和角度,利用三角函数求出菱形的各点的坐标。通过for循环,改变角度并循环输出每一个菱形。

My  solution:

循环菱形:

#include<GL/glut.h>
#include<cmath>
#include<cstdio>
#include<iostream>
using namespace std;
double reddegree=45;//红色菱形的夹角度数
double sidelength=0.4;//菱形边长
const double PI=3.1415926;
void myDisplay(void)
{
   glClearColor(0.0,0.0,0.0,0.0);
   glClear(GL_COLOR_BUFFER_BIT);

   glColor3f(1.0f, 1.0f, 1.0f);
   glRectf(-0.85f,-0.85f,0.85f,0.85f);

   double redx,redy,greenx,greeny,dglength,drlength;
   redx=sin((reddegree*1.0/2)/180*PI)*sidelength;//最上面的菱形与原点相邻右顶点的,x,y坐标
   redy=cos((reddegree*1.0/2)/180*PI)*sidelength;
   greenx=greeny=(redx+redy);//最右面绿菱形的顶点坐标
   dglength=sqrt(2*greenx*greenx);//绿色菱形最长对角线
   drlength=2*redy;//红色菱形最长对角线
   int count=1;//纪录循环次数
   double nowdegree1=-reddegree/2,nowdegree2=0;//从最右边的红色菱形开始旋转
   double dx,dy;
   dx=sidelength*cos(nowdegree1/180*PI);//中间变量,用来记录菱形中的第二个点坐标
   dy=sidelength*sin(nowdegree1/180*PI);
   while(count<9)//每循环一次输出一个菱形。每次循环由于角度的增加,而边长始终不变,可以利用三角函数求得每次循环中的菱形各点的坐标 
   {
	   if(count%2==1)//选择颜色
		   glColor3f(1.0f, 0.0f, 0.0f);
	   else
		   glColor3f(0.0f, 1.0f, 0.0f);

       glBegin (GL_POLYGON);
       glVertex2d(0.0,0.0);//四边形第一个点
	   glVertex2d(dx,dy);//四边形第2个点
	   if(count%2==1)//判断输出第3个点:绿色菱形顶点,还是红色菱形顶点。因为预先设定的角度不同,红色菱形和绿色菱形可能不一样大
	   {
		   float cx,cy;
		   cx=drlength*cos(nowdegree2/180*PI);
		   cy=drlength*sin(nowdegree2/180*PI);
		   glVertex2d(cx,cy);//红色菱形顶点
	   }
	   //    glVertex2d(drlength*cos(nowdegree2/180*PI),drlength*sin(nowdegree2/180*PI));//红色菱形顶点
       else
	   {
           float cx,cy;
		   cx=dglength*cos(nowdegree2/180*PI);
		   cy=dglength*sin(nowdegree2/180*PI);
		   glVertex2d(cx,cy);//绿色菱形顶点
	   
	   }
		  // glVertex2d(dglength*cos(nowdegree2/180*PI),dglength*sin(nowdegree2/180*PI));//绿色菱形顶点
	   if(count%2==1)
		   nowdegree1+=reddegree;
	   else
		   nowdegree1+=(90-reddegree);
	   dx=sidelength*cos((nowdegree1)/180*PI);//计算第4个点的坐标,同时该点也是下一次循环输出的菱形的第二个点的坐标
       dy=sidelength*sin(nowdegree1/180*PI);
	   glVertex2d(dx,dy);//第四个点
       nowdegree2+=45;
       count++;
       glEnd();
	   glFlush();
   }
}

int main(int argc,char *argv[])
{
    glutInit(&argc, argv);
	glutInitDisplayMode( GLUT_RGB | GLUT_SINGLE);
	glutInitWindowPosition(100, 100);
	glutInitWindowSize(400, 400);
	glutCreateWindow("Hello World!");
	glutDisplayFunc(&myDisplay);
    glutMainLoop();
	return 0;

}

循环矩形:
#include<GL/glut.h>
#include<iostream>
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const float initlength=0.6;//最外边正方形长度
const float finalength=0.03;//最里层正方形长度
void myDisplay(void)
{
	glClearColor(0.0,0.0,0.0,0.0);
	glClear(GL_COLOR_BUFFER_BIT);

//	glBegin(GL_POLYGON);
	float a_x,a_y,b_x,b_y,c_x,c_y,d_x,d_y;//四个坐标
    float a_x1,a_y1,b_x1,b_y1,c_x1,c_y1,d_x1,d_y1;//辅助转换坐标
	int colorchange=0;//控制颜色循环
	float exit01,exit02;//循环的出口。因为在旋转过程中,a可能会在坐标轴上,此时与原点的横坐标或纵坐标差值为0,因此需
	                    //同时需要同时比较横坐标、纵坐标的差值当二者都很小时,说明a足够接近原点,跳出循环
	a_x=d_x=-initlength;
	b_x=c_x=initlength;
	a_y=b_y=initlength;
	c_y=d_y=-initlength;
    exit01=a_x;//设置循环出口,当足够接近原点,就结束循环;
	exit02=a_y;
	if(exit01<0)
		exit01=-exit01;
	if(exit02<0)
		exit02=-exit02;
	while(exit01>finalength||exit02>finalength)//设置循环出口,当最内层边长足够小就结束循环;
	{

		switch(colorchange)
		 {
			 case 0:  glColor3f(1.0f,1.0f,1.0f);break;//白色
			 case 1:  glColor3f(1.0f,0.0f,1.0f);break;//粉色=红+蓝   
			 case 2:  glColor3f(0.0f,0.0f,1.0f);break;//蓝色
			 case 3:  glColor3f(1.0f,1.0f,0.0f);break;//(黄=红+绿)
			 case 4:  glColor3f(0.0f,1.0f,0.0f);break;//绿色
			 default: glColor3f(1.0f,0.0f,0.0f);//红色
		 }
    
	 glBegin(GL_POLYGON);
	  //glBegin(GL_LINE_LOOP);//矩形框
     glVertex2f(a_x,a_y);//输出正方形四个点
	 glVertex2f(b_x,b_y);
	 glVertex2f(c_x,c_y);
     glVertex2f(d_x,d_y);
     glEnd();

	 glFlush();

     a_x1=(a_x+b_x)/2;  a_y1=(a_y+b_y)/2;//变换坐标
	 b_x1=(b_x+c_x)/2;  b_y1=(b_y+c_y)/2;
	 c_x1=(c_x+d_x)/2;  c_y1=(c_y+d_y)/2;
	 d_x1=(d_x+a_x)/2;  d_y1=(d_y+a_y)/2;
	 
	 a_x=a_x1;  a_y=a_y1;//重新赋值
	 b_x=b_x1;  b_y=b_y1;
	 c_x=c_x1;  c_y=c_y1;
	 d_x=d_x1;  d_y=d_y1;

	 colorchange++;
	 colorchange%=6;//控制6种颜色变化

     exit01=a_x;//设置循环出口,当足够接近原点,就结束循环;
	 exit02=a_y;
	 if(exit01<0)
		exit01=-exit01;
	 if(exit02<0)
		exit02=-exit02;
	}
}
 int main(int argc,char *argv[])
 {
	 glutInit(&argc,argv);
	 glutInitDisplayMode(GLUT_RGB|GLUT_SINGLE);
	 glutInitWindowPosition(100,100);
	 glutInitWindowSize(400,400);
	 glutCreateWindow("Hello World!");
	 glutDisplayFunc(&myDisplay);
	 glutMainLoop();
	 return 0;
 }



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值