图形学作业与答案 doc- 精品课程建设平台

更新时间:2024-06-23 21:26:01 阅读量: 综合文库 文档下载

说明:文章内容仅供预览,部分内容可能不全。下载后的文档,内容与下面显示的完全一致。下载之前请确认下面内容是否您想要的,是否完整无缺。

图形学作业与答案.doc - 精品课程建设平台

摘要:优缺点:边缘填充算法的数据结构和程序结构都简单的多,缺点:执行时许对帧缓冲器中的大批元素反复赋值,故速度不必扫描线算法快,另外,如果区域内原来有其他的颜色, ... 关键词:算法,数据结构 类别:专题技术

来源:牛档搜索(Niudown.COM)

本文系牛档搜索(Niudown.COM)根据用户的指令自动搜索的结果,文中内涉及到的资料均来自互联网,用于学习交流经验,作品其著作权归原作者所有。不代表牛档搜索(Niudown.COM)赞成本文的内容或立场,牛档搜索(Niudown.COM)不对其付相应的法律责任!

第三章作业与答案

3.1 试证:若把(3.30)改为

??xi?1??cos??y???b?i?1??sin??a则该式可用于产生椭圆

a??sin???x?x??x?icb??c? ???cos???yi?yc??yc??(x?xc)2/a2?(y?yc)2/b2?1

上的点,从而可用于绘椭圆。 证明:将待证式展开得:

xi+1 = xc + (xi-xc)cos?- (yi-yc)?asin? bayi+1 = yc + (xi-xc)sin? + (yi-yc)cos?

b该式即为计算椭圆内接多边形顶点的递推公式,并可知椭圆的长短轴分别为 a和b,中心点为(xc,yc),对称轴平行于坐标轴,即: (x?xc)2/a2?(y?yc)2/b2?1 证毕。

3.2 用二元函数的泰勒(Taylor)展式证明(3.16),并把正负法推展到绘椭圆

(x?xc)2/a2?(y?yc)2/b2?1

证明:二元函数的泰勒(Taylor)展开式:

设函数f(x,y)在点(x,y)某一邻域内连续,且有直至n+1阶的连续偏导数,给xi以增量?x;给yi以增量?y,使连接点(xi,yi)、(xi+?x,yi+?y)的直线段仍在点(xi,yi)的邻域内,则可将函数值f(xi+?x,yi+?y)近似表示为?x,?y 的n 次多项式:

f(xi+?x,yi+?y)=f(xi,yi)+( ?x

??+?y)f(xi,yi)+ ?x?y1?1??2

( ?x+?y)·f(xi,yi)+…+( ?x+?

?x?x2!n!?yy

?n

)·f(xi,yi)+ Rn ?y 由此所产生的误差Rn是一个比?x2??y2高于n阶的无穷小。

由圆的方程:(x-xc) 2+ (y-yc) 2 - R2 =0 2(xi-xc) 当f(xi,yi)≤0时 ( ?x=0

-2(yi-yc) 当f(xi,yi)>0时 ?x=0,?y=-1

21?1?2 2?f( ?x+?y)·f(xi,yi)= ( ?x

?x2!2!?x?y??f?+?y)f(xi,yi)= ?x

?x?x?y?xi

+?y

?f?y?yi= ?

x=1,?y

?xi+2?x?y

?f?x?xi

?f?y?yi+?

?f2y?y2

?yi)

1 当f(xi,yi)≤0时, ?x=1,?y=0

=

1 当f(xi,yi) >0时, ?x=0,?y=-1

F(xi,yi)+2(xi-xc)+1当f(xi,yi)≤0

时f(xi+?x,yi+?y)=F(xi+1,yi+1) ≈

F(xi,yi)-2(yi-yc)+1 当f(xi,yi) >0时

证毕。

由椭圆方程:(x?xc)2/a2?(y?yc)2/b2?1?0 ;转化为:

b2(x?xc)2?a2(y?yc)2?a2b2?0

同理推出椭圆正负法(不分上、下区的简单)递推公式为:

F(xi,yi)+2b2(xi-xc)+b2当f(xi,yi)≤0

