繁体   English   中英

如何在 Swift 包管理器中添加 Reality 文件?

[英]How to add Reality file in a Swift Package Manager?

我听说 Xcode 12(现在是 Beta 6),Swift 包管理器现在能够包含资源。 但我无法打开现实(.rcproject)文件。

这是我尝试过的; (你可以复制)

  1. 我创建了一个新的Augmented Reality App项目。 (RealityKit + SwiftUI + Swift)
  2. 现在,如果您尝试运行该项目,一切正常,您会看到一个默认的金属框。
  3. 现在我创建了一个新的SPM (Swift 包管理器)
  4. 现在,我将本地创建的SPM拖到项目中,并将其添加到“常规”>“目标”选项卡中的框架中。 (通知项目有关本地添加的 spm)
  5. 我将Experience.rcproject & ContentView (也复制了自动生成的Experience枚举,您可以通过 Cmd+Click 访问它)到SPM
  6. 修复了ContentView一些访问初始化问题并添加了平台支持platforms: [.iOS(.v13)],SPM
  7. SPM为存在路径Experience.rcproject添加了resources

完成这些步骤后,我希望有一个包含 AR 的 swift 包管理器。
但是自动生成的Experience枚举会抛出.fileNotFound("Experience.reality")错误。
好像还是没能在 Bundle 中找到真人档案?

你有没有尝试过类似的东西。 等待任何帮助。 谢谢..


文件夹结构

Package.swift

// swift-tools-version:5.3
// The swift-tools-version declares the minimum version of Swift required to build this package.

import PackageDescription

let package = Package(
    name: "ARSPM",
    platforms: [.iOS(.v13)],
    products: [
        .library(
            name: "ARSPM",
            targets: ["ARSPM"]),
    ],
    dependencies: [],
    targets: [
        .target(
            name: "ARSPM",
            dependencies: [], resources: [
                .copy("Resources")
            ]),
        .testTarget(
            name: "ARSPMTests",
            dependencies: ["ARSPM"]),
    ]
)

ARView.swift

import SwiftUI
import RealityKit

public struct EKARView : View {
    public init() { }
    public var body: some View {
        return ARViewContainer().edgesIgnoringSafeArea(.all)
    }
}

public struct ARViewContainer: UIViewRepresentable {
    
    public func makeUIView(context: Context) -> ARView {
        
        let arView = ARView(frame: .zero)
        
        // Load the "Box" scene from the "Experience" Reality File
        let boxAnchor = try! Experience.loadBox()
        
        // Add the box anchor to the scene
        arView.scene.anchors.append(boxAnchor)
        
        return arView
        
    }
    
    public func updateUIView(_ uiView: ARView, context: Context) {}
    
}

GeneratedExperienceFile.swift

//
// Experience.swift
// GENERATED CONTENT. DO NOT EDIT.
//

import Foundation
import RealityKit
import simd
import Combine

internal enum Experience {

    public enum LoadRealityFileError: Error {
        case fileNotFound(String)
    }

    private static var streams = [Combine.AnyCancellable]()

    public static func loadBox() throws -> Experience.Box {
        guard let realityFileURL =
//                Also tried >> Foundation.Bundle.module
                Foundation.Bundle(for: Experience.Box.self)
                    .url(forResource: "Experience", withExtension: "reality") else {
            throw Experience.LoadRealityFileError.fileNotFound("Experience.reality")
        }

        let realityFileSceneURL = realityFileURL.appendingPathComponent("Box", isDirectory: false)
        let anchorEntity = try Experience.Box.loadAnchor(contentsOf: realityFileSceneURL)
        return createBox(from: anchorEntity)
    }

    public static func loadBoxAsync(completion: @escaping (Swift.Result<Experience.Box, Swift.Error>) -> Void) {
        guard let realityFileURL = Foundation.Bundle(for: Experience.Box.self).url(forResource: "Experience", withExtension: "reality") else {
            completion(.failure(Experience.LoadRealityFileError.fileNotFound("Experience.reality")))
            return
        }

        var cancellable: Combine.AnyCancellable?
        let realityFileSceneURL = realityFileURL.appendingPathComponent("Box", isDirectory: false)
        let loadRequest = Experience.Box.loadAnchorAsync(contentsOf: realityFileSceneURL)
        cancellable = loadRequest.sink(receiveCompletion: { loadCompletion in
            if case let .failure(error) = loadCompletion {
                completion(.failure(error))
            }
            streams.removeAll { $0 === cancellable }
        }, receiveValue: { entity in
            completion(.success(Experience.createBox(from: entity)))
        })
        cancellable?.store(in: &streams)
    }

    private static func createBox(from anchorEntity: RealityKit.AnchorEntity) -> Experience.Box {
        let box = Experience.Box()
        box.anchoring = anchorEntity.anchoring
        box.addChild(anchorEntity)
        return box
    }

    public class Box: RealityKit.Entity, RealityKit.HasAnchoring {

        public var steelBox: RealityKit.Entity? {
            return self.findEntity(named: "Steel Box")
        }

    }

}

ContentView文件中,我简单地显示EKARView

Xcode 知道如何将.rcproject文件处理为构建应用程序时所需的.reality文件。 不幸的是,在使用 Swift 包访问项目文件时没有完成此处理。

您概述的步骤几乎可以奏效。 归结为使用已编译的.reality文件代替.rcproject文件。 为了转换默认的.rcproject文件,您需要使用 Apple 的Reality Composer应用程序。

使用 Xcode 12 概述的步骤...

  • 选择Experience.rcproject文件后,单击“在 Reality Composer 中打开”按钮。
  • 打开后,通过“文件”菜单导出项目。
  • 选择“项目”并单击“导出”。 这会生成一个Experience.reality文件。
  • 将该文件放在您的 swift 包资源中。
  • 确保将Experience.swift文件中的Bundle引用替换为Bundle.module ,因为现有引用将针对您的应用程序包。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM