为动画添加UIImage到NSMutable数组

时间:2015-07-20 14:13:47

标签: ios objective-c animation memory-leaks uiimage

我有一个应用程序,可以根据项目导航器(不是Images.xcassets)中存储在组中的图像创建动画。此代码“有效”,因为它可以正常设置动画,但使用imageNamed会导致内存泄漏,因为图像文件未被释放。

我无法弄清楚为什么使用imageNamed:添加可以将图像添加到我的数组中,但imageWithContentsOfFile:却没有。

关于我的应用机制的一些信息:

self.myPhoto在另一个ViewController的segue上设置。图像的数量可能会有所不同,因此在将文件添加到阵列之前,我会测试文件是否为“那里”。

文件名遵循以下命名约定:

"1-1.jpg"
"2-1.jpg"
"2-2.jpg"
"99-1.jpg"
"99-2.jpg"
"99-3.jpg"
"99-4.jpg"

此代码有效,但图像没有解除分配,导致内存泄漏:

- (void)startAnimation {

    NSMutableArray *imageArray = [[NSMutableArray alloc] init];

    for (int imageNumber = 1; self.myPhoto != nil; imageNumber++) {
        NSString *fileName = [NSString stringWithFormat:@"%@-%d.jpg", self.myPhoto, imageNumber];

        // check if a file exists
        if ([UIImage imageNamed:fileName]) {
            // if it exists, add it to the array
            [imageArray addObject:[UIImage imageNamed:fileName]];
        } else {
            // otherwise, don't add image to the array
            break;
        }
    }

    self.myImageView.animationImages = imageArray;
    self.myImageView.animationDuration = 1.5f;
    self.myImageView.animationRepeatCount = 0;
    self.myImageView.contentMode = UIViewContentModeScaleAspectFit;
    [self.myImageView startAnimating];

}

我在上面运行了仪器,看到我的动画发生了内存泄漏。在StackOverflow上挖掘一下,我发现我将文件添加到myArray的方式会导致图像无法解除分配。

所以我尝试了这个,而不是:

- (void)startAnimation {

    NSMutableArray *imageArray = [[NSMutableArray alloc] init];

    for (int imageNumber = 1; self.myPhoto != nil; imageNumber++) {
        NSString *fileName = [NSString stringWithFormat:@"%@-%d", self.myPhoto, imageNumber];

        // check if a file exists
        if ([UIImage imageNamed:fileName]) {
            // if it exists, add it to the array
            [imageArray addObject:[UIImage imageWithContentsOfFile:[[NSBundle mainBundle]pathForResource:[NSString stringWithFormat:@"%@", fileName] ofType:@"jpg"]]];
            NSLog(@"%@ added to imageArray", fileName);
        } else {
            // otherwise, don't add image to the array
            break;
        }
    }

    NSLog(@"There are %lu images in imageArray", (unsigned long)imageArray.count);

    self.myImageView.animationImages = imageArray;
    self.myImageView.animationDuration = 1.5f;
    self.myImageView.animationRepeatCount = 0;
    self.myImageView.contentMode = UIViewContentModeScaleAspectFit;
    [self.myImageView startAnimating];

}

当我这样做的时候,动画加载的页面会出现,但图像不会被添加到我的数组中 - 。这是一个记录完备的问题。以下是一些涉及此问题的帖子:

Dirty Memory because of CoreAnimation and CG image

How do I use imageWithContentsOfFile for an array of images used in an animation?

感谢您的阅读。我很难过,虽然我有信心解决这个问题对我来说是一个令人吃惊的愚蠢的疏忽。证明我是正确的;)

1 个答案:

答案 0 :(得分:1)

我在绝望中做了一些小改动,我偶然发现了“答案”。评论说明我做了哪些更改:

- (void)startAnimation {

    NSMutableArray *imageArray = [[NSMutableArray alloc] init];

    for (int imageNumber = 1; self.myPhoto != nil; imageNumber++) {
        // I set the filename here, adding .jpg to it
        NSString *fileName = [NSString stringWithFormat:@"%@-%d.jpg", self.myPhoto, imageNumber];

        // check if a file exists
        if ([UIImage imageNamed:fileName]) {
            // if it exists, add it to the array
            // I blanked out ofType, as it's set when I create the local fileName variable
            [imageArray addObject:[UIImage imageWithContentsOfFile:[[NSBundle mainBundle]pathForResource:[NSString stringWithFormat:@"%@", fileName] ofType:@""]]];
        } else {
            // otherwise, don't add image to the array
            break;
        }
    }

    self.myImageView.animationImages = imageArray;
    self.myImageView.animationDuration = 1.5f;
    self.myImageView.animationRepeatCount = 0;
    self.myImageView.contentMode = UIViewContentModeScaleAspectFit;
    [self.myImageView startAnimating];

}