iOS幾點開發技巧

幾點iOS開發技巧

發佈於:2013-08-27 15:59閱讀數:8636

原文作者是開發界中知曉度相當高的 Mugunth Kumar,他是 MKNetworkKit 的作者(雖然沒有 AFNetworking 使用那麼廣泛,但也是一個很棒的 Network Kit),更是最近流傳甚廣的《iOS 5/6 Programming - Pushing The L

轉自I'm Allen的博客
 
 
原文來自破船的分享
 
原文作者是開發界中知曉度相當高的 Mugunth Kumar,他是 MKNetworkKit 的作者(雖然沒有 AFNetworking 使用那麼廣泛,但也是一個很棒的 Network Kit),更是最近流傳甚廣的《iOS 5/6 Programming - Pushing The Limits》的作者。
 
文章中 MK 介紹了幾點開發中常用的小技巧,幾條 Tips 簡單易懂,但是很實用,不但可以提高開發效率,而且可以提高代碼的可讀性和可複用性。
 
Types in Objective-C 和 Naming Conventions 兩個章節介紹性內容較多,下面從 Subclassing 開始簡單直譯一下,第一次翻譯,有諸多不到位的地方,各位多包涵。
 
Subclassing 繼承/子類
大多語言允許開發者子類化框架所提供的類,但是在 Objective-C 中不完全是這樣。大部分常用的類,諸如 NSArray、NSSet、NSDictionary 基本上都是集合類型的。不建議繼承這些類,除非你準備轉發調用或者實現所有必要的原始方法。
 
在傳統的開發語言中,通常會通過繼承基礎類型(類似 NSArray 的類)來新增方法,重載已有的方法,或是自定義 UI 組件的外觀。在 Objective-C 中,一般通過 Category 來擴展新方法。通過混合方法(swizzling the method?)來重載 SDK 提供的實現。以及外觀相關的代理協議(Protocol)來定製 UI 組件的外觀。
 
雖說如此,還是有一些類是經常會繼承它們的,比如 UIViewController、UITableViewController、UIControl 等。繼承 UIViewController 大概是開發過程中最棒的一件事,因爲它使得添加常見的功能變得異常簡單。在我開發的每個 App 中,會有一個繼承自 UIViewController 的子類,它實現了一組常用的方法。所有其他的 View Controllers 則都繼承自這個基礎類。
 
(譯者注:Web 開發中也常會有一個用於被繼承的 BaseController 來提供公共方法,看來開發是觸類旁通的,要多思考)
 
所以,以下繼承方法:
  1. @interface MyAppFeaturedYouTubeVideosViewController : UIViewController 
應該替換成:
  1. @interface MyAppFeaturedYouTubeVideosFeaturedViewController : MyAppViewController 
  2. @interface MyAppViewController : UIViewController 
這個公用基礎類可以在後續開發過程中用來添加公用的方法。在這個基礎父類中,我通常會申明以下方法:
  1. -(UIView*) errorView; 
  2. -(UIView*) loadingView; 
  3. -(void) showLoadingAnimated:(BOOL) animated; 
  4. -(void) hideLoadingViewAnimated:(BOOL) animated; 
  5. -(void) showErrorViewAnimated:(BOOL) animated; 
  6. -(void) hideErrorViewAnimated:(BOOL) animated; 
 
