2012-07-17 89 views
1

我將UIButton添加爲子視圖後遇到問題。當我嘗試調整視圖上的按鈕位置時,我始終只用第一個按鈕添加UIView而不是UIButton。當我使用isKindOfClass時,其餘的返回爲UIButton。這裏是一個代碼片段如下添加到子視圖後,UIButton返回爲UIView?

首先,我從viewDidload調用createTiles方法將按鈕添加爲子視圖,然後通過調用adustLandscapeTiles/Portrait方法檢測設備方向後調整按鈕佈局。

我不確定爲什麼會發生任何想法? ?

// Adding buttons to view 
- (void)createTiles 
{  
    for(int i=0;i<[self.contentList count];i++) 
    { 
     UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect]; 
     [button addTarget:self action:@selector(buttonSelection:)forControlEvents:UIControlEventTouchDown]; 
     [button setTitle:[ [contentList objectAtIndex:i] valueForKey:@"nameKey"] forState:UIControlStateNormal]; 
     button.tag=i; 

     [self.view insertSubview:button atIndex:0]; 
     NSLog(@"adding %i %@",i , [ [contentList objectAtIndex:i] valueForKey:@"nameKey"]); 
     [button release]; 

    } 
    } 

- (void)adustLandscapeTiles 
{ 
    for (int row = 0; row < Portrait_TILE_ROWS; ++row) 
    { 
     for (int col = 0; col < Portrait_TILE_COLUMNS; ++col) 
     { 
      int index = (row * Portrait_TILE_COLUMNS) + col;  
      CGRect frame = CGRectMake(LandScape_TILE_MARGIN + col * (LandScape_TILE_MARGIN + LandScape_TILE_WIDTH), 
            LandScape_TILE_MARGIN + row * (LandScape_TILE_MARGIN + LandScape_TILE_HEIGHT), 
            LandScape_TILE_WIDTH, LandScape_TILE_HEIGHT); 
    /// check subview is a button  
    NSLog(@"index: %i tag : %i Is of type UIButton?: %@",index,[[self.view viewWithTag:index] tag], ([ [self.view viewWithTag:index] isKindOfClass: [UIButton class]])? @"Yes" : @"No"); 

     /// Only the first button added with tag zero return UView instead of UIButton ?? 
      UIButton *tmb= (UIButton *)[self.view viewWithTag:index]; 
      if([tmb isKindOfClass:[UIButton class]]) //isKindOfClass 
      { 
       [ [self.view viewWithTag:index] setFrame:frame]; 

      } 

     } 
    } 

} 

回答

1

當我加入了更強大的解決您的問題,我注意到你在釋放button。你不應該打電話[button release]你不擁有它!但這不是你唯一的問題...

如果你沒有給UIView分配一個標籤,它會有一個零標籤,所以如果你的視圖有一些你沒有給你分配標籤的其他子視圖可能是得到其中一個。嘗試添加一些偏移將自己的代碼,例如:

// Somewhere early in your .m file 
const NSInteger kButtonTagOffset 256 

// In your createTiles 
button.tag = (kButtonTagOffset + i); 

顯然,你需要添加,當您找回您的瓷磚也該偏移。

話雖如此,當前的方法是什麼一個更有經驗的程序員可能調用脆弱如果有人曾經子類類或者即使你編輯了一段時間以後,你可以分配發生衝突的代碼,並導致一些問題。您可能會考慮更多穩健的解決方案。

因爲你真正想要做的就是保持按鈕的數組,你可以通過索引訪問,爲什麼不做到這一點,而不依賴於標籤?

因此在您的UIViewController中添加一個NSMutableArray來保存您的按鈕。

// In your .h or with private methods: 
@property (nonatomic, retain) NSMutableArray* buttons; 

// At the top of your @implementation 
@synthesize buttons; 

// A modified createTiles 
// Adding buttons to view 
- (void)createTiles 
{  
    self.buttons = nil; /* in case viewDidUnload id not do this. */ 
    self.buttons = [[[NSMutableArray alloc] init] autorelease]; 
    for(int i=0;i<[self.contentList count];i++) 
    { 
     UIButton *button = [UIButton buttonWithType:UIButtonTypeRoundedRect]; 
     [button addTarget:self  
        action:@selector(buttonSelection:) 
     forControlEvents:UIControlEventTouchDown]; 
     [button setTitle:[[contentList objectAtIndex:i] valueForKey:@"nameKey"] 
       forState:UIControlStateNormal]; 

     [self.view insertSubview:button atIndex:0]; 
     NSLog(@"adding %i %@", i, 
         [[contentList objectAtIndex:i] valueForKey:@"nameKey"]); 
     [self.buttons insertObject:button atIndex:0]; 
    } 
} 

- (void)adustLandscapeTiles 
{ 
    for (int row = 0; row < Portrait_TILE_ROWS; ++row) 
    { 
     for (int col = 0; col < Portrait_TILE_COLUMNS; ++col) 
     { 
      int index = (row * Portrait_TILE_COLUMNS) + col;  
      UIView* buttonView = [self.buttons objectAtIndex:index]; 

      CGRect frame = CGRectMake(LandScape_TILE_MARGIN + col *  
           (LandScape_TILE_MARGIN + LandScape_TILE_WIDTH), 
           LandScape_TILE_MARGIN + row *  
           (LandScape_TILE_MARGIN + LandScape_TILE_HEIGHT), 
           LandScape_TILE_WIDTH, 
           LandScape_TILE_HEIGHT); 
      // check subview is a button  
      NSLog(@"index: %i Is of type UIButton?: %@", index, 
        ([ [buttonView viewWithTag:index] isKindOfClass: [UIButton class]])? 
         @"Yes" : @"No"); 

      UIButton *tmb= (UIButton *)buttonView; 
      if([tmb isKindOfClass:[UIButton class]]) //isKindOfClass 
      { 
       [buttonView setFrame:frame]; 
      } 
     } 
    } 
} 
+0

感謝IDZ,當我試圖改變在Interface Builder的觀點是沒有工作的標記值,但與你的偏移建議的工作完美...謝謝 – user519274 2012-07-17 14:09:53

+0

糾正我,如果我錯了,也不會該語句[self.view insertSubview:按鈕atIndex:0]增加按鈕的保留計數與[self.buttons insertObject:button atIndex:0]相同? 。您的方法肯定會更易於維護,而我最初將執行該方法,但我擔心增加按鈕的保留數量? – user519274 2012-07-17 16:56:12

+0

保留兩次只要釋放兩次就沒有問題。因此,在您的情況下,要成爲一名優秀的內存管理公民,您需要確保在'viewDidUnload'中設置'self.buttons = nil'並刪除所有子視圖。您應該已經在執行刪除所有子視圖步驟,因爲您提到您正在從'viewDidLoad'調用'createTiles'。規則是你應該在'viewDidUnload'和'dealloc'中釋放* viewDidLoad中創建的任何內容。 – idz 2012-07-17 19:02:25

相關問題