2011-07-08 70 views
0

我有一個通過NIB文件創建的按鈕。我從UIButton派生出一個類,替換了NIB文件中的類名。UIButton子類顯示錯誤

現在我的按鈕顯示沒有背景。文本在那裏,文本的字體和顏色是正確的,它按照預期做出反應,但是就好像背景是透明的。在NIB中,它不透明 - 我沒有改變除類名以外的任何屬性。

子類很平凡 - 它不會覆蓋任何東西(現在)。請問我做錯了什麼?

的原因,我需要的UIButton的子類,是因爲我希望能夠在某些情況下,從按鈕拖動文本到別處。如果在UIKit提供的視圖中有另一種方法來處理拖放,我願意聽到。

回答

0

真的不知道有什麼不對的子類,但「網(包括SO)全是有關繼承UIButton的警世故事,怎麼你不應該。

所以我會用四種觸摸處理方法來調整方法。下面的函數取代了按鈕的設置方法與我的實現(從myButton的類所),同時節省了舊系統中的按鈕類根據不同的選擇:

//Does NOT look at superclasses 
static bool MethodInClass(Class c, SEL sel) 
{ 
    unsigned n,i ; 
    Method *m = class_copyMethodList(c, &n); 
    for(i=0;i<n;i++) 
    { 
     if(sel_isEqual(method_getName(m[i]), sel)) 
      return true; 
    } 
    return false; 
} 

static void MountMethod(Class &buc, SEL SrcSel, SEL SaveSlotSel) 
{ 
    IMP OldImp = [buc instanceMethodForSelector:SrcSel]; 
    IMP NewImp = [[MyButton class] instanceMethodForSelector:SrcSel]; 
    if(OldImp && NewImp) 
    { 
     //Save the old implementation. Might conflict if the technique is used 
     //independently on many classes in the same hierarchy 
     Method SaveMe = class_getInstanceMethod(buc, SaveSlotSel); 
     if(SaveMe == NULL) 
      class_addMethod(buc, SaveSlotSel, OldImp, "[email protected]:@@"); 
     else 
      method_setImplementation(SaveMe, OldImp); 

     //Note: the method's original implemenation might've been in the base class 
     if(MethodInClass(buc, SrcSel)) 
     { 
      Method SrcMe = class_getInstanceMethod(buc, SrcSel); 
      if(SrcMe) 
       method_setImplementation(SrcMe, NewImp); 
     } 
     else //Add an override in the current class 
      class_addMethod(buc, SrcSel, NewImp, "[email protected]:@@"); 
    } 
} 

,並呼籲它這樣:

Class buc = [bu class]; 
MountMethod(buc, @selector(touchesBegan:withEvent:), @selector(MyButton_SavedTouchesBegan:withEvent:)); 
    MountMethod(buc, @selector(touchesCancelled:withEvent:), @selector(MyButton_SavedTouchesCancelled:withEvent:)); 
    MountMethod(buc, @selector(touchesEnded:withEvent:), @selector(MyButton_SavedTouchesEnded:withEvent:)); 
    MountMethod(buc, @selector(touchesMoved:withEvent:), @selector(MyButton_SavedTouchesMoved:withEvent:)); 

這有安裝了所有的按鈕說方法的缺點,不只是爲那些需要的。在MyButton的實現中,如果要爲此特定按鈕啓用拖放功能,還需要進行額外的檢查。爲此,我使用了關聯的對象。

一個晴朗的一點是,touchesXXX方法在UIControl類來實現,而不是在UIButton的。所以我的第一個天真的混合實現將取代UIControl中的方法而不是按鈕類。目前的實施方式並不以任何方式。此外,它不會假設按鈕的運行時類。可以是UIButton,可以是任何東西(並且在真正的iOS中,它是UIRoundedRectButton)。

0

檢查NIB文件中按鈕的狀態。 您可能正在查看「活動」狀態或其他更常見的UICONTROLSTATENORMAL。

+0

不,背景和alpha設置爲所有狀態。 –