我目前正在开发一款iPad应用程序,该应用程序将大约250个UIImage加载到UIButton中(然后更改颜色),创建世界地图 - 每个国家都有自己的按钮和相应的图像 - 在加载游戏时。我遇到的问题是,在retina iPad上,应用程序在加载图像时使用了约650MB的RAM,这是不可思议的。
当应用程序最初加载游戏时,它使用以下代码将图像设置为按钮(Territory是UIButton的子类)。
这导致以下的内存使用情况。尽管块被
在另一个循环中使用此代码(该循环由另一个函数中的
我在苹果开发者论坛上发布了一个帖子,预示了这个问题。
我也联系过苹果开发者TSI,他们建议使用“惰性图像加载”。我研究了一下,但我没有找到在非基于页面的
现在我已经迷失了如何解决这个问题。我尝试了我能想到的一切,花了几个小时来尝试解决这个问题,但似乎找不到任何可行的解决方案。如果有人能帮我,我真的很感激。如果您想查看更多信息或代码,请告诉我,我很乐意发布它。提前感谢您的帮助。
编辑:
我一直在尝试,我正在使用以下代码在
当应用程序最初加载游戏时,它使用以下代码将图像设置为按钮(Territory是UIButton的子类)。
//Initialize the arrays of each territory and add an action to the territory
for (int i = (int)territoryArray.count - 1; i >= 0; i--) {
@autoreleasepool {
//Cast the object into a territory object
Territory *ter = (Territory *)[territoryArray objectAtIndex:i];
//Set the territory's image
[ter setImage:[UIImage imageWithContentsOfFile:[[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:@"%@T%i.png", [defaults objectForKey:@"Current_Map"], i + 1] ofType:nil]] forState:UIControlStateNormal];
}
}
这导致以下的内存使用情况。尽管块被
@autoreleasepool
包围,但循环运行时会出现峰值,且该峰值不会消失。请注意,ImageIO
正在使用内存:
当领土的图像文件中包含原始颜色时,该屏幕截图被拍摄。我正在使用MGImageUtilities
中的UIImage+Tint
库对图像进行着色。在使用该库时,使用以下代码:
[ter setImage:[[ter imageForState:UIControlStateNormal] imageTintedWithColor:[UIColor colorWithRed:[[colors objectAtIndex:0] floatValue]/255.0 green:[[colors objectAtIndex:1] floatValue]/255.0 blue:[[colors objectAtIndex:2] floatValue]/255.0 alpha:1.0]] forState:UIControlStateNormal];
在另一个循环中使用此代码(该循环由另一个函数中的
@autoreleasepool
包围),在加载所有图像后,会出现以下内存使用情况。请注意,CG光栅数据
正在使用内存。
我在苹果开发者论坛上发布了一个帖子,预示了这个问题。
我也联系过苹果开发者TSI,他们建议使用“惰性图像加载”。我研究了一下,但我没有找到在非基于页面的
UIScrollView
上执行此操作的方法。现在我已经迷失了如何解决这个问题。我尝试了我能想到的一切,花了几个小时来尝试解决这个问题,但似乎找不到任何可行的解决方案。如果有人能帮我,我真的很感激。如果您想查看更多信息或代码,请告诉我,我很乐意发布它。提前感谢您的帮助。
编辑:
我一直在尝试,我正在使用以下代码在
scrollViewDidScroll:
中工作。它似乎起作用了,但是内存并没有被释放,它继续增加。有什么想法吗?CGRect currentF = [scrollView convertRect:scrollView.bounds toView:scrollView.contentView];
//Loop through all territories and determine which need to be rendered
for (int i = (int)territoryArray.count - 1; i >= 0; i--) {
@autoreleasepool {
//See if the territory is on-screen
if (CGRectIntersectsRect(currentF, [[territoryArray objectAtIndex:i] frame])) {
//See if the territory needs an image
if ([[territoryArray objectAtIndex:i] image] == nil) {
//Set the territory's image
[[territoryArray objectAtIndex:i] setImage:[UIImage imageWithContentsOfFile:[[NSBundle mainBundle] pathForResource:[NSString stringWithFormat:@"%@T%i.png", [defaults objectForKey:@"Current_Map"], i + 1] ofType:nil]] forState:UIControlStateNormal];
}
} else {
//Remove the territory's image, it is off-screen
[[territoryArray objectAtIndex:i] setImage:nil forState:UIControlStateNormal];
}
}
}