赞助商

swift – SceneKit:应用程序在SCNView上渲染SpriteKit粒子系统时崩溃,当所有代码似乎都是系统代码的一部分时如何调试

发布时间:2019-05-15 发布网站:脚本之家
脚本之家收集整理的这篇文章主要介绍了swift – SceneKit:应用程序在SCNView上渲染SpriteKit粒子系统时崩溃,当所有代码似乎都是系统代码的一部分时如何调试脚本之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
在SCNView的overlaySKScene属性中运行SpriteKit粒子系统会导致应用程序崩溃,并显示下面的堆栈跟踪.

基于堆栈跟踪,似乎所有系统代码都在运行,所以你应该如何调试崩溃,更重要的是,确定它是否是SceneKit / SpriteKit的错误或应用程序中的错误?

对于它的价值,下面是添加粒子系统的函数,但它没有在堆栈跟踪中引用.

fileprivate func animateFireworks(scnPoint: CGPoint,color: UIColor) {
    // Set emitter properties
    let particleBirthRate = CGFloat(150)
    let maxParticles = 50
    let numEmitters = 5

    // SceneView point -> SpriteKit point
    let skOverlayPoint = skOverlay.convertPoint(fromView: scnPoint)

    // Create emitters
    for _ in 0..<numEmitters {
        let fireworksEmitter = SKEmitterNode(fileNamed: ExplosionEmitterFilename)!

        // Set particle size
        let particleSize = CGSize(width: 20,height: 20)
        fireworksEmitter.particleSize = particleSize

        // Set color for emitter
        fireworksEmitter.particleColorSequence = nil
        fireworksEmitter.particleColor = color

        // Set number of particles
        fireworksEmitter.particleBirthRate = particleBirthRate
        fireworksEmitter.numParticlesToEmit = maxParticles

        // Position at point
        fireworksEmitter.position = skOverlayPoint

        // Add to SpriteKit overlay
        skOverlay.addChild(fireworksEmitter)

        // Remove emitter,<animationDur> is only a rough estimate
        let animationDur = 3 * Double(fireworksEmitter.particleLifetime + fireworksEmitter.particleLifetimeRange)
        delay(animationDur) {
            fireworksEmitter.removeFromParent()
        }
    }
}


func delay(_ delay:Double,closure:@escaping ()->()) {
    DispatchQueue.main.asyncAfter(
        deadline: DispatchTime.now() + Double(Int64(delay * Double(NSEC_PER_SEC))) / Double(NSEC_PER_SEC),execute: closure)
}


> Thread 11 Queue : com.apple.scenekit.renderingQueue.SCNView0x121d8d570
> (serial)
> #0    0x000000019c710aac in SKCParticleManager::enumerateParticleSystems(void (SKCParticleSystem*)
> block_pointer) ()
> #1    0x000000019c723d74 in SKCParticleSystemNode::generateRenderData_Quads(SKCRenderInfo*) ()
> #2    0x000000019c7236c0 in SKCParticleSystemNode::addRenderOps_Quads(SKCRenderInfo*,> std::__1::shared_ptr<jet_command_buffer> const&) ()
> #3    0x000000019c71dc4c in SKCRenderer::expandRenderGroup(std::__1::shared_ptr<SKCRenderSortGroup>
> const&,std::__1::shared_ptr<jet_command_buffer> const&) ()
> #4    0x000000019c71b238 in SKCRenderer::expandRenderPass(std::__1::shared_ptr<SKCRenderPass>
> const&,std::__1::shared_ptr<jet_command_buffer> const&) ()
> #5    0x000000019c71a888 in SKCRenderer::render(SKCNode*,float __vector(4),std::__1::shared_ptr<jet_framebuffer> const&,unsigned int __vector(4),simd_float4x4,bool,NSDictionary*,SKCStats*,> SKCStats*,double) ()
> #6    0x000000019c6516a4 in -[SKSCNRenderer renderWithEncoder:pass:commandQueue:] ()
> #7    0x0000000199479fc8 in -[SCNRenderContextMetal renderSKSceneWithRenderer:overlay:atTime:] ()
> #8    0x0000000199525018 in -[SCNRenderer _drawOverlaySceneAtTime:] ()
> #9    0x00000001995e199c in __C3DEngineContextRenderPassInstance ()
> #10   0x00000001995e27cc in C3DEngineContextRenderMainTechnique ()
> #11   0x0000000199526508 in -[SCNRenderer _renderSceneWithEngineContext:sceneTime:] ()
> #12   0x0000000199526688 in -[SCNRenderer _drawSceneWithNewRenderer:] ()
> #13   0x0000000199526ccc in -[SCNRenderer _drawScene:] ()
> #14   0x0000000199527144 in -[SCNRenderer _drawAtTime:] ()
> #15   0x00000001995cfa74 in -[SCNView _drawAtTime:] ()
> #16   0x00000001994876c0 in __69-[NSObject(SCN_DisplayLinkExtensions) SCN_setupDisplayLinkWithQueue:]_block_invoke ()
> #17   0x000000019959700c in __36-[SCNDisplayLink _callbackWithTime:]_block_invoke ()
> #18   0x00000001042a12cc in _dispatch_call_block_and_release ()
> #19   0x00000001042a128c in _dispatch_client_callout ()
> #20   0x00000001042aff80 in _dispatch_queue_serial_drain ()
> #21   0x00000001042a47ec in _dispatch_queue_invoke ()
> #22   0x00000001042b0f6c in _dispatch_root_queue_drain_deferred_wlh ()
> #23   0x00000001042b8020 in _dispatch_workloop_worker_thread ()
> #24   0x00000001858a6f1c in _pthread_wqthread ()

解决方法

单独查看此函数时很难分辨出发生了什么,但崩溃堆栈跟踪行SKCParticleManager :: enumerateParticleSystems(void(SKCParticleSystem *))让我怀疑该问题与粒子发射器的添加/删除有关,可能是主队列以外的队列.

SKNode docs

Manipulations to nodes must occur in the main thread.

我将仔细检查是否仅在主队列上调用addChild和removeFromParent方法.

总结

以上是脚本之家为你收集整理的swift – SceneKit:应用程序在SCNView上渲染SpriteKit粒子系统时崩溃,当所有代码似乎都是系统代码的一部分时如何调试全部内容,希望文章能够帮你解决swift – SceneKit:应用程序在SCNView上渲染SpriteKit粒子系统时崩溃,当所有代码似乎都是系统代码的一部分时如何调试所遇到的程序开发问题。

如果觉得脚本之家网站内容还不错,欢迎将脚本之家网站推荐给程序员好友。

本图文内容来源于网友网络收集整理提供,作为学习参考使用,版权属于原作者。
如您有任何意见或建议可联系处理。小编QQ:76874919,请注明来意。
标签: