对 SceneKit 中相机的正交投影感到困惑 [英] Confused about Orthographic Projection of camera in SceneKit
问题描述
我想使用正交投影在我的应用中显示 3D 场景.在我的代码中,我在场景中放置了一个框,并设置了视点的正交投影,如打击.(0,0,500) 处的相机看 -z 方向,并在世界的原点框.所以相机应该能够捕捉到盒子.
让 cameraNode = SCNNode()让 pov = SCNCamera()pov.usesOrthographicProjection = true让宽度 = UISreen.main.bounds.size.width让 glMat = GLKMatrix4MakeOrtho(-width/2, width/2, -width/2, width/2, 1, 1000)pov.projectionTransform = SCNMatrix4FromGLKMatrix4(glMat)cameraNode.camera = povcameraNode.position = SCNVector3.init(0, 0, 500)场景.rootNode.addChildNode(cameraNode)让 boxGeo = SCNBox.init(宽度:100,高度:100,长度:1,倒角半径:0)让 box = SCNNode.init(几何:boxGeo)场景.rootNode.addChildNode(box)
但我什么也看不见.我发现如果将 orthographicScale
设置为 width/2.0
将正常工作.
pov.orthographicScale = Double(width/2);
问题 1:我不知道为什么会这样.我阅读了苹果的文档,但仍然感到困惑.
问题 2: 我还发现如果我创建像 Blow 这样的投影矩阵,它的工作原理和以前一样.
让 glMat = GLKMatrix4MakeOrtho(0, width, 0, width, 1, 1000)
在OpenGL中表示不同的观察框,会显示不同的场景分区.
感谢任何帮助!
我想,你在使用 GLKMatrix4MakeOrtho
的场景中看不到你的 3D 对象,因为有这么多类适用于 iOS 和 macOS 的 GLKit 现已弃用.
为了查看您的 3D 对象,您需要在 Attributes Inspector
中手动设置 Far Z Clipping
参数.这两个字段分别是正交相机截头体的 near
和 far
剪切平面.默认值 Far=100
不允许您看到 100 单位以外的场景.
然后使用 Scale
属性为正交视图中的对象设置比例因子.
为了通过 GLKMatrix4MakeOrtho
以编程方式使用它,您需要导入 GLKit
和 OpenGL
模块(以及所有必要的委托协议) 首先进入您的项目.
导入 GLKit导入 OpenGL//Obj-C GLKMatrix4GLK_INLINE GLKMatrix4 GLKMatrix4MakeOrtho(向左浮动,向右浮动,浮底,浮在上面,漂浮在Z附近,浮动远Z){浮动 ral = 右 + 左;浮动 rsl = 右 - 左;浮动标签 = 顶部 + 底部;浮动 tsb = 顶部 - 底部;浮动风扇 = farZ + nearZ;浮动 fsn = farZ - nearZ;GLKMatrix4 m = { 2.0f/rsl, 0.0f, 0.0f, 0.0f,0.0f, 2.0f/tsb, 0.0f, 0.0f,0.0f, 0.0f, -2.0f/fsn, 0.0f,-ral/rsl,-tab/tsb,-fan/fsn,1.0f};返回米;}
<块引用>
此外,在 iOS 上,GLKit 需要 OpenGL ES 2.0 上下文.在 macOS 中,GLKit 需要支持 OpenGL 3.2 Core Profile 的 OpenGL 上下文.
但请记住!许多 GL 功能已弃用,因此您最好使用 Metal
框架.查看已弃用的 GLKit 类.
I want to use orthographic projection to display 3D scene in my app. In my code I put a box in scene and set orthographic projection of Point of view like blow. Camera at (0,0,500) look at -z direction, and box at origin of world. So camera should be able to capture the box.
let cameraNode = SCNNode()
let pov = SCNCamera()
pov.usesOrthographicProjection = true
let width = UISreen.main.bounds.size.width
let glMat = GLKMatrix4MakeOrtho(-width/2, width/2, -width/2, width/2, 1, 1000)
pov.projectionTransform = SCNMatrix4FromGLKMatrix4(glMat)
cameraNode.camera = pov
cameraNode.position = SCNVector3.init(0, 0, 500)
scene.rootNode.addChildNode(cameraNode)
let boxGeo = SCNBox.init(width: 100, height: 100, length: 1, chamferRadius: 0)
let box = SCNNode.init(geometry: boxGeo)
scene.rootNode.addChildNode(box)
But I can see nothing. I find out If set orthographicScale
to width/2.0
will works correctly.
pov.orthographicScale = Double(width/2);
Question 1 : I don't know why this works. I read docs of apple but still confused. https://developer.apple.com/documentation/scenekit/scncamera/1436612-orthographicscale?language=objc
orthographicScale
Specifies the camera’s magnification factor when using an orthographic projection.
Why I need magnify orthographic projection? I already set the dimension of it through GLKMatrix4MakeOrtho
.
I'm not sure whether it is relate to viewport transform? Because viewport transform in OpenGL computed as follows: https://docs.microsoft.com/en-us/windows/desktop/opengl/glviewport
Question 2 : I also find If I create projection matrix like blow it works same as before.
let glMat = GLKMatrix4MakeOrtho(0, width, 0, width, 1, 1000)
In OpenGL it means different viewing box and will display different partition of scene.
Any help is appreciated!
I suppose, you can't see your 3D objects in the scene using GLKMatrix4MakeOrtho
, due to the fact that so many classes of GLKit for iOS and macOS are deprecated now.
In order to see your 3D object, you need to manually set Far Z Clipping
parameter in Attributes Inspector
. These two fields are near
and far
clipping planes of the frustum of your Orthographic Camera. A default value of Far=100
doesn't allow you see the scene further than 100 units away.
Then use a
Scale
property to set a scale factor for your objects in an ortho view.
In order to use it programmatically via GLKMatrix4MakeOrtho
, you need to import GLKit
and OpenGL
modules (as well as all the necessary delegate protocols) into your project at first.
import GLKit
import OpenGL
// Obj-C GLKMatrix4
GLK_INLINE GLKMatrix4 GLKMatrix4MakeOrtho(float left,
float right,
float bottom,
float top,
float nearZ,
float farZ) {
float ral = right + left;
float rsl = right - left;
float tab = top + bottom;
float tsb = top - bottom;
float fan = farZ + nearZ;
float fsn = farZ - nearZ;
GLKMatrix4 m = { 2.0f / rsl, 0.0f, 0.0f, 0.0f,
0.0f, 2.0f / tsb, 0.0f, 0.0f,
0.0f, 0.0f, -2.0f / fsn, 0.0f,
-ral / rsl, -tab / tsb, -fan / fsn, 1.0f };
return m;
}
Also, on iOS, GLKit requires an OpenGL ES 2.0 context. In macOS, GLKit requires an OpenGL context that supports the OpenGL 3.2 Core Profile.
But remember! Many GL Features are deprecated, so you'd better use Metal
framework. Look at deprecated classes of GLKit.
这篇关于对 SceneKit 中相机的正交投影感到困惑的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!