14-《ARKit by Tutorials》读书笔记1:开始入门

栏目: IOS · 发布时间: 6年前

内容简介:可以打开AR视图的debug选项来帮助调试:可配置项如下:在SceneKit中可用的光照模型(着色器)如下:
  • Pausing:ARSession.pause()可以用来暂停会话.
  • Resuming:ARSession.run()可恢复一个暂停的session.
  • Updating:ARSession.run(ARSessionConfig)可以更新配置项.
  • Resetting: ARSession.run(_:options:)可以重置session. 当session状态改变时,可以在代理方法中处理:
func session(_ session: ARSession, 
  cameraDidChangeTrackingState camera: ARCamera) {
  switch camera.trackingState {
    // 1
    case .notAvailable:
      trackingStatus = "Tracking:  Not available!"
    // 2  
    case .normal:
      trackingStatus = "Tracking: All good!"
    // 3 
    case .limited(let reason):
      switch reason {
        case .excessiveMotion:
          trackingStatus = "Tracking: Limited due to 
            excessive motion!"
        // 3.1  
        case .insufficientFeatures:
          trackingStatus = "Tracking: Limited due to 
            insufficient features!"
        // 3.2
        case .initializing:
          trackingStatus = "Tracking: Initializing..."
        // 3.3
        case .relocalizing:
          trackingStatus = "Tracking: Relocalizing..."
        }
    }
  }
}
复制代码

调试选项

可以打开AR视图的debug选项来帮助调试:

sceneView.debugOptions = []
复制代码

可配置项如下:

  • Feature points:显示检测到的特征点.
  • World origin:红绿蓝三色线交叉组成的世界坐标原点.
  • Bounding boxes:3D物体的边界盒.
  • Wireframe:3D物体线框图.

着色器,材质和纹理

在SceneKit中可用的光照模型(着色器)如下:

14-《ARKit by Tutorials》读书笔记1:开始入门

材质是2D图片,可以包裹在3D几何体周围提供特殊属性,比如color颜色, specularity高光, reflectivity反射率, shininess发光率, roughness粗糙度, metalness金属度 甚至transparency透明度.

14-《ARKit by Tutorials》读书笔记1:开始入门
具体可以看我以前写的SceneKit系列文章Lights灯光, Materials材质 , Shadows阴影

基于物理的渲染(PBR)

PBR光照模型是新引入的特性,可以让你的3D物体看起来更真实.

下面我们来重点学习一下其中的特性:

Environment map环境贴图

环境贴图是一种 cube map立方体贴图 ,比如天空盒子shybox是这样的:

14-《ARKit by Tutorials》读书笔记1:开始入门

SceneKit还支持其它类型的立方体贴图:

14-《ARKit by Tutorials》读书笔记1:开始入门

环境贴图有两方面作用:一方面类似于reflection map反射贴图,可以在高反射率表面看到环境图像的反射;另一方面,对于支持PBR的3D物体,可以提供真实的光照环境.如下:

14-《ARKit by Tutorials》读书笔记1:开始入门

Diffuse map漫反射贴图

漫反射贴图提供基础颜色,无需考虑灯光和其它特效.

14-《ARKit by Tutorials》读书笔记1:开始入门

需要注意的是,漫反射贴图可以通过图片的alpha通道来指定透明度.比如在地球外面再包层大气云层图,你只能看到大气层的不透明部分.

14-《ARKit by Tutorials》读书笔记1:开始入门

Normal map法线贴图

所谓法线,就是垂直于几何体表面的向量.可以用来计算光线的反射等效果.

法线贴图通过图片的RGB通道来定义了像素级的表面法线.用来与光线混合计算,模拟表面的凹凸效果.这样无需增加多边形及顶点数据,就模拟出了真实的表面.

14-《ARKit by Tutorials》读书笔记1:开始入门

Height map高度贴图

高度贴图并不是PBR光照模型的一部分,但是也值得大家学习.高度贴图是黑白图像,白色代表物体的最高点,黑色代表最低点.

