[3D]第一人称相机类Camera

2023-10-30 10:20
文章标签 3d 相机 camera 第一人称

本文主要是介绍[3D]第一人称相机类Camera,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

自己根据C++ D3D的源码改写一个相机类(第一人称)。

  1 using System;
  2 using System.Collections.Generic;
  3 using System.Linq;
  4 using System.Text;
  5 using Microsoft.DirectX;
  6 using Microsoft.DirectX.PrivateImplementationDetails;
  7 using Microsoft.DirectX.Direct3D;
  8 
  9 namespace AppScene
 10 {
 11     public enum CameraType { LANDOBJECT, AIRCRAFT };
 12     public class Camera
 13     {
 14         CameraType mCameraType;
 15         Vector3 mPosition; //相机位置
 16         Vector3 mLook;//LookVector  
 17         Vector3 mUp;// UpVector  
 18         Vector3 mRight;// RightVector  
 19         Vector3 ViewFrustum;// 平面截投体  
 20 
 21         protected Viewport mViewPort;//视口大小
 22         protected Matrix m_ProjectionMatrix; //上一次渲染采用的投影变换矩阵 Projection matrix used in last render.
 23         protected Matrix m_ViewMatrix; //上一次渲染采用的观察矩阵 View matrix used in last render.
 24         protected Matrix m_WorldMatrix = Matrix.Identity;//世界变换矩阵
 25         public Camera()
 26         {
 27             mCameraType = CameraType.AIRCRAFT;
 28             mPosition = new Vector3(0.0f, 0.0f, -50.0f);//注意默认位置,现在对了。
 29             mRight = new Vector3(0.0f, 1.0f, 0.0f);
 30             mUp = new Vector3(0.0f, 1.0f, 0.0f);
 31             mLook = new Vector3(0.0f, 0.0f, 10.0f);
 32         }
 33         public Camera(Vector3 cameraPosition, Vector3 cameraTarget, Vector3 upVector)
 34         {
 35             mCameraType = CameraType.AIRCRAFT;
 36             mPosition = new Vector3(0.0f, 0.0f, -100.0f);
 37             mRight = new Vector3(1.0f, 0.0f, 0.0f);
 38             mUp = new Vector3(0.0f, 1.0f, 0.0f);
 39             mLook = new Vector3(0.0f, 0.0f, 0.0f);
 40         }
 41         public void setCameraType(CameraType cameraType)
 42         {
 43             mCameraType = cameraType;
 44         }
 45         //前后移动
 46         public void walk(float units)
 47         {
 48             // move only on xz plane for land object
 49             if (mCameraType == CameraType.LANDOBJECT)
 50                 mPosition += new Vector3(mLook.X, 0.0f, mLook.Z) * units;
 51 
 52             if (mCameraType == CameraType.AIRCRAFT)
 53                 mPosition += mLook * units;
 54         }
 55         //左右移动,扫射
 56         public void strafe(float units)
 57         {
 58             // move only on xz plane for land object
 59             if (mCameraType == CameraType.LANDOBJECT)
 60                 mPosition += new Vector3(mRight.X, 0.0f, mRight.Z) * units;
 61 
 62             if (mCameraType == CameraType.AIRCRAFT)
 63                 mPosition += mRight * units;
 64         }
 65         //上下移动
 66         public void fly(float units)
 67         {
 68             // move only on y-axis for land object
 69             if (mCameraType == CameraType.LANDOBJECT)
 70                 mPosition.Y += units;
 71 
 72             if (mCameraType == CameraType.AIRCRAFT)
 73                 mPosition += mUp * units;
 74         }
 75 
 76         // 倾斜角 
 77         public void Pitch(float angle)
 78         {
 79             Matrix T = Matrix.Identity;
 80             //D3DXMatrixRotationAxis(&T, &_right, angle);
 81             T.RotateAxis(mRight, angle);
 82             // rotate _up and _look around _right vector
 83             mUp.TransformCoordinate(T);
 84             mLook.TransformCoordinate(T);
 85             //D3DXVec3TransformCoord(&_up, &_up, &T);
 86             //D3DXVec3TransformCoord(&_look, &_look, &T);
 87         }
 88         //俯仰角
 89         public void Roll(float angle)
 90         {
 91             // only roll for aircraft type
 92             if (mCameraType == CameraType.AIRCRAFT)
 93             {
 94                 Matrix T = Matrix.Identity;
 95                 T.RotateAxis(mLook, angle);
 96 
 97                 // rotate _up and _right around _look vector
 98                 mRight.TransformCoordinate(T);
 99                 mUp.TransformCoordinate(T);
100             }
101         }
102         // 航偏角
103         public void Yaw(float angle)
104         {
105             Matrix T = Matrix.Identity;
106 
107             // rotate around world y (0, 1, 0) always for land object
108             if (mCameraType == CameraType.LANDOBJECT)
109                 T.RotateY(angle);
110             // rotate around own up vector for aircraft
111             if (mCameraType == CameraType.AIRCRAFT)
112                 T.RotateAxis(mUp, angle);
113 
114             // rotate _right and _look around _up or y-axis
115             mRight.TransformCoordinate(T);
116             mLook.TransformCoordinate(T);
117         }
118         public void SetPosition(Vector3 position)// 设置相机世界坐标  
119         {
120             mPosition = position;
121         }
122         //更新相机状态
123         public Matrix UpdateCamera()
124         {
125             Matrix mViewMatrix = Matrix.Identity;
126             // Keep camera's axes orthogonal to eachother
127             //D3DXVec3Normalize(&_look, &_look);
128             mLook.Normalize();
129             //D3DXVec3Cross(&, &_look, &_right);
130             // _up = Vector3.Cross(_look, _right);
131             //D3DXVec3Normalize(&_up, &_up);
132             mUp.Normalize();
133             //D3DXVec3Cross(&_right, &_up, &_look);
134             mRight = Vector3.Cross(mUp, mLook);
135             //D3DXVec3Normalize(&_right, &_right);
136             mRight.Normalize();
137             // Build the view matrix:
138             //float x = -D3DXVec3Dot(&_right, &_pos);
139             //float y = -D3DXVec3Dot(&_up, &_pos);
140             //float z = -D3DXVec3Dot(&_look, &_pos);
141             float x = -Vector3.Dot(mRight, mPosition);
142             float y = -Vector3.Dot(mUp, mPosition);
143             float z = -Vector3.Dot(mLook, mPosition);
144 
145             mViewMatrix.M11 = mRight.X; mViewMatrix.M12 = mUp.X; mViewMatrix.M13 = mLook.X; mViewMatrix.M14 = 0.0f;
146             mViewMatrix.M21 = mRight.Y; mViewMatrix.M22 = mUp.Y; mViewMatrix.M23 = mLook.Y; mViewMatrix.M24 = 0.0f;
147             mViewMatrix.M31 = mRight.Z; mViewMatrix.M32 = mUp.Z; mViewMatrix.M33 = mLook.Z; mViewMatrix.M34 = 0.0f;
148             mViewMatrix.M41 = x; mViewMatrix.M42 = y; mViewMatrix.M43 = z; mViewMatrix.M44 = 1.0f;
149             return mViewMatrix;
150         }
151 
152         public void Update(Microsoft.DirectX.Direct3D.Device m_Device3d)
153         {
154             Matrix V = UpdateCamera();
155             m_Device3d.SetTransform(TransformType.View, V);
156         }
157         //视口大小
158         public Viewport Viewport
159         {
160             get
161             {
162                 return mViewPort;
163             }
164         }
165         //观察变换矩阵
166         public Matrix ViewMatrix
167         {
168             get
169             {
170                 return m_ViewMatrix;
171             }
172         }
173         //投影变换矩阵
174         public Matrix ProjectionMatrix
175         {
176             get
177             {
178                 return m_ProjectionMatrix;
179             }
180         }
181         //世界变换矩阵
182         public Matrix WorldMatrix
183         {
184             get
185             {
186                 return m_WorldMatrix;
187             }
188         }
189         /// <summary>
190         /// UnProject和Project之前需要调用该方法
191         /// </summary>
192         /// <param name="m_Device3d"></param>
193         public void ComputeMatrix(Device m_Device3d)
194         {
195             m_WorldMatrix = m_Device3d.GetTransform(TransformType.World);
196             m_ProjectionMatrix = m_Device3d.GetTransform(TransformType.Projection);
197             m_ViewMatrix = m_Device3d.GetTransform(TransformType.View);
198             mViewPort = m_Device3d.Viewport;
199         }
200         /// <summary>
201         /// Projects a point from world to screen coordinates.
202         /// 计算指定世界坐标的屏幕坐标
203         /// </summary>
204         /// <param name="point">Point in world space</param>
205         /// <returns>Point in screen space</returns>
206         public Vector3 Project(Vector3 point)
207         {
208             point.Project(mViewPort, m_ProjectionMatrix, m_ViewMatrix, m_WorldMatrix);
209             return point;
210         }
211 
212         internal Vector3 UnProject(Vector3 v1)
213         {
214             v1.Unproject(mViewPort, m_ProjectionMatrix, m_ViewMatrix, m_WorldMatrix);
215             return v1;
216         }
217     }
218 }
View Code

