2011-03-25 63 views
11

对于我的应用程序,我试图将CGRect对象存储到NSMutableArray中。它正在加载并在日志语句中打印,但试图从数组中取出CGRect会显示错误。这里是一个代码片段:从数组中获取CGRect

CGRect lineRact = CGRectMake([[attributeDict objectForKey:@"x"] floatValue], 
    [[attributeDict objectForKey:@"y"] floatValue], 
    [[attributeDict objectForKey:@"width"] floatValue], 
    [[attributeDict objectForKey:@"height"] floatValue]); 

    [lineRactangle addObject:NSStringFromCGRect(lineRact)]; 

我怎样才能从数组中得到rects?

回答

22
[lineRactangle addObject:[NSValue valueWithCGRect:lineRect]]; 
+0

感谢您的早期重播...... – ajay 2011-03-25 11:40:06

0

CGRect是一个结构,你不能把它放在NSArray中。你只能添加对象。

40

CGRect是一个结构体,而不是一个对象,因此不能存储在NSArrays或NSDictionaries中。你可以把它变成一个字符串,把该字符串回一个的CGRect,但最好的方法是通过一个NSValue封装它:

NSValue *myValue = [NSValue valueWithCGRect:myCGRect]; 

然后,您可以在存储阵列和字典此NSValue对象。为了把它放回一个的CGRect,你会怎么做:

CGRect myOtherCGRect = [myValue CGRectValue]; 
+0

还是今天,'NSValue * myvalue的= [NSValue valueWithRect:myCGRect ];' – 2015-02-24 14:54:32

+1

@FitterMan:这只适用于OS X,不适用于iOS; iOS上不提供'valueWithRect:'。但即使在OS X上,你也不应这样做:'valueWithRect:'需要一个'NSRect',而不是'CGRect'。在64位构建中,'NSRect'是'CGRect'的一个类型定义,所以它在那里工作没有问题,但是对于32位构建,如果没有定义'NS_BUILD_32_LIKE_64'定义,你会得到一个警告/错误因为它们被定义为两个独立的结构。尽管他们的内存表示是相同的,但编译器(正确地)将它们视为两个不同的东西。 – DarkDust 2015-02-24 15:15:53

+0

感谢您的澄清。 – 2015-02-24 19:11:22

6

使用NSValueCGRect从而将它们存储在NSArray秒。

例如:

CGRect r = CGRectMake(1,2,3,4); 
NSValue *v = [NSValue valueWithCGRect:rect]; 
NSArray *a = [NSArray arrayWithObject:v]; 
CGRect r2 = [[a lastObject] CGRectValue]; 

参见documentation为其它支持的结构。

0

或更多的东西 '极端' ...创建保存的CGRect(S)

movPosTable = [[NSArray alloc] initWithObjects: 
      [[NSArray alloc] initWithObjects: [NSValue valueWithCGRect:[GridAB frame]], [NSValue valueWithCGRect:[GridBA frame]], [NSValue valueWithCGRect:[GridBB frame]], nil], 
      [[NSArray alloc] initWithObjects: [NSValue valueWithCGRect:[GridAA frame]], [NSValue valueWithCGRect:[GridAC frame]], [NSValue valueWithCGRect:[GridBA frame]], [NSValue valueWithCGRect:[GridBB frame]], [NSValue valueWithCGRect:[GridBC frame]], nil], 
      [[NSArray alloc] initWithObjects: [NSValue valueWithCGRect:[GridAB frame]], [NSValue valueWithCGRect:[GridBB frame]], [NSValue valueWithCGRect:[GridBC frame]], nil], nil]; 

的阵列的阵列,其中 'GridAA', 'GridAB' 等对应UIViews

+0

应该更好地添加此附录作为对所引用答案的评论,因为我们无法将其视为解决方案,并且它似乎是一条评论。 – iOS 2012-10-28 09:59:35

2

实际上,我认为迄今为止的答案都不能解决阿贾伊问的问题。简短的回答是:您需要提供CGRectMakeintValue,而不是floatValue字典项目。如果你需要几个CGRects做到这一点,这里有一个建议的方法:

- (CGRect) NSArrayToCGRect: (NSDictionary *) attributeDict 
{ 
    int x = [[attributeDict objectForKey:@"x"] intValue]; 
    int y = [[attributeDict objectForKey:@"y"] intValue]; 
    int w = [[attributeDict objectForKey:@"width"] intValue]; 
    int h = [[attributeDict objectForKey:@"height"] intValue]; 

    return CGRectFromString([NSString stringWithFormat: @"{{%d,%d},{%d,%d}}", x, y, w, h]); 
} 

有可能做到这一点更优雅的方式,但上面的代码不工作。

2

如果你的对象可以用 “.frame” 进行设置,你可以使用:

// {{CGFloat x,CGFloat y}, {CGFloat width,CGFloat height}} 
NSString *objectCoords = @"{{116,371},{85,42}}"; 
myObject.frame = CGRectFromString(objectcoords); 

或多个对象:

NSArray *objectCoords = [NSArray arrayWithObjects: 
         @"{{116,371},{85,42}}", 
         @"{{173,43},{85,42}}", 
         @"{{145,200},{85,42}}", 
         nil]; 

myObject1.frame = CGRectFromString([objectCoords objectAtIndex:0]); 
myObject2.frame = CGRectFromString([objectCoords objectAtIndex:1]); 
myObject3.frame = CGRectFromString([objectCoords objectAtIndex:2]);