如何在呈现前更改 SKScene 位置?

How to change SKScene position before presenting?

我正在尝试根据游戏 运行 的设备调整 SKScene 位置。例如,由于 iPhone XS Max 的 'top notch' 区域,我需要从 SKScene 高度中减去该高度并相应地定位场景。

所以这就是我如何计算 AppDelegate 中的高度 safeAreaHeight 并从场景高度中减去 sceneHeight:

    safeAreaHeight = UIApplication.shared.statusBarFrame.size.height
    sceneHeight -= safeAreaHeight

GameViewController 中,我尝试重新定位 SKScene,如下所示:

    if let view = self.view as! SKView? {
        // Load the SKScene from 'MainMenuScene.sks'
        if let scene = SKScene(fileNamed: "MainMenuScene") {
            // Set the scale mode to scale to fit the window
            scene.scaleMode = .aspectFit
            scene.size.height = sceneHeight
            scene.size.width = sceneWidth
            scene.position.y -= safeAreaHeight
            // Present the scene
            view.presentScene(scene)
        }

        view.ignoresSiblingOrder = true
        view.showsFPS = true
        view.showsNodeCount = true
    }

但是,我遇到以下错误:

SKScene: Setting the position of a SKScene has no effect.

此外,我也尝试使用 SKAction 移动 SKScene 的位置,然后收到以下错误:

SKScene: Animating the position of a SKScene has no effect.

感谢您的帮助。

好吧,我想出了如何实现这一点,我正在分享,以防它对其他人有所帮助。

AppDelegate 中,您可以获得正确的安全区域值并将其存储在单例中(在我的例子中:safeAreaHeight),以便在整个应用程序中访问。从场景高度中减去数量 (sceneHeight)。

    let kWindow = UIApplication.shared.windows[0]
    safeAreaHeight = kWindow.safeAreaInsets.top + kWindow.safeAreaInsets.bottom
    screenHeight = screenRect.size.height - safeAreaHeight

在展示它之前不要忘记在 GameViewController 中调整 sceneHeight:

    if let view = self.view as! SKView? {
        // Load the SKScene from 'MainMenuScene.sks'
        if let scene = SKScene(fileNamed: "MainMenuScene") {
            // Set the scale mode to scale to fit the window
            scene.scaleMode = .aspectFit
            scene.size.height = sceneHeight
            scene.size.width = sceneWidth
            // Present the scene
            view.presentScene(scene)
        }

        view.ignoresSiblingOrder = true
        view.showsFPS = true
        view.showsNodeCount = true
    }

在加载的场景中,在本例中为MainMenuScene,您只需找到 SKScene 的子视图并通过减去其中心 safeAreaHeight

来调整其 Y 位置
    guard let subView = self.view else { return }
    subView.center.y -= safeAreaHeight

PS.: 不要调整不同场景中的所有视图(即:GameScene,GameOverScene等)。一旦调整,它会保留在整个应用程序中。