實現如下:
  1. -(UIView*) errorView { 
  2.   
  3.   return nil; 
  4.   
  5. -(UIView*) loadingView { 
  6.   
  7.   return nil; 
  8.   
  9. -(void) showLoadingAnimated:(BOOL) animated { 
  10.   
  11.   UIView *loadingView = [self loadingView]; 
  12.   loadingView.alpha = 0.0f; 
  13.   [self.view addSubview:loadingView]; 
  14.   [self.view bringSubviewToFront:loadingView]; 
  15.   
  16.   double duration = animated ? 0.4f:0.0f; 
  17.   [UIView animateWithDuration:duration animations:^{ 
  18.     loadingView.alpha = 1.0f; 
  19.   }]; 
  20.   
  21. -(void) hideLoadingViewAnimated:(BOOL) animated { 
  22.   
  23.   UIView *loadingView = [self loadingView]; 
  24.   
  25.   double duration = animated ? 0.4f:0.0f; 
  26.   [UIView animateWithDuration:duration animations:^{ 
  27.     loadingView.alpha = 0.0f; 
  28.   } completion:^(BOOL finished) { 
  29.     [loadingView removeFromSuperview]; 
  30.   }]; 
  31.   
  32. -(void) showErrorViewAnimated:(BOOL) animated { 
  33.   
  34.   UIView *errorView = [self errorView]; 
  35.   errorView.alpha = 0.0f; 
  36.   [self.view addSubview:errorView]; 
  37.   [self.view bringSubviewToFront:errorView]; 
  38.   
  39.   double duration = animated ? 0.4f:0.0f; 
  40.   [UIView animateWithDuration:duration animations:^{ 
  41.     errorView.alpha = 1.0f; 
  42.   }]; 
  43.   
  44. -(void) hideErrorViewAnimated:(BOOL) animated { 
  45.   
  46.   UIView *errorView = [self errorView]; 
  47.   
  48.   double duration = animated ? 0.4f:0.0f; 
  49.   [UIView animateWithDuration:duration animations:^{ 
  50.     errorView.alpha = 0.0f; 
  51.   } completion:^(BOOL finished) { 
  52.     [errorView removeFromSuperview]; 
  53.   }]; 
 
現在,App 中的每個 View Controller 中,可以很方便的通過調用以上方法來改變當前 View 的狀態爲 Loading 或者 Error。而且,View Controller 可以通過重載 -errorView 和 -loadingView 方法來提供自定義錯誤界面和 Loading 界面。
 
你還可以通過重載這個基礎類中的 -viewDidLoad 來統一修改所有 View 的表現。比如爲所有的 View 添加相同的背景圖片或背景色:
 
  1. - (void)viewDidLoad 
  2.   [super viewDidLoad]; 
  3.   self.view.backgroundColor = [UIColor appOffWhiteColor]; // changes all my views to "off-white" 
 
 
UI Customization 自定義 UI
自定義 UI 可以大致分成兩類,一是自定義控件,二是皮膚/主題。前者可以讓 App 更出色,而後者是大部分 App 都需要的。我建議給 UIFont 和 UIColor 寫 Category 擴展來提供自定義字體和自定義顏色。
 
例如,給 UIFont 添加如下方法:
  1. +(UIFont*) appFontOfSize:(CGFloat) pointSize { 
  2.   
  3.   return [UIFont fontWithName:@"MyriadPro-Regular" size:pointSize]; 
  4.   
  5. +(UIFont*) boldAppFontOfSize:(CGFloat) pointSize { 
  6.   
  7.   return [UIFont fontWithName:@"MyriadPro-Black" size:pointSize]; 
你就可以很方便地使用 [UIFont appFontOfSize:13] 得到 MyriadPro-Regular 字體。這樣當你的設計需求變更時,就可以很快速的更換整個 App 中的字體。
 
相同的設計模式也可以應用到自定義顏色中。給 UIColor 添加以下方法:
  1. #define GREY(color) [UIColor colorWithRed:color/255.0 green:color/255.0 blue:color/255.0 alpha:1] 
  2.   
  3. +(UIColor*) appBackgroundColor { 
  4.   
  5.   return [UIColor colorWithPatternImage:[UIImage imageNamed:@"BGPattern"]]; 
  6.   
  7. +(UIColor*) appBlack1Color { 
  8.   
  9.   return GREY(38); 
  10.   
  11. +(UIColor*) appOffWhiteColor { 
  12.   
  13.   return GREY(234); 
 
所以,千萬不要用 Interface Builder 來選顏色。
Subclassing UILabels 繼承 UILabel
還有一個小竅門,當開發者繼承 UILabel、UITextField 和 UITextView 時,通常在 -initWithFrame: 和 -initWithCoder: 方法中設置字體和顏色,參見以下代碼:
  1. @implementation AppPrefixLabel 
  2.   
  3. -(void) setup { 
  4.   
  5.   self.font = [UIFont fontWithName:@"SourceSansPro-Semibold" size:self.font.pointSize]; 
  6.   self.textColor = [UIColor redColor]; 
  7.   
  8. -(id) initWithFrame:(CGRect)frame { 
  9.   
  10.   if((self = [super initWithFrame:frame])) { 
  11.   
  12.     [self setup]; 
  13.   } 
  14.   
  15.   return self; 
  16. -(id) initWithCoder:(NSCoder *)aDecoder { 
  17.   
  18.   if((self = [super initWithCoder:aDecoder])) { 
  19.   
  20.     [self setup]; 
  21.   } 
  22.   
  23.   return self; 
  24.   
  25. @end 
這個技巧使得開發者可以在 Interface Builder 中自定義這些元素的外觀。在 IB 中拖入一個 UILabel,並且修改它的類爲你自定義的類,瞬間就完成了這個 Label 字體和顏色的自定義,不用任何多餘的代碼。
這個技巧多數情況下相當管用,但是當你的 App 支持自定義主題,且用戶可以通過設置界面更換主題時,就會顯得有些麻煩。
 
-initWithFrame: 和 initWithCoder: 會在 UI 組件創建的時候被調用,所以在這之後如果要改變字體和顏色,就需要很多額外的代碼。因此,如果你的 App 支持主題,寫一個主題管理器的全局單例來提供全局的主題、字體、顏色。
 
如果你用到了我說的第一個方法,你的 UIFont 的 Category 現在可以這樣實現了:
  1. +(UIFont*) appFontOfSize:(CGFloat) pointSize { 
  2.   
  3.   NSString *currentFontName = [[ThemeProvider sharedInstance] currentFontName]; 
  4.   return [UIFont fontWithName:currentFontName size:pointSize]; 
UIColor 同理。其實沒有正確或錯誤的方法,上述方法都是可行的。
 
遵從這裏提到的設計模式,可以讓你的代碼乾淨得像寫的很漂亮的 JS/CSS。試着在你的下一個項目中用這些方法吧。
 
Allen 後記
之前在想 iOS 開發到底是否需要一個類似 Web 開發中的所謂的框架,但漸漸發現其實 iOS SDK 本就是一個高度封裝了的框架了,可能我們需要的不是更更高層的框架,而是一種好的設計模式、開發習慣和代碼結構。因此是不是可以從一個 Project 的層面出發,寫一個乾淨的框架,並且定義一些規範,就是一個很好的“框架”了?而不是非得提供 Router 之類的往 Web 開發框架去靠。

CocoaChina是全球最大的蘋果開發中文社區,官方微信每日定時推送各種精彩的研發教程資源和工具,介紹app推廣營銷經驗,最新企業招聘和外包信息,以及Cocos2d引擎、Cocos Studio開發工具包的最新動態及培訓信息。關注微信可以第一時間瞭解最新產品和服務動態,微信在手,天下我有!

發佈了4 篇原創文章 · 獲贊 1 · 訪問量 5萬+
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章