f(xi+?x,yi+?y)=F(xi+1,yi+1)≈

F(xi,yi)-2 a2 (yi-yc) +a2 当f(xi,yi)>0

3.3 试证:若把(3.24)改为

a??cos??sin???xi?xc??xc??xi?1??b???y???b???y? y?yc??i?1??sin??c?cos???i?a?则该式可用于产生椭圆

(x?xc)2/a2?(y?yc)2/b2?1

上的点,从而可用于绘椭圆。 证明:假设椭圆的中心在(xc,yc),长短轴分别为a,b,对称轴平行于坐标轴,则椭圆的参数方程为

x?acos??xc,y?bsin??yc

则顶点序列的第I个顶点Pi的坐标为(xi ,yi)(ao,则下一个顶点cs?i,bnis?i)Pi+1的坐标为(xi+1 ,yi+1)应该满足

xi?1?acos(?i??)?xc, yi?1?bsin(?i??) ?yc 经过整理可得

xi?1?xc?a(cos?cos??sin?sin?)yi?1?yc?b(sin?cos??cos?sin?)

因为xi?acos?i?xc, yi?bsin?i ?yc 整理可得

a??cos? -sin???xi?xc??xc??xi?1??b???,这就是计算椭圆的第推公式 ???y???a??i?1??sin? cos???yi?yc??yc????b?

3.4 多边形的顶点和点阵表示各有什么优点?

答:顶点表示是用多边形的顶点的序列来描述多边形,该表示几何意义强、占内存少。(但他不能直观地说明哪些像素在多边形内)。点阵表示用位于多边形内的像素的集合来描述多边形。该方法虽然没有多边形的几何信息,是面着色所需要的图像表示形式。

3.5多边形扫描填充的扫描线算法利用了区域的连续性、扫描线连续性和边的连续性,在数据结构和算法中各体现在何处?

答:ET数据结构体现了区域的连贯性、边的连贯性。AEL体现了扫描线的连贯性、边的连贯性。AEL的动态增删及排序集中体现了扫描线的连贯性和边的连贯性。

3.6任意给定五边形的五个顶点坐标,利用多边形填充的扫描线算法,编写程序生成一个实心五边形。

答:

typedef struct tEdge{ int yUpper; int xIntersect; float dxPerScan; struct tEdge * next; }Edge;

void insertEdge(Edge * list,Edge * edge) {

Edge * p ,* q=list; p=q->next;

while(p!=NULL){

if(edge->xIntersectxIntersect) p=NULL; else{ q=p;

p=p->next; } }

edge->next=q->next; q->next=edge; }

int yNext(int k,int cnt,CPoint *points) {

int j;

if((k+1)>(cnt-1)) j=0; else

j=k+1;

while(points[k].y==points[j].y) if((j+1)>(cnt-1)) j=0; else j++;

return(points[j].y); }

void makeEdgerec(CPoint lower,CPoint upper,int yComp,Edge edge,Edge *edges[])