增加一个围绕某条射线旋转的方法:

 1  //
 2         public void RotateRay(float angle, Vector3 vOrigin, Vector3 vAxis)
 3         {
 4             // 计算新的焦点
 5             Vector3 vView = mLook - vOrigin;
 6             Matrix temp = Matrix.RotationAxis(vAxis, angle);
 7             vView.TransformCoordinate(temp);
 8             //vView.RotateAxis(angle, vAxis);
 9             mLook = vOrigin + vView;
10 
11             // 计算新的视点
12             vView = mPosition - vOrigin;
13            // Matrix temp2 = Matrix.RotationAxis(vAxis, angle);
14             vView.TransformCoordinate(temp);
15             //vView.RotateAxis(angle, vAxis);
16             mPosition = vOrigin + vView;
17 
18             mUp.TransformCoordinate(temp);
19           //  m_strafe.RotateAxis(angle, vAxis);
20         }

 

这篇关于[3D]第一人称相机类Camera的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/307258

相关文章

无人叉车3d激光slam多房间建图定位异常处理方案-墙体画线地图切分方案

墙体画线地图切分方案 针对问题:墙体两侧特征混淆误匹配,导致建图和定位偏差,表现为过门跳变、外月台走歪等 ·解决思路:预期的根治方案IGICP需要较长时间完成上线,先使用切分地图的工程化方案,即墙体两侧切分为不同地图,在某一侧只使用该侧地图进行定位 方案思路 切分原理:切分地图基于关键帧位置,而非点云。 理论基础:光照是直线的,一帧点云必定只能照射到墙的一侧,无法同时照到两侧实践考虑:关

