2011-02-16 71 views
0

我有3種方法之一,其獲得一個顏色並將其保存爲在用戶的默認值的數據對象,其中一個繪製一個矩形,並與保存在用戶的默認值的顏色填充它和一種方法,其初始化並NSColor實例,當應用程序啓動時,顏色以用戶默認值保存。NSColor和NSUserDefaults導致;程序接收到的信號:「EXC_BAD_ACCESS」

下面是3種方法,但問題是當我建立並運行應用程序,我得到這個錯誤,任何人都可以理解爲什麼我得到這個錯誤的,什麼是錯我的代碼。

Program received signal: 「EXC_BAD_ACCESS」.

- (void)setColor:(NSColor *)color 
{ 
    _color = [color copy]; 

    NSData *data = [NSArchiver archivedDataWithRootObject:_color]; 
    [[NSUserDefaults standardUserDefaults] setObject:data forKey:@"MyColor"]; 

    [self setNeedsDisplay:YES]; 
} 


    - (void)drawRect:(NSRect)rect 
{ 

    NSRect rect1 = NSInsetRect([self bounds], 4.0, 4.0); 
    NSBezierPath * path; 
    [_color set]; 
    path = [NSBezierPath bezierPathWithRoundedRect:rect1 
                xRadius:6.0 
                yRadius:6.0]; 
    [path fill]; 
} 

- (id)initWithFrame:(NSRect)frame 
{ 
    self = [super initWithFrame:frame]; 
    if (self == nil) 
     return nil; 

    _color = [NSColor blackColor]; 
    NSData *data = [[NSUserDefaults standardUserDefaults] objectForKey:@"MyColor"]; 
    if (data != nil){ 
    NSColor *color1 = [NSUnarchiver unarchiveObjectWithData:data]; 
    _color = color1;} 

    return self; 
} 

回答

4

的問題是在你的initWithFrame:方法。 _color設置爲[NSColor blackColor][NSUnarchiver unarchiveObjectWithData:data]。這兩種方法都會返回自動釋放的對象。您需要保留它們以確保在調用drawRect:時它們仍然存在。最簡單的方法是在解壓後調用[_color retain],這樣如果blackColor被替換,仍然會自動釋放。

此外,請確保您釋放舊_Color在setColor:。現在它每次調用時都會泄漏一個NSColor對象。

+0

用於發現泄漏的+1。 – dreamlax 2011-02-17 00:04:28

1

這是你的問題,我認爲:

NSColor *color1 = [NSUnarchiver unarchiveObjectWithData:data]; 
_color = color1; 

你不擁有該對象由unarchiveObjectWithData:返回,但你把它分配給一個實例變量,並把它當作如果您所擁有。通過使用copy方法,您可以明確地獲取對象的所有權:

_color = [color1 copy]; 
相關問題