高度贴图和法线贴图可以互相转换,网上有免费工具Normal Map Online — available atbit.ly/1ELCePX

14-《ARKit by Tutorials》读书笔记1:开始入门
14-《ARKit by Tutorials》读书笔记1:开始入门

Occlusion map闭塞贴图

也就是ambient occlusion map环境光闭塞贴图(OA贴图).用来阻止环境光照亮闭塞的区域,比如墙壁上的裂缝里.黑白贴图,黑色代表不可照亮,白色代表可以照亮.

14-《ARKit by Tutorials》读书笔记1:开始入门

Emission map发光贴图/发射贴图

定义了光照和阴影来制造一种发光效果.例如地球黑夜的灯光(需要关闭光照.PBR下停用环境贴图):

14-《ARKit by Tutorials》读书笔记1:开始入门

Self-illumination map自发光贴图

自发光贴图在其它所有效果之后才应用;可以用来给最终效果上色,增亮或变暗

14-《ARKit by Tutorials》读书笔记1:开始入门

Displacement map位移贴图

在法线贴图中,我们可以在光滑表面创造出像素级的不同高度,但它只是幻像,只是改变了光线的反射而已.

在位移贴图中,我们可以真正地改变表面地形.灰色到白色表示凸起,灰色到黑色表示凹陷:

14-《ARKit by Tutorials》读书笔记1:开始入门

Metalness and roughness maps金属度和粗糙度贴图

PBR的主要特性就是能够展示出可见的 微观细节 ,就是用金属度和粗糙度贴图来实现的:

14-《ARKit by Tutorials》读书笔记1:开始入门
  • 金属度:从后往前,逐渐增强.
  • 粗糙度:从左到右,逐渐增强.

Metalness map金属度贴图

金属度模拟了物体表面的属性,如反射,折射和菲涅耳反射.该灰度纹理中,黑色代表非金属,白色代表金属性表面:

14-《ARKit by Tutorials》读书笔记1:开始入门

Roughness map粗糙度贴图

粗糙度贴图模拟了真实世界表面的微观细节.产生明亮或暗淡的外观.该灰度纹理中,黑色代表最粗糙,白色代表最光滑表面:

14-《ARKit by Tutorials》读书笔记1:开始入门

Detect plane表面检测

Anchor锚点

锚点是3D物体的参考点,和UIView中的anchor锚点类似.对3D物体应用的 transform 变换也是相对于锚点的.

14-《ARKit by Tutorials》读书笔记1:开始入门

添加了新锚点

当平面检测发现平面时,会添加一个锚点,并创建一个SCNNode,并调用代理方法:

// 1
func renderer(_ renderer: SCNSceneRenderer,
  didAdd node: SCNNode, for anchor: ARAnchor) {
  // 2
  guard let planeAnchor = anchor as? ARPlaneAnchor else { return }
  // 3
  DispatchQueue.main.async {
    // 4
    let planeNode = self.createARPlaneNode(
      planeAnchor: planeAnchor,
      color: UIColor.yellow.withAlphaComponent(0.5))
     // 5
     node.addChildNode(planeNode)
  }
}
复制代码

锚点更新

当锚点更新时,也会调用代理方法:

// 1
func renderer(_ renderer: SCNSceneRenderer, 
  didUpdate node: SCNNode, for anchor: ARAnchor) {
  // 2
  guard let planeAnchor = anchor as? ARPlaneAnchor else { return }
    // 3
    DispatchQueue.main.async {
      // 4
      self.updateARPlaneNode(planeNode: node.childNodes[0],
        planeAchor: planeAnchor)
    }
}

复制代码

Physics物理效果

Physics body物理形体

首先要了解的是就是physics body物理形体的概念:

  • static body:静态形体,在物理模拟中可以与其它物体发生作用,但自身不受影响,始终在原来位置上.如墙壁.
  • dynamic body:动态形体,在物理模拟中完全由物理引擎控制并可以与其它物理形体发生作用.如小球.
  • kinematic body:动力学形体,在物理模拟中不受物理引擎控制,但可以通过代码来移动.如电梯.