基于UE5和ROS2的激光雷达+深度RGBD相机小车的仿真指南(五):Blender锥桶建模

前言 本系列教程旨在使用UE5配置一个具备激光雷达+深度摄像机的仿真小车,并使用通过跨平台的方式进行ROS2和UE5仿真的通讯,达到小车自主导航的目的。本教程默认有ROS2导航及其gazebo仿真相关方面基础,Nav2相关的学习教程可以参考本人的其他博客Nav2代价地图实现和原理–Nav2源码解读之CostMap2D(上)-CSDN博客往期教程: 第一期:基于UE5和ROS2的激光雷达+深度RG

MiniGPT-3D, 首个高效的3D点云大语言模型,仅需一张RTX3090显卡,训练一天时间,已开源

项目主页:https://tangyuan96.github.io/minigpt_3d_project_page/ 代码:https://github.com/TangYuan96/MiniGPT-3D 论文:https://arxiv.org/pdf/2405.01413 MiniGPT-3D在多个任务上取得了SoTA,被ACM MM2024接收,只拥有47.8M的可训练参数,在一张RTX

SAM2POINT:以zero-shot且快速的方式将任何 3D 视频分割为视频

摘要 我们介绍 SAM2POINT,这是一种采用 Segment Anything Model 2 (SAM 2) 进行零样本和快速 3D 分割的初步探索。 SAM2POINT 将任何 3D 数据解释为一系列多向视频,并利用 SAM 2 进行 3D 空间分割,无需进一步训练或 2D-3D 投影。 我们的框架支持各种提示类型,包括 3D 点、框和掩模,并且可以泛化到不同的场景,例如 3D 对象、室

