SKShapeNode存在无界内存增长问题。

6
如果我在SKScene子类的init方法中运行这段代码
for (int i = 0; i < 100; i++) {

            SKShapeNode *shape = [SKShapeNode node];

            shape.antialiased = NO;

            CGMutablePathRef path = CGPathCreateMutable();

            CGPathAddEllipseInRect(path, NULL, CGRectMake(arc4random()%320, arc4random()%320, 10, 10));

            shape.path = path;

            [shape setStrokeColor:[UIColor blackColor]];

            CGPathRelease(path);

            [self addChild:shape];

            [shape removeFromParent];

        }

每当我在控制SKView的控制器中运行这段代码时,它都会执行。
SKView * skView = (SKView *)self.view;

// Create and configure the scene.

SKScene * scene = [ZTMyScene sceneWithSize:skView.bounds.size];

scene.scaleMode = SKSceneScaleModeAspectFill;



// Present the scene.

[skView presentScene:scene];

我的内存使用量会不断增长,直到内存被填满并崩溃。如果我使用SKSpriteNode,就不会发生这种情况。有人有解决方法吗?
概述:我创建了一个Sprite Kit模板项目,添加了很多SKShapeNodes,并用新的SKScene替换了旧的场景。
我将示例项目添加到了Github上:https://github.com/zeiteisen/MemoryTest

3
如果你能将此问题隔离在一个简化的项目中并验证此行为,则应向苹果报告此漏洞。报告方法请参考 https://developer.apple.com/bug-reporting/using-bug-reporter/。 - CodeSmile
2个回答

1

我在阅读另一篇文章时意识到了这个问题。我稍微尝试了一下 SKShapeNode,并确实验证了这里指出的内存泄漏问题。

在这样做的时候,我有了一个想法...

不是一个新想法,更像是重新运用的想法。这个美妙的想法让我可以尽情使用 SKShapeNodes :)

对象池

是的... 我只是创建了一个 SKShapeNodes 的对象池,根据需要重复使用。真是有很大的区别 :)

您只需在需要时重新定义路径,完成后返回到您的池中,并在以后的某个时间再次使用。

在您的 SKScene 中创建一个 ivar 或属性 NSMutableArray,并在 init 时创建。您可以在 init 期间填充数组或根据需要创建它们。

这是我为了从池中获取新节点创建的快速方法:

-(SKShapeNode *)getShapeNode
{
    if (pool.count > 0)
    {
        SKShapeNode *shape = pool[0];
        [pool removeObject:shape];
        return shape;
    }

    // if there is not any nodes left in the pool, create a new one to return
    SKShapeNode *shape = [SKShapeNode node];

    return shape;
}

所以,无论在场景中的哪个位置,您都需要一个SKShapeNode,可以这样做:
SKShapeNode *shape = [self getShapeNode];
// do whatever you need to do with the instance

当您使用完形状节点后,只需将其返回到池中并将路径设置为NULL,例如:
[pool addObject:shape];
[shape removeFromParent];
shape.path = NULL;

我知道这只是一个权宜之计,而不是一个理想的解决方案,但无疑这是对于任何想要使用大量SKShapeNodes且不会内存泄漏的人来说非常可行的解决方法。


0
您正在添加形状,然后立即将其删除,为什么?
[self addChild:shape];

[shape removeFromParent]

3
为了展示他所遇到的问题最简单的形式,可以推测如此。 - Dfowj

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接