RoomPlan
是WWDC22
上发布的一开非常酷的一个库,虽然,第一天的Keynote
中都没有任何介绍和相关的技术展示。但是,从开发者网站中我们窥探到了这一新库出现。这个库主要是干嘛的呢?从目前来看,可以使用它扫描房间,它会帮我们创建好房间的3D模型。
来看下官方的这个演示视频,可以直观的感受下这个库的魅力。
嗯,看上去貌似对房地产行业和家装行业比较友好。
下面主要从技术角度介绍下RoomPlan RoomPlan
其实是ARKit
的一个再封装,其主要利用的技术是借助LiDAR
扫描周围的环境,捕获到场景的深度信息。然后,根据场景几何建立我们的Room
网格。RoomPlan
还利用影像数据结合AI的能力,对现实物体进行了更加细致的分类、检测和分割。主要可以识别这几大类:
1 2 3 4 5 6 7 8 9 10 // 墙体 public var walls: [CapturedRoom.Surface] { get } // 门 public var doors: [CapturedRoom.Surface] { get } // 窗户 public var windows: [CapturedRoom.Surface] { get } // 开口 public var openings: [CapturedRoom.Surface] { get } // 物体 public var objects: [CapturedRoom.Object] { get }
其中,Object 下面还有细分的类别:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 public enum Category : Codable, Sendable { // 未知 case unknown // 储物柜 case storage // 冰箱 case refrigerator // 厨灶 case stove // 床 case bed // 水槽 case sink // 洗衣机 case washer // 马桶 case toilet // 浴缸 case bathtub // 烤箱 case oven // 洗碟机 case dishwasher // 桌子 case table // 沙发 case sofa // 椅子 case chair // 壁炉 case fireplace // 屏幕 case screen // 楼梯 case stairs }
可以看到,识别的物品还是比较多的,未来苹果应该会增加更多的识别项。
如何使用? 主要有两种使用方式,一种是直接使用封装好的RoomCaptureView
,另一种是通过API
接口来自定义实现。下面主要介绍使用RoomCaptureView
实现房间的模型创建。
RoomCaptureView
是UIView
的子类,我们可以轻松地在自己的应用程序中使用它。RoomCaptureView
主要负责三件事情:
根据扫描到的物理环境空间实时在屏幕上进行反馈;
实时生成当前扫描得到的房间模型;
在一些特殊情况时候显示对用户的引导;
使用RoomCaptureView
只需要通过四个简单的步骤。
首先,我们需要在对应的 ViewController 中创建一个 RoomCaptureView 引用。
其次,我们需要创建对 RoomCaptureSession 配置对象的引用。
第三,创建开始扫描的函数,在run中置传递相关参数。
最后,创建停止扫描函数。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 import UIKit import RoomPlan class RoomCaptureViewController: UIViewController { private var roomCaptureView: RoomCaptureView! private var roomCaptureSessionConfig: RoomCaptureSession.Configuration override func viewDidLoad() { super.viewDidLoad() // Set up after loading the view. setupRoomCaptureView() } private func setupRoomCaptureView() { roomCaptureView = RoomCaptureView(frame: view.bounds) roomCaptureView.captureSession.delegate = self roomCaptureView.delegate = self view.insertSubview(roomCaptureView, at: 0) } override func viewDidAppear(_ animated: Bool) { super.viewDidAppear(animated) startSession() } override func viewWillDisappear(_ flag: Bool) { super.viewWillDisappear(flag) stopSession() } private func startSession() { roomCaptureView?.captureSession.run(configuration: roomCaptureSessionConfig) } private func stopSession() { roomCaptureView?.captureSession.stop() } }
我们可以通过遵循RoomCaptureViewDelegate
协议,选择扫描结束后是否要进行后期优化处理,以及存储和导出USDZ
文件。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 class RoomCaptureViewController: UIViewController, RoomCaptureViewDelegate{ // ... private var finalResults: CapturedRoom? // 选择扫描结束后是否要进行后期处理 func captureView(shouldPresent roomDataForProcessing: CapturedRoomData, error: Error?) -> Bool { return true } // 选择最终模型如何处理 func captureView(didPresent processedResult: CapturedRoom, error: Error?) { // 存储以便后期使用 finalResults = processdResult // 或者导出 try processdResult.export(to: destinationURL) } }
以上就是RoomCaptureView
的完整使用,通过简短的代码就能创建房间空间的模型。
不足 对我来说RoomPlan
最大的不足在于纹理上,扫描出来的模型文件没有纹理数据。当然这应该也是苹果对这个产品的定位问题吧,也是出于性能和当前实现的效果考量吧。另外,RoomPlan
当前还存在一些测量尺寸不准确的bug
,以及一些识别不对的bug
。