海鸥相机存储卡格式化如何恢复数据

在摄影的世界里,‌每一张照片都承载着独特的记忆与故事。‌然而,‌当我们不慎将海鸥相机的存储卡格式化后,‌那些珍贵的瞬间似乎瞬间消逝,‌让人心急如焚。‌但请不要绝望,‌数据恢复并非遥不可及。‌本文将详细介绍在海鸥相机存储卡格式化后,‌如何高效地恢复丢失的数据,‌帮助您重新找回那些宝贵的记忆。‌ 图片来源于网络,如有侵权请告知 一、‌回忆备份情况 ‌海鸥相机存储卡格式化如何恢复数据?在意

4-4.Andorid Camera 之简化编码模板(获取摄像头 ID、选择最优预览尺寸)

一、Camera 简化思路 在 Camera 的开发中,其实我们通常只关注打开相机、图像预览和关闭相机,其他的步骤我们不应该花费太多的精力 为此,应该提供一个工具类,它有处理相机的一些基本工具方法,包括获取摄像头 ID、选择最优预览尺寸以及打印相机参数信息 二、Camera 工具类 CameraIdResult.java public class CameraIdResult {

模具要不要建设3D打印中心

随着3D打印技术的日益成熟与广泛应用,模具企业迎来了自建3D打印中心的热潮。这一举措不仅为企业带来了前所未有的发展机遇,同时也伴随着一系列需要克服的挑战,如何看待企业引进增材制造,小编为您全面分析。 机遇篇: 加速产品创新:3D打印技术如同一把钥匙,为模具企业解锁了快速迭代产品设计的可能。企业能够迅速将创意转化为实体模型,缩短产品从设计到市场的周期,抢占市场先机。 强化定制化服务:面

机器视觉硬件选型根据某项目相机镜头

一 项目总需求 1、大视野检测需求: (1)大视野: ①产品尺寸15.6寸屏幕,产品大小:350mm x 225mm; ②产品料盘尺寸大小:565mm x 425mm; ③工作距离:880mm;检测精度:500μm; 1、大视野检测需求: (1)大视野: ①产品尺寸15.6寸屏幕,产品大小:350mm x 225mm; ②产品料盘尺寸大小:565mm x 425mm; 工作距离:

WPF入门到跪下 第十三章 3D绘图 - 3D绘图基础

3D绘图基础 四大要点 WPF中的3D绘图涉及4个要点: 视口,用来驻留3D内容3D对象照亮部分或整个3D场景的光源摄像机,提供在3D场景中进行观察的视点 一、视口 要展示3D内容,首先需要一个容器来装载3D内容。在WPF中,这个容器就是Viewport3D(3D视口),它继承自FrameworkElement,因此可以像其他元素那样在XAML中使用。 Viewport3D与其他元素相

005:VTK世界坐标系中的相机和物体

VTK医学图像处理---世界坐标系中的相机和物体 左侧是成像结果                                                    右侧是世界坐标系中的相机与被观察物体 目录 VTK医学图像处理---世界坐标系中的相机和物体 简介 1 在三维空间中添加坐标系 2 世界坐标系中的相机 3 世界坐标系中vtkImageData的参数 总结: