视图和模型变换

视图变换,是指变换照相机的位置,角度。
模型变换,是指变换被照物体的位置,角度。

这两个变换,都会影响最终图形中,物体的位置,角度。而这两个变换,可以达到相同的效果。比如,你想要一个倒着的水杯图形,可以把你自己倒立,这样看到的水杯就是倒立的了。或者把水杯倒立,自己直立,也能看到倒立的水杯。
这里写图片描述
如图所示,这两种变换,可以看做达到目的的不同途径。甚至可以同时使用视图变换和模型变换,只要最终拿到了我们想要的图像就可以了。至于使用的是视图变换,还是模型变换,看我们理解问题的角度。

3.2.1 对变换进行思考

变换顺序,对最终的结果影响很大。
看下面的例子:
这里写图片描述
图中有两个操作,旋转和移动。一个是沿原点绕z轴逆时针旋转45度,另一个是沿x轴向下平移。左图中,是先旋转,再移动,物体最终在x轴上。右图中,是先移动,再旋转,物体最终在x=y轴上。变换顺序不同,导致物体最终位置不同,这就是变换顺序的影响。

变换顺序,在OpenGL中的具体实现。
在OpenGL中,所有的变换,都是通过矩阵来实现的。一个矩阵,表示一个或多个变换。模型视图变换,是通过模型视图矩阵来实现的。由于这个矩阵经常变换,需要进行管理,OpenGL中是通过矩阵堆栈来对矩阵进行管理的。

当前模型视图矩阵如果用C来表示,在当前模型视图基础上,进行一个变换,这个变换使用的矩阵为M。那么一个顶点v的变换之后的坐标为CMv。也就是说,M变换先作用于顶点v,然后再是当前模型视图矩阵C。

看下面的例子:

glMatrixMode(GL_MODELVIEW);
glLoadIndentity();
glMultMatrixf(N);       //变换N
glMultMatrixf(M); //变换M glMultMatrixf(L); //变换L glBegin(GL_POINTS); glVertex3f(v); glEnd();
 

这段代码中,模型视图矩阵按顺序分别包含了I, N, NM,最后是NML,其中I表示单位矩阵。经过变换的顶点是NMLv。因此,顶点变换就是N(M(Lv)),也就是说,v首先与L相乘,Lv再与M相乘,MLv再与N相乘,而不是按它们指定的顺序出现的。

全局固定坐标系

图3-4中,左图中的先旋转,再平移,代码实现如下:

glMatrixMode(GL_MODELVIEW);
glLoadIdentity();
glMultMatrixf(T);   //平移
glMultMatrixf(R); //旋转 draw_the_object();

只要记住一点,物体的变换顺序,和矩阵的出现顺序,正好相反。

局部移动坐标系统

这个通常用于模型的关节控制。比如机器人手臂。比如画汽车轮子上的螺钉,这个螺钉的位置,相对于汽车轮子,这个轮子上建立的坐标系,叫局部移动坐标系。而轮子的位置,又是相对于汽车本身,最后,汽车本身,是在全局坐标系中指定。

3.2.2 模型变换

模型变换,主要涉及三个函数,移动、旋转、缩放。有了这三个函数的组合,我们可以进行任意变换。

void glTranslate{fd}(TYPE x, TYPE y, TYPE z);
void glRotate{fd}(TYPE angle, TYPE x, TYPE y, TYPE z); void glScale{fd}(TYPE x, TYPE y, TYPE z);
这三个函数,之前接触过。glTranslate,进行平移,平移的偏移量,由(x, y, z)指定。 glRotate,旋转,以逆时针方向绕着从原点到点(x, y, z)的直线旋转角度angle。glScale,按照一定比列进行缩放,比例在x轴,y轴,z轴方向上的量是(x, y, z)。

3.2.3 视图变换

视图变换,相关的三个函数是glTranslate,glRotate和gluLookAt函数。

这个glTranslate和glRotate在模型变换中,我们已经见过了。怎么模型变换和视图变换,使用的是同样的函数呢?因为变换是相对的。 比如,让模型和照相机距离5个单位长度,假设模型和照相机放在一起。我们可以将物体向前移动5个单位长度,也可以将照相机向后移动5个单位长度。所以,视 图变换,也是使用glTranslate和glRotate。只是这个参数的含义相反罢了。
比如

glTranslatef(0.0, 0.0, -5.0);

这个函数在场景中把物体沿z轴移动-5个单位,相当于把照相机沿z轴移动+5个单位。

使用工具函数gluLookAt()

void gluLookAt(GLdouble eyex, GLdouble eyey, GLdouble eyez,GLdouble centerx, GLdouble centery, GLdouble centerz,GLdouble upx, GLdouble upy, GLdouble upz);
定义一个视图矩阵,并把它与当前矩阵进行右乘。目标观察点eyex, eyey, eyez。centerx, centery和centerz参数指定了视线上的任意一点。upx,upy和upz参数表示哪个方向是朝上的(也就是说,在视景体中自底向上的方向)。

默认情况下,照相机位于原点,指向z轴的负方向,以y轴的正方向为朝上方向。相当于调用:

gluLookAt(0.0, 0.0, 0.0, 0.0, 0.0, -100.0, 0.0, 1.0, 0.0);
参考点的z值是-100.0, 但它也可以是任意的负值,因为它不会影响视线的方向。

下面是使用gluLookAt的一个例子。

gluLookAt(4.0, 2.0, 1.0, 2.0, 4.0, -3.0, 2.0, 2.0, -1.0);

这里写图片描述
这个函数,将摄像机移动到了(4.0, 2.0, 1.0)这个点,摄像机朝向(2.0, 4.0, -3.0)方向,摄像机向上的方向为(2.0, 2.0, -1.0)。

强烈推荐,理解这几个函数(glTranslate, glRotate, gluLookAt),使用Nate Robin的教程。网上有下的。

创建自定义的工具函数

创建自定义的函数,其实就是在自己的函数中,调用glTranslate和glRotate这两个函数。
要创建自定义的工具函数,主要是弄清楚两个东西:一个是参数是相对于哪个坐标系的,第二个就是照相机的变换顺序,与glTranslate,glRotate出现的顺序相同。

比如编写一个飞机模拟器,并且以飞机的驾驶员座位观察点显示飞机外面的景象。我们可以用一个圆点位于跑道上的坐标系统来描述整个场景,飞机相对于坐 标(x, y, z)。然后,假设飞机还有倾侧角、螺旋角和航向改变角(这些都是飞机相对于它的重心的旋转角度)。下面这个函数可以作用视图变换函数使用。

void pilotView(GLdouble planex, GLdouble planey, GLdouble planez, GLdouble roll, GLdouble pitch, GLdouble heading)
{glRotated(roll, 0.0, 0.0, 1.0); glRotated(pitch, 0.0, 1.0, 0.0); glRotated(heading, 1.0, 0.0, 0.0); glTranslated(-planex, -planey, -planez); }
这个其实很好理解,因为这个roll, pitch, heading,都是相对于飞机的。而飞机,就是我们的相机。所以,先将飞机旋转到一定角度,然后移动到点(planex, planey, planez)上面。因为这个planex, planey, planez是相对于机场跑道的坐标系,而我们移动的飞机相当于相机,所以都要取负号。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/397833.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

phoenix的元数据一般存在哪里_Phoenix的一些问题

date: 2020-09-10 13:50:00updated: 2020-09-14 16:30:001. Phoenix索引全局索引:适合读多写少的场景。写数据时因为索引表分布在不同数据节点,跨节点数据传输带来巨大的性能消耗。全局索引必须是查询语句中所有列都包含在全局索引中,它才会生…

鸿蒙os全面升级,华为突然宣布,鸿蒙OS正式版6月底全面升级,幸福来得太突然...

原标题:华为突然宣布,鸿蒙OS正式版6月底全面升级,幸福来得太突然摘要:早在今年2月华为Mate X2折叠屏新品发布会上,余承东曾表示,鸿蒙OS正式版将于今年4月份全面上线。或许是因为华为宣布卖车分散了很多的精…

5-python学习——条件语句

5-python学习——条件语句 5-python学习——条件语句 条件语句if else形式if else条件语句说明 测试一下编程语言一般都由这么几个部分组成 变量条件分支语句循环语句函数这里要说的就是条件分支语句。 python的条件语句和shell脚本的非常像,也就是if else if else这…

eclipse启动失败:An internal error occurred during: reload maven project

2019独角兽企业重金招聘Python工程师标准>>> 1.找到workspace文件夹下的/.metadata文件夹,将其删除掉,然后在讲项目重新导入进去eclipse中。但是这个有一点不好的地方,之前对eclipse所做的配置也会恢复为默认配置 2.在.metadata下…

Quartz2D知识点聚合案例

Quartz2D知识点聚合 基本 //画图片UIImage *image [UIImage imageNamed:"阿狸头像"];[image drawInRect:rect];//字体NSString *title "标题";NSMutableDictionary *atr [NSMutableDictionary dictionary];atr[NSFontAttributeName] [UIFont systemFon…

skt7850鸿蒙策略,lol 英雄联盟 SKT状态回暖轻取外卡,SUP难挡Faker

MSI 第四日 SUP vs SKT双方bpBAN LISTBAN:SUP:流浪 牛头 豹女SKT:巴德 妖姬 鱼人PICKSUP:大树 男枪 冰女 卢锡安 锤石SKT:艾克 千珏 沙皇 EZ 布隆比赛开始,双方正常对线开局。前期下路锤石多次勾中ez,男枪也来逼出EZ布…

spring集成struts2

Struts2前身是WebWork,核心并没有改变,其实就是把WebWork改名为struts2,与Struts1一点关系没有。 Struts2中通过ObjectFactory接口实现创建及获取Action实例,类似于Spring的IoC容器,所以Action实例可以由ObjectFactory…

slqite3库查询数据处理方式_SQLite3命令操作大全

SQLite3命令操作大全SQLite库包含一个名字叫做sqlite3的命令行,它可以让用户手工输入并执行面向SQLite数据库的SQL命令。本文档提供一个样使用sqlite3的简要说明.一.qlite3一些常用Sql语句操作创建表: create table 表名(元素名 类型,…);删除表: drop …

Android学习之查看网络图片

在这里小编学习了查看网络图片的小案例,: 初始界面: 点击浏览后,效果如下: 需要注意的是 该案例需要获取联网权限,即: <uses-permission android:name"android.permission.INTERNET"/>具体步骤如下: 1.定义并初始化控件: private EditText etImageUrl;private …

AutoLayout 浅析动画

1.AutoLayout相关的几个易混淆的方法 setNeedsLayout layoutIfNeeded layoutSubViews setNeedsUpdateConstraints updateConstraitsIfNeed updateConstraints 子视图在界面上的显示大概经过了&#xff1a;更新约束-通过约束依赖关系得到具体的frame-展示到界面。上面几个是和au…

vue 转为静态html,Vue CLI 3使用:HTML和静态资源(五)

HTMLpublic/index.html 文件是一个会被 html-webpack-plugin 处理的模板。构建中&#xff0c;各种资源路径会被注入解析。可以使用 lodash template 语法插入内容。用来做不转义插值&#xff1b;用来做 HTML 转义插值&#xff1b;用来描述 JavaScript 流程控制。除了被 html-we…

animate css3 应用的借鉴,一个同事写的JS

$("#banner").height($(window).height()-125);$(window).resize(function(){ $("#banner").height($(window).height()-125);}); //首页幻灯$(".indeximgs:first").show();var i0;$(".leftbut").click(function(){$(".indexim…

从html导出带样式的excel,Jquery导出带样式的Excel

工作中做导出的时候&#xff0c;需要导出自定义的表格或嫌弃导出的Excel格式太难看了。需要设置颜色、字号大小、加粗、合并单元格等等。特性&#xff1a;支持过滤 某个位置支持过滤 img 标签支持过滤 a 标签支持过滤 input 标签支持包含 行内样式。HTML页面&#xff1a;HTML页…

elementui from表单提交_elementui upload与form一起提交

学生基本信息管理操作中&#xff0c;有照片&#xff0c;可以上传也可以不上传&#xff0c;在表单界面可以修改照片&#xff0c;el-upload控件可以带额外参数提交&#xff0c;jquery的post模拟不了成表单带文件提交的方式&#xff0c;因此&#xff0c;判断如果有上传文件时&…

information_schema.character_sets 学习

information_schema.character_sets 表用于查看字符集的详细信息 1、character_sets 常用列说明&#xff1a; 1、character_set_name&#xff1a;    字符集名 2、default_collate_name&#xff1a;    默认排序规则   3、description&#xff1a;         …

asp.net mvc 用Redis实现分布式集群共享Session。

1、这两天研究Redis搞分布式session问题&#xff0c;网上找的资料都是用ServiceStack.Redis来实现的&#xff0c;但是在做性能测试的时候发现最新的v4版本有限制每小时候最多请求6000次&#xff0c;因为官网开始商业化要收费了&#xff0c;好坑爹的说&#xff0c;还好我前期弄了…

如何用计算机求和,求和计算器

求和计算器您可以使用此求和计算器快速计算预定范围内某个表达式的序列之和。如何使用求和计算器输入总和的表达式输入上限和下限提供表达式中使用的变量的详细信息单击“计算”按钮生成结果。求和Σ符号计算器k ∑n 0变量:nixyzabc 103740支持的运算符常量和函数算术运算符加“…

Zookeeper概述、特点、数据模型

Zookeeper1.Zookeeper概述Zookeeper是一个工具&#xff0c;可以实现集群中的分布式协调服务。所谓的分布式协调服务&#xff0c;就是在集群的节点中进行可靠的消息传递&#xff0c;来协调集群的工作。Zookeeper之所以能够实现分布式协调服务&#xff0c;靠的就是它能够保证分布…

云计算机创意名,有创意的道路名字推荐,分享一些好听有内涵的路名

提到龙岗板块&#xff0c;“风向”一直飘忽不定。原本地铁4号线今年通车&#xff0c;但是因为五象火车站的规划建设&#xff0c;暂时未开通;机场线已经敲定&#xff0c;然而没有龙岗的份…… [本文来自&#xff1a;www.777y.com]虽然机场线暂时无缘(可以期待下)&#xff0c;但是…

250W电源带i7+GTX1080?

电源的科学: Q1&#xff1a;电源的额定功率是什么&#xff1f;峰值功率又是什么&#xff1f;A1&#xff1a;电源的额定功率就是电源正常工作时的功率&#xff0c;它的值为用电器的额定电压乘以额定电流。而峰值功率指的是电源短时间内能达到的最大功率&#xff0c; 一般情况下电…