Physics body type物理形体的形状

还有SceneKit内置的物体形状:

14-《ARKit by Tutorials》读书笔记1:开始入门

并可调节各个参数:

14-《ARKit by Tutorials》读书笔记1:开始入门

还可以调整整个场景的物理效果速度及物理模拟帧数:

scene.physicsWorld.speed = 0.05 //效果就像慢镜头

scene.physicsWorld.timeStep = 1.0 / 60.0 //每秒60帧;如果物体运动速度过快,需要增加帧数以提高精度,但也会提高CPU的负载.
复制代码

Force力

力使用3维向量SCNVector3表示,使用applyForce(_: atPosition: impluse:)方法来添加一个力,并指定位置.一个力可以同时影响线速度和角速度. impluse脉冲状只作用一次,比如踢一个球,非脉冲状的则可以持续作用. Position位置可以影响力的作用效果

更多物理效果相关内容,可以参考physics物理效果

灯光和阴影

在AR中给物体添加阴影一般有两种方法:

  • 在物体下面放上一块浅灰纹理的平面,这样仿佛就有了阴影.这也就是所谓的将光照和阴影"烘焙"进纹理中.
  • 在物体下面放一块平面,并将平面的 Reflectivity 设置为0;再添加一个光源,并将光源的 Mode 改为 Deferred ,这样就能产生实时的阴影了.
    14-《ARKit by Tutorials》读书笔记1:开始入门
    14-《ARKit by Tutorials》读书笔记1:开始入门
    14-《ARKit by Tutorials》读书笔记1:开始入门

同时文章中还提供了,如何用代码来禁止某个物体写入颜色缓冲区.

func hideARPlaneNodes() {
    // 1
    for anchor in
      (self.sceneView.session.currentFrame?.anchors)! {
      // 2 
      if let node = self.sceneView.node(for: anchor) {
        // 3
        for child in node.childNodes {
          // 4
          let material = child.geometry?.materials.first!
          material?.colorBufferWriteMask = []
        }
      }
    }
}
复制代码

更多相关内容可以看我以前写的SceneKit系列文章Lights灯光,Shadows阴影以及官方Demo解读中关于阴影的官方解读 苹果官方AR变色龙Demo解读

Hit testing命中测试

命中测试可以用来提供与3D物体的交互

override func touchesBegan(_ touches: Set<UITouch>,
  with event: UIEvent?) {
  DispatchQueue.main.async {
    // 1
    if let touchLocation = touches.first?.location(
      in: self.sceneView) {
      // 2
      if let hit = self.sceneView.hitTest(touchLocation,
        options: nil).first {
        // 3
        if hit.node.name == "dice" {
          // 4
          hit.node.removeFromParentNode()
          self.diceCount += 1
        }
      }
    }
  }
}
复制代码

第一部分读书笔记结束!


以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持 码农网

查看所有标签

猜你喜欢:

本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们

一站式学习C编程

一站式学习C编程

宋劲杉 / 电子工业出版社 / 2011-3 / 59.00元

《一站式学习c编程》有两条线索,一条线索是以linux平台为载体全面深入地介绍c语言的语法和程序的工作原理,另一条线索是介绍程序设计的基本思想和开发调试方法。本书分为两部分:第一部分讲解编程语言和程序设计的基本思想方法,让读者从概念上认识c语言;第二部分结合操作系统和体系结构的知识讲解程序的工作原理,让读者从本质上认识c语言。 《一站式学习c编程》适合做零基础的初学者学习c语言的第一本教材,......一起来看看 《一站式学习C编程》 这本书的介绍吧!

在线进制转换器
在线进制转换器

各进制数互转换器

XML、JSON 在线转换
XML、JSON 在线转换

在线XML、JSON转换工具

UNIX 时间戳转换
UNIX 时间戳转换

UNIX 时间戳转换