{

edge->dxPerScan=(float)(upper.x-lower.x)/(upper.y-lower.y); edge->xIntersect=lower.x; if(upper.y

edge->yUpper=upper.y-1; else

edge->yUpper=upper.y;

insertEdge(edges[lower.y],edge); }

void buildEdgeList(int cnt,CPoint *points,Edge * edges[]) {

Edge *edge; CPoint p1,p2;

int i,yprev=points[cnt-2].y; p1.x=points[cnt-1].x; p1.y=points[cnt-1].y; for(i=0;i

*

if(p1.y!=p2.y){

edge=(Edge*)malloc(sizeof(Edge)); if(p1.y

makeEdgerec(p1,p2,yNext(i,cnt,points),edge,edges); else

makeEdgerec(p2,p1,yprev,edge,edges); }

yprev=p1.y; p1=p2; } }

void buildActiveList(int scan,Edge * active,Edge *edges[]) {

Edge * p,* q;

p=edges[scan]->next; while(p){

q=p->next;

insertEdge(active,p); p=q; } }

void fillScan(int scan,Edge * active,CDC *pDC) {

Edge *p1,*p2; int i;

p1=active->next; while(p1){

p2=p1->next;

for(i=p1->xIntersect;ixIntersect;i++) pDC->SetPixel((int)i,scan,RGB(255,0,0)); p1=p2->next; } }

void deleteAfter(Edge * q) {

Edge * p=q->next; q->next=p->next; free(p); }

void updateActiveList(int scan,Edge * active) {

Edge *q=active,*p=active->next; while(p){

if(scan>=p->yUpper) {

p=p->next;

deleteAfter(q); }

else{

p->xIntersect=p->xIntersect+p->dxPerScan; q=p;p=p->next;

} } }

void resortActiveList(Edge * active) {

Edge *q,*p=active->next; active->next=NULL; while(p){

q=p->next;

insertEdge(active,p); p=q; } }

void scanFill(int cnt,CPoint * points,CDC *pDC) {

Edge * edges[WINDOW_HEIGHT],* active; int i,scan;

for(i=0;i

edges[i]=(Edge*)malloc(sizeof(Edge)); edges[i]->next=NULL; }

buildEdgeList(cnt,points,edges); active=(Edge*) malloc(sizeof(Edge)); active->next=NULL;

for(scan=0;scannext){

fillScan(scan,active,pDC); updateActiveList(scan,active); resortActiveList(active); } } }

3.7简述边缘填充算法和边界标志算法的基本思想、步骤以及优缺点。

答:边缘填充基本思想:对于多边形P的每一非水平边PiPi+1(I=0,1,┅n)

上的各个像素做向右求反运算即可.优缺点:边缘填充算法的数据结构和程序结构都简单的多,缺点:执行时许对帧缓冲器中的大批元素反复赋值,故速度不必扫描线算法快,另外,如果区域内原来有其他的颜色,也不能保证最后的区域内的颜色是多边形的颜色。 边界标志算法的基本思想:首先用一种特殊的颜色在帧缓冲器中将多边形的边界(水平边的部分边界除外)勾画出来。然后再把位于多边形内的各个像素着上所需的颜色

步骤1:以值为boundary-color 的特殊颜色勾画多边形P的边界。设多边形顶点

为Pi= (xi, yi),0≤i≤n, xi, yi均为整数;置Pn+1=P0。每一条扫描线上着上这种特殊颜色的点的个数必定是偶数(包括零)。

?步骤2:设interior_point 是一布尔变量。对每一条扫描线从左到右进行搜索,

如果当前是像素位于多边形P内,则interior_point=true,需要填上值为polygon_color的颜色;否则该像素在多边形P外,需要填上值为background_color的颜色

优缺点:避免了对帧缓冲器中的大量元素的多次赋值,但需逐条扫描线并对帧缓

冲器中的元素进行搜索和比较。

3.8区域种子填充在图形学应用中有何作用?

答案:区域种子填充在只改变区域的颜色属性,不改变区域的表示方法时使用,尤其适用于交互改变区域颜色时,比如:墨水瓶、油漆桶等。

3.9请简要叙述种子算法的基本思想及其用堆栈实现八连通算法原理。 答:种子算法充分利用了递归调用的机理,在前一种子点确定并变为新颜色后,

按照自身调用的八向顺序依次查找新的种子点,找到即变为新颜色,继续下一种子的查找。未查的方向被压栈保存,等退栈时继续查找,最终完成蔓延至整个区域所有点都变为新颜色。

3.10简述几种主要反走样算法的基本思想及优缺点。

答:1提高分辨率基本思想:提高硬件的分辨率。优缺点::能在非反走样算法

的基础上进行反走样的工作。

2线段反走样算法的基本思想:因为线段是有宽度的,将向段看作是狭长的矩形,具有一定的面积,当线段通过某象素时,可以求出两者面积得交,之后根据每个象素与线段相交部分的面积只决定该象素的颜色值或灰度值 优缺点:极大改善了线段显示时的线形质量,但是由于要计算面积,使得计算量大大增加,不适合动态的交互式图形显示。

3多边形反走样算法基本思想:采用反走样线段的思想来改善多边形边界的显示质量。当某象素玉多边形区域相交时,求出两者相交的面积,然后以此面积值来决定该象素的颜色值或灰度值。 优缺点

3.11扩展Bresenham算法,实现一个反走样程序,从而调整直线路径附近的像素亮度。

m = 2*(ye–ys)/(xe-xs); y = ys; x= xs; e = m-0.5; nloop =(xe-xs)/2;

for (i=1;i<=nloop;i++) {

if( e>1){ DrawPixels(pattern4,x,y); //gl_Point(x+1,y+1); gl_Point(x+2,y+2); y= y+2; e= e-2; } else

if (e>0 && e<=1) { if (e>0.5) Draw Pixels(pattern3,x,y); else Draw Pixels(pattern2,x,y); y = y+1; e = e-1; } else

Draw Pixels(pattern1,x,y); e = e+m; x = x+2; }//end for

gl_Point(xe,ye);

3.12在区域填充的扫描线算法中加上反走样程序,使用连续性来减少连续扫描线上的计算量。

答案:

deltax=xe-xs; deltay=ye-ys; m=deltay/deltax; y=ys; x=xs; a=1-m; d=0.5;

for(I=1;I

setpixel(framebuffer,x,y,d); if(d>=a) {

y=y+1; d=d-a;

}

else d=d+m;

x=x+1; }

第四章作业与答案

第四章 变换

习题

4.1 下面有关平面几何投影的叙述中,哪些是正确的?

(1). 平面几何投影中,透视投影的投影中心到投影平面的距离是有限的。(Y) (2). 平面几何投影中,一组平行线的投影仍保持平行。(N) (3). 平行投影与透视投影相比,视觉效果更有真实感,而且能真实地反映物体的精确集合尺

寸与形状。(N)

(4). 在三维空间中的平行投影变换不可能产生灭点。(Y) 4.2写出下列二维图形变换的变换矩阵:

(1). 沿x轴正向移动一个绘图单位,同时,沿y轴负向移动一个绘图单位。

?x'??101??x?x'10x1?????????????y?

y'?01?1,???y'??01??y???1????????????????1??001??1???????(2). 绕原点逆时针旋转90度

?x'??0?1??x??y'???10??y? ??????(3). 沿x轴负向移动2个绘图单位,同时,沿y轴正向移动2个绘图单位。

?x'??10?2??x??x'??10??x???2??????y?

y'?012,???y'??01??y??2????????????????1??001??1???????(4). 坐标轴为对称轴的反射图形。

?x'??10??x??x'???10??x?X轴为对称轴??????y?,y轴为对称轴?y'???01??y?

y'0?1????????????(5). y=x为对称轴的反射图形。

?x'??01??x??y'???10??y? ??????4.3证明三维变换矩阵的乘积对以下运算顺序是可交换的: (1). 任意两个连续平移。

?x'??1?y'??0?????z'??0????1??0?x\??1?y\??0?????z\??0????1??0010001000?x'??100?x??x??1?010?y??y??00?y'????????1?z'??001?z??z??0??????01??0001??1??00?x??100?x'??x??1?010?y'??y??00?y????????1?z??001?z'??z??0??????01??0001??1??0010001000?x??x'??x??y?0?y??y'????

1?z??z'??z????01??1?0?x'??x??x??y?0?y'??y????

1?z'??z??z????01??1??x'??x\?????由上面两式可得:y'?y\ ??????z'????z\??(2). 任意两个连续的放缩变换。

?x'??sx?y'???0?????z'????0?x\??sx?y\???0?????z\????0'\0s\y00s'y0'0??sx??0??0??s\z??00s'y00s\y0'0??x??s\xsx???0???y???0'?sz?z??????0'\0??x??sxsx???0???y???0????0s\z??z??0's\ysy00s'ys\y00??x???0???y? '???s\zsz??z?0??x???0???y? '\?szsz???z??0??s\x??0??0'??sz??0?x'??x\?????由上两式可得:y'=y\ ??????z\???z'???(3). 任意两个连续的关于任一坐标轴的旋转。

以绕x轴为例,绕其他轴旋转同理可得

?x'??cos??y'???sin??????z'????0?x\??cos??y\???sin??????z\????0?sin?cos?0?sin?cos?00??cos??sin?0???1????00??cos??sin?0???1????0?sin?cos?0?sin?cos?00??x??cos(???)?sin(???)0??x??y???sin(???)cos(???)0??y?0????????1?001????z???????z??0??x??cos(???)?sin(???)0??x??y???sin(???)cos(???)0??y?0????????1?001????z???????z???x'??x\?????由上两式可得:y'=y\ ??????z\???z'???4.4给定方向(α,β,γ),试推导出该方向以放缩因子为s进行缩放,然后再绕该方向旋转90

度的变换矩阵。

??????2??2?????2??2??0??????????22?????????2??2??2222?2??222?2??2?????2??2??2???????2??2?????????0?10???????100??????2??2??2??2??2?2??2??2?????001?????????2222???2??2???????????????22222??2??2?2??2??2??2??2??2???s??2?????2??2???2??2??0?2??2??2??2??2???????0??2???2??2??00?s?2??2??20?????0???s???2??2??2?0

4.5推导以直线ax+by+c=0为对称轴的二维对称变换矩阵。

a2?1?()?b?a?()2?1?b?2a??b??(a)2?1?b?0??????a()2?1ba()2?1ba()2?1b02ab2ac?b2?a2?()?1?b?2c???b? a()2?1??b1???????4.6试从三维图形几何变换的一般表达式推倒出以F(xf,yf,zf)为参考点,x,y,z轴3个方向的比

例因子分别为sx,sy,sz的比例变换矩阵。

?x'??1?y'??0?????z'??0????1??001000xf??sx000??1???0yf???0sy00??01zf??00sz0??0????01??0001??001000?xf??x???0?yf???y?

1?zf??z????01??1?4.7请写出当透视投影中心为原点,投影平面为z=3的透视投影矩阵,并求端点为A(5,15,25)和B(10,20,30)的线段在该投影平面的投影。

?xq??300??x????????yq???030??y?,xp?xq /q,yp?yq /q.A点在该平面上的投影为(3/5,9/5,3)?q??001??z?????????13?3?y?x?B点在该平面上的投影为(1,2,3),投影线段的方程为?22,x?[,1]

5?z?3?4.8将梁友栋-Barsky裁减算法改写成多边形裁减算法。

答:梁友栋-Barsky裁减算法是线段裁减,如果对多边形的每条边用该方法,会使原来封闭的多边形变成不封闭或是一些离散的线段。为此可以将梁友栋-Barsky裁减算法改写成多边形裁减算法。

包含PiPi+1的直线与窗口4条边界相交,其中两个是潜在的进入交点,另外两个是潜在的离开交点,计算出交点的参数值,并分别记为t_in1,t_in2,t_out1,t_out2.跨越窗口直线有2种情形

12

for(每条边e){ 确定边的方向

用此来确定包含线首先与裁减区域的哪条边界线相交 寻找退出点的t值 if(t_out2>0)

寻找第2个进入点的t值 if(t_in2>t_out1){

if (0

output_vert(turning_vertex); }else{

If (0=t_in2){ If(0<=t_in2)

Output_vert(适当的面交点); Else

Output_vert(起始顶点); If (1>=t_out1)

Output_vert(适当的面交点); Else

Output_vert(终止顶点); } }

If(0

Output_vert(适应的窗口角点); }/*对每条边*/

4.9对Sutherland-Hodgman算法做改进,使其能处理图4.28所示的情况。

答:Sutherland-Hodgman算法是用每条裁减边对多边形裁剪,得到一个顶点序列,作为下一条裁剪边处理过程的输入。为使其能处理4.28所示情况,需要在一条边对多边形进行裁剪时设置一个记录,将窗口与边的交点依序记录下来,交点两两配对,每两个对应一个多边形。 4.10将梁友栋-Barsky裁减算法扩展到三维空间时,在规范的平行投影视口中确定其需要的不等式。

p1?(x1,y1,z1),p1?(x2,y2,z2)为线段的终点,线段的参数表达式为

?x?x1?(x2?x1)u??y?y1?(y2?y1)u,u??0,1? ?z?z?(z?z)u121??xmin??x1?(x2?x1)u??xmax?在规范的平行投影视口中的点满足下列不等式?ymin??y1?(y2?y1)u??ymax

?z??z?(z?z)u??z121max?minxmin?ymin?zmin?0,xmax?ymax?zmax?1。

?p1???x,q1?x1(左)?p??x,q?1?x(右)21?2??p3???y,q3?y1(下)上述不等式可以写为pk? u??qk,k?1..6?p??y,q?1?y(上)41?4?p5???z,q5?z1(前)???p2??z,q6?1?z1(后)4.11用OpenGL编写程序以实现一个立方体的平移,放缩和旋转变换

void CExam2View::draw_cuboid(GLdouble a, GLdouble b, GLdouble c)

{

glColor3f(0,0,0);

glBegin(GL_LINE_LOOP); glVertex3f(0,b,0); glVertex3f(0,b,c); glVertex3f(a,b,c); glVertex3f(a,b,0); glEnd();

glBegin(GL_LINE_LOOP); glVertex3f(a,0,0); glVertex3f(a,b,0); glVertex3f(a,b,c); glVertex3f(a,0,c); glEnd();

glBegin(GL_LINE_LOOP); glVertex3f(0,0,c); glVertex3f(a,0,c); glVertex3f(a,b,c); glVertex3f(0,b,c); glEnd();

glEnable(GL_LINE_STIPPLE);//线型设置 glLineStipple(1,0xF0F0);//虚线 glBegin(GL_LINES);//点按照线段连接 glVertex3f(0,0,0);

glVertex3f(a,0,0); glVertex3f(0,0,0); glVertex3f(0,b,0); glVertex3f(0,0,0); glVertex3f(0,0,c); glEnd();

glDisable(GL_LINE_STIPPLE); SwapBuffers(m_hDC); }

void CExam2View::draw_coord() {

glLineWidth(1);

glEnable(GL_LINE_STIPPLE);//线型设置 glLineStipple(1,0xF0F0);//虚线 glBegin(GL_LINES); glVertex3f(0,0,0); glVertex3f(7,0,0); glVertex3f(0,0,0); glVertex3f(0,7,0); glVertex3f(0,0,0); glVertex3f(0,0,7); glEnd();

glDisable(GL_LINE_STIPPLE); }

void CExam2View::OnDraw(CDC* pDC) {

CExam2Doc* pDoc = GetDocument(); ASSERT_VALID(pDoc); glClearColor(1,1,1,1);

glClear(GL_COLOR_BUFFER_BIT); glLoadIdentity();

gluLookAt(5,5.5,7,0,0,0,0,0,1);//视点变换的视点 glColor3f(1,0,0); draw_coord(); glPushMatrix(); if(c_mode==1)

glTranslatef(1.5,0,0);// 平移 if(c_mode==2)

glScalef(1.1,1.2,1);//缩放 if(c_mode==3)

glRotatef(30,0,1,0);//旋转 draw_cuboid(4,4,4); glPopMatrix();

ii = *ptr;

else if (j == 1) jj = *ptr; ptr++; }

printf (\

board[ii][jj] = (board[ii][jj] + 1) % 2; } }

#define BUFSIZE 512

void pickSquares(int button, int state, int x, int y) {

GLuint selectBuf[BUFSIZE]; GLint hits;

GLint viewport[4];

if (button != GLUT_LEFT_BUTTON || state != GLUT_DOWN) return;

glGetIntegerv (GL_VIEWPORT, viewport); glSelectBuffer (BUFSIZE, selectBuf); (void) glRenderMode (GL_SELECT); glInitNames(); glPushName(0);

glMatrixMode (GL_PROJECTION); glPushMatrix (); glLoadIdentity ();

gluPickMatrix ((GLdouble) x, (GLdouble) (viewport[3] - y),5.0, 5.0, viewport); gluOrtho2D (0.0, 2.0, 0.0, 2.0); drawSquares (GL_SELECT);

glMatrixMode (GL_PROJECTION); glPopMatrix (); glFlush ();

hits = glRenderMode (GL_RENDER); processHits (hits, selectBuf); glutPostRedisplay(); }

void display(void) {

glClear(GL_COLOR_BUFFER_BIT); drawSquares (GL_RENDER); glFlush(); }

void reshape(int w, int h) {

glViewport(0, 0, w, h);

glMatrixMode(GL_PROJECTION); glLoadIdentity();

gluOrtho2D (0.0, 2.0, 0.0, 2.0); glMatrixMode(GL_MODELVIEW); glLoadIdentity(); }

int main(int argc, char** argv) {

glutInit(&argc, argv);

glutInitDisplayMode (GLUT_SINGLE | GLUT_RGB); glutInitWindowSize (200, 200); glutInitWindowPosition (100, 100); glutCreateWindow (argv[0]); init ();

glutMouseFunc (pickSquares); glutReshapeFunc (reshape); glutDisplayFunc(display); glutMainLoop(); return 0; }

6.10编写程序,绘制三个基本图元,并在反馈模式下输出这些图元的三维坐标反馈信息。 #include #include #include void init(void) {

glEnable(GL_LIGHTING); glEnable(GL_LIGHT0); }

void drawGeometry (GLenum mode) {

glBegin (GL_LINE_STRIP); glNormal3f (0.0, 0.0, 1.0); glVertex3f (30.0, 30.0, 0.0); glVertex3f (50.0, 60.0, 0.0); glVertex3f (70.0, 40.0, 0.0); glEnd ();

if (mode == GL_FEEDBACK) glPassThrough (1.0); glBegin (GL_POINTS);

glVertex3f (-100.0, -100.0, -100.0); /* will be clipped */ glEnd ();

if (mode == GL_FEEDBACK) glPassThrough (2.0);

glBegin (GL_POINTS);

glNormal3f (0.0, 0.0, 1.0); glVertex3f (50.0, 50.0, 0.0); glEnd (); }

void print3DcolorVertex (GLint size, GLint *count, GLfloat *buffer) {

int i;

printf (\

for (i = 0; i < 7; i++) {

printf (\*count = *count - 1; }

printf (\}

void printBuffer(GLint size, GLfloat *buffer) {

GLint count; GLfloat token; count = size; while (count) {

token = buffer[size-count]; count--; if (token == GL_PASS_THROUGH_TOKEN) { printf (\

printf (\count--; }

else if (token == GL_POINT_TOKEN) { printf (\

print3DcolorVertex (size, &count, buffer); }

else if (token == GL_LINE_TOKEN) { printf (\

print3DcolorVertex (size, &count, buffer); print3DcolorVertex (size, &count, buffer); }

else if (token == GL_LINE_RESET_TOKEN) { printf (\

print3DcolorVertex (size, &count, buffer); print3DcolorVertex (size, &count, buffer); } } }

void display(void) {

GLfloat feedBuffer[1024]; GLint size;

glMatrixMode (GL_PROJECTION); glLoadIdentity ();

glOrtho (0.0, 100.0, 0.0, 100.0, 0.0, 1.0); glClearColor (0.0, 0.0, 0.0, 0.0); glClear(GL_COLOR_BUFFER_BIT); drawGeometry (GL_RENDER);

glFeedbackBuffer (1024, GL_3D_COLOR, feedBuffer); (void) glRenderMode (GL_FEEDBACK); drawGeometry (GL_FEEDBACK);

size = glRenderMode (GL_RENDER); printBuffer (size, feedBuffer); }

int main(int argc, char** argv) {

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_SINGLE | GLUT_RGB); glutInitWindowSize (100, 100); glutInitWindowPosition (100, 100); glutCreateWindow(argv[0]); init();

glutDisplayFunc(display); glutMainLoop(); return 0; }

本文来源:https://www.bwwdw.com/article/fvv3.html

Top