iOS狂暴之路---iOS的第一個應用中能學到哪些知識

來源:互聯網
上載者:User

標籤:

  一、前文回顧
  
  在之前已經介紹了 iOS的學習路線圖,因為中間遇到一些Android開發問題,所以就耽擱了一段時間,那麼接下來的這段時間我們將繼續開始iOS的狂暴之路學習,按照國際慣例,第一個應用當然是我們的HelloWorld程式了。那麼本文將會通過這麼一個簡單的程式來講解一下iOS中的程式生命週期,應用中關鍵的幾個對象,項目結構,最後在手把手的建立一個空項目。
  
  二、建立簡單程式HelloWorld
  
  下面先用Xcode來建立一個HelloWorld程式:
  
  點擊下一步即可:
  
  這裡和我們在AndroidStudio中建立Android程式非常類似,不多說了,點擊下一步即可:
  
  這樣項目就建立好了,下面我們讓程式運行起來,展示一個HelloWorld文字。這個有兩種方式,在Android中也是類似,我們這裡使用UILabel來進行操作。類似於Android中的TextView控制項,一種方式是代碼寫布局,一種是採用拖的方式類似於Android中的布局檔案。這裡為了方便而且以後會詳細介紹拖的那種方式,直接用代碼進行編寫了。
  
  那麼我們在哪裡編寫代碼呢?這裡的入口是在根控制器ViewController類:
  
  這個入口類似於Android中的Activity的onCreate方法,我們一般都是在這裡初始化一個View,這裡看到代碼邏輯不是很複雜,但是隱含的知識點很多,不過不是本文的重點,比如這裡涉及到了iOS的座標問題,View之間的關係等,這個是在後面章節會詳細介紹View知識點在加以分析。代碼寫完了,運行程式吧,運行也很簡單:
  
  直接點擊左上方的運行按鈕即可,同時可以選擇項目啟動並執行目標裝置。運行結果如下:
  
  這裡看到了,在4s裝置中一個簡單的HelloWorld就展示出來了。好了,下面就要開始我們今天的重要內容了,我們從這個簡單的程式入手能夠學習到哪些知識。
  
  三、程式知識點分析
  
  第一、程式的入口和生命週期
  
  我們在開發Android程式的時候都知道其實一個應用程式的入口並不是MainActivity的onCreate方法也不是Application的onCreate方法,而是ActivityThread的main方法,與之類似,在iOS中一個程式的入口也是main方法,而這個main類在main方法中:
  
  每個程式都有一個main.m這個類,內部有一個main方法,而這個方法我們看到和C語言中的main函數形式是一致的,入口就在這裡,那麼這裡幹了一件事就是託付應用程式的代理對象AppDelegate類,也就是把整個應用程式的邏輯都託付給了AppDelegate類,在iOS中這種方式叫做代理,而在Android中我們通常叫做回調機制,然後UIApplicationMain類就會和AppDelegate類進行互動,比如應用的生命週期,事件處理等,那麼下面就來看一下AppDelegate這個類:
  
  在這個類中我們可以看到很多時機的回調方法,這個就是和應用的生命週期方法相關聯的,下面就來一一分析這些方法的回調時機:
  
  1、告訴代理啟動基本完成程式準備開始運行
  
  - (BOOL)application:(UIApplication *)application www.yghrcp88.cn didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
  
  2、告訴代理進程啟動但還沒進入狀態儲存
  
  - (BOOL)application:(UIApplication *)application willFinishLaunchingWithOptions:(NSDictionary *)launchOptions
  
  3、當應用程式將要入非使用中執行,在此期間,應用程式不接收訊息或事件,比如來電話了
  
  - (void)applicationWillResignActive:www.huacairen88.cn(UIApplication *)application
  
  4、當程式被推送到背景時候調用。所以要設定後台繼續運行,則在這個函數裡面設定即可
  
  - (void)applicationDidEnterBackground:(UIApplication *)application
  
  5、當程式從後台將要重新回到前台時候調用,這個剛好跟上面的那個方法相反
  
  - (void)applicationWillEnterForeground:(UIApplication *)application
  
  6、當應用程式入活動狀態執行,這個剛好跟上面那個方法相反
  
  - (void)applicationDidBecomeActive:(UIApplication *)application
  
  7、當程式將要退出是被調用,通常是用來儲存資料和一些退出前的清理工作
  
  - (void)applicationWillTerminate:www.zhenloyl88.cn(UIApplication *)application
  
  8、當應用接收到記憶體警告回調方法
  
  -(void)applicationDidReceiveMemoryWarning:www.yinbaovip.cn/(UIApplication *)application
  
  看完上面的這些生命週期的回調方法之後,大家可能會想到這個和Android中的Activity非常類似了,而不是Application類了,在Android中比較複雜一般有三個物理按鍵關係Activity的生命週期,而在iOS中只有一個Home鍵,所以這裡的生命週期很好理解的。
  
  第二、應用的視窗
  
  上面就介紹完了iOS程式的生命週期相關的類AppDelegate,下面還需要繼續分析,怎麼關聯上ViewController類的,把HelloWorld展示出來的?
  
  首先我們在程式啟動完成之後的回調方法中列印一個日誌,把當前應用的跟控制器列印出來:
  
  注意:iOS中的列印日誌方法和Android也很類似,使用字串格式化列印即可,一般列印對象的預留位置是%@,而如果想列印一個對象特定值的話,就需要實現這個類的description方法,這個和Java中的toString方法一樣的。這裡在多說幾句,就是一般列印基本類型的格式如下:
  
  %d,%i 整型 (%i的老寫法)
  
  %hd 短整型
  
  %ld,%lld 長整型
  
  %u 無符整型
  
  %f 浮點型和double型
  
  %0.2f 精度浮點數,只保留兩位小數
  
  %x 為32位的無符號整型數(www.zhenlyule.cn/ unsigned int),列印使用數字0-9的十六進位,小寫a-f;
  
  %X 為32位的無符號整型數(unsigned int),列印使用數字0-9的十六進位,大寫A-F;
  
  %o 八進位
  
  %p 指標地址
  
  %s char*類型的字串
  
  %c char字元類型
  
  %C unichar類型
  
  而這些類型列印格式不用背的,用多了就自然記住了,而且這裡用的最多的應該就是%i,%s,%p,%c,%f這幾個。
  
  列印結果如下:
  
  看到了當一個應用啟動了之後,有哪些生命週期的回調方法會執行,同時看到了根控制器就是我們上面添加HelloWorld控制項的入口ViewController類對象。那麼這裡就引出了兩個對象:一個是selfwww.myqunliphoto.com .window對象,一個是window.rootViewController對象。下面先來看看self.window這個對象了,其實這個對象是一個UIWindow類型。和Android一樣,一個程式就對應一個視窗是後續展示View的基礎。
  
  通常一個應用就對應一個UIWindow,就是應用的視窗,但是這話也不能說的太絕對,因為後面不管是Android還是iOS都會出現多屏開發模式,到時候就不止一個Window視窗了。他是後續展示View的基石,如果沒有了這個UIWindow的話,那麼應用所有的UI都展示不出來,其實UIWindow是一個特殊的View,他繼承了UIView類的,也是可以直接添加View控制項的以及你可以像使用View那樣去操作它:
  
  而上面是說到了,一個應用只能有一個UIWindow,但是我們可以定義多個UIWindow,然後設定指定的UIWindow為主視窗,也是可以的。如果想讓哪個視窗成為主視窗並且展示的話,只需要調用makeKeyAndVisible方法即可。
  
  第三、應用的根控制器
  
  上面介紹完了UIWindow知識點,下面在來看一下UIViewController類,在iOS中UIViewController類就相當於Android中的Activity,用於控制View的展示功能,他是一個應用中每個頁面的載體,在Android中一個程式都有一個預設或者是主Activity,在iOS中也是一樣,有一個根控制器,而這個根控制器就是需要設定到應用的唯一視窗中,也就是UIWindow的rootViewController屬性值。關於控制器也有一些生命週期方法,用的最多也是最主要的一個就是View載入完成之後的方法:
  
  - (void)viewDidLoad
  
  這個方法有點類似於Activity的onCreate方法,我們如果想自己添加View的話,就是在這個方法中進行操作的。從上面的那個例子中我們可以看到在這個方法中我們定義了一個UILabel屬性,而每個控制器又有一個非常重要的屬性就是父View,我們自己需要添加的View都可以通過addSubView方法添加即可。
  
  注意:
  
  在iOS中添加View非常簡單和方便,因為任何一個控制項包括上面講到的UIWindow都是繼承UIView類,而這些控制項可以隨便添加其他控制項,沒有任何限制,比如你可以在一個按鈕UIButton中添加一個標籤UILabel完全可以的,但是你要是在Android中就不可以了,Android中如果一個控制項要添加子View,他必須繼承ViewGroup,比如我們常用的幾種布局類,這個看來iOS真的比Android簡單多了。
  
  我們可以看到一個應用程式肯定會包含多個控制器的,因為一般應用都會包含多個頁面,而且每個頁面之間還可以跳轉,在Android中Activity之間的跳轉使用Intent來進行操作的,但是在iOS中沒有這種機制,而是用特定的控制器管理類,一般是用到的導航控制器和選項卡控制器來做管理,具體知識到後面接受控制器在詳細講解。
  
  第四、總結四大對象關係
  
  到這裡,我們就分析完了一個iOS程式中非常重要的四個對象:UIApplicationDelegate,UIWindow,UIViewController,UIView
  
  從這張圖中,可以瞭解到,一個應用程式一定包含了程式應用的代理對象UIAppDelegate類,應用視窗UIWindow類。然後視窗還有一個根控制器頁面UIViewController類,每個控制器都有一個展示UI的父View,根控制器也不例外。最後是每個控制器都會關聯一個父View用於展示每個頁面的UI。
  
  四、建立一個空項目
  
  當我們知道了一個應用的結構以及關鍵對象之後,下面我們就來手把手的建立一個空項目,然後自己去建立這四個關鍵對象。因為Xcode8之後就不在支援建立一個空項目了,為了建立一個空項目,我們可以建立一個項目然後把類都刪了,就變成這樣了:
  
  第一步:建立一個UIViewController根控制器
  
  一定要選擇CocoaTouch Class檔案:
  
  到這裡我們其實就相當於完成了一個簡單的應用程式了,下面就需要在應用的回調方法中設定視窗資訊和根控制器資訊即可:
  
  這時候運行程式可以看到,一片紅色的應用:
  
  從這裡就可以看到,一個應用其實最基本的元素一定有UIApplicationDelegate和UIWindow和根控制器即可,那麼這個其實也是一個簡單的應用了,但是在實際開發中肯定是包含多個控制器的,並且每個根控制器都對應一個View布局檔案,所以下面就開始手把手的建立對應的View資訊。當然這裡可以可以在控制器的回調方法中手動的編碼添加View,但是這裡我們在介紹iOS中其實和Android一樣,每個控制器都有對應的布局檔案,這裡叫做xib檔案。
  
  第二步:建立一個xib檔案
  
  選擇下一步,命名root.xib即可
  
  建立完成之後,可以看到什麼都沒有:
  
  我們就需要一步一步的建立了。
  
  第三步:關聯xib和控制器
  
  然後我們把當前的xib的File‘s Owner設定成我們的根控制器,這裡必須得設定xib的File‘ Owner,不然會報錯的。
  
  所以從這裡可以看到,這裡的xib其實就相當於Android中的布局檔案xml,每個布局檔案都是和一個Activity進行關聯的,而這裡也是一樣的原理,一個xib必須依託一個控制器,所以這裡的File‘s Owner設定對應的控制器即可。
  
  注意:
  
  但是iOS中的xib檔案和Android中的布局檔案又有點差別,這裡xib不僅可以設定視圖布局格式,後面再會介紹一個案例,這裡可以包含一些特殊的對象,後面介紹如何把控制器,視窗等對象都搞到一個xib中,完全不用編寫代碼可以實現一個應用的建立了,而關於xib和Xcode預設建立的stroyboard有什麼區別呢?就可以簡單的理解,stroyboard更好的管理多個控制器和視圖之間的關係,比如現在我想建立一個控制器,那麼就要建立對應的xib檔案了,而一個項目中如果有多個控制器頁面,那麼工程中就會有多個xib檔案,這樣可能會不好管理,而stroyborad就可以把這些檔案都搞到一起管理,但是從其他iOS老鳥中得知,這個其實還是要具體項目和每個人的開發習慣了,並不是強烈要求一定要用stroyborad的。
  
  第四步:在xib中添加父View
  
  上面設定好了xib檔案和控制器的關係,下面還得設定控制器的父View屬性值,首先我們得給這個xib中添加一個View,如果不設定的話,運行程式會報錯的,添加View很簡單,我們在Xcode的最右下角有一個可以選擇各種控制項和對象的介面:
  
  搜尋View控制項,找到之後,直接拖到xib內容中即可。托成功之後,我們還需要把控制器的view屬性關聯到這個View控制項中,不然也是會報錯的。這裡就很簡單了,對於Xcode開發工具來說,只要一拖串連即可。如所示:
  
  注意:
  
  在iOS中有一個很方便的功能,就是給對象賦值以及後面給控制項添加事件,有時候可以選擇拖這種捷徑的,不過得有一個前提,就是這個屬性必須設定IBOutlet特性,設定之後就可以看到屬性前面有一個小圓圈了:
  
  表示會出現在拖的列表中了,然後如果想賦值給這個屬性,就把他拖到指定對象即可,所以中這裡也可以看到iOS中的xib和Android中的布局檔案有點區別。還有一個是IBAction特性,這個主要是添加控制項的事件的,這個一般是添加在一個方法中的,然後這個方法就會出現在拖的列表中,比如我們在控制器中定義一個這個方法:
  
  這裡可以看到也是有一個小圓圈的,下面在回去看xib中的File‘s Owner:
  
  這裡可以看到了,當你去拖doClick方法的右邊加號圓圈到一個UIButton控制項上的時候,會出現這個介面,其中列舉了多個事件,我們可以選中一個之後,就表示這裡的UIButton控制項的這個事件觸發的方法是doClick了。從這個可以看到給View控制項賦值和添加事件的方法還是非常方便的,而在Android中就需要findViewById方法,然後在set一些事件回調了,當然Android中現在有一些開源架構做到了這種類似功能,主要採用註解功能,無序findViewById賦值和添加事件了。不過我不怎麼喜歡使用這個架構,感覺原生最好!
  
  第五步:載入xib檔案
  
  好了,到這裡我們就建立好了一個根控制器以及對應的xib檔案了,那麼下面如果想讓這個控制器展示這個xib內容,還需要做一些工作就是要手動的載入這個xib檔案,上面那個串連操作只是簡單的建立關係,載入還得自己寫代碼,就相當於Android中的setContentView方法效果一下,這裡就需要改一下控制器的初始化方法了:
  
  控制器提供了一個initWithNibName:bundle:方法,這個方法可以顯示的載入一個xib檔案,這裡需要注意兩點就是xib檔案名稱不能攜帶尾碼名,其次就是第二個參數表示xib檔案的路徑,傳入nil表示從項目的根目錄中尋找。
  
  設定了控制器載入xib代碼之後,下面就可以運行程式了:
  
  看到效果之後,發現我們不僅可以在控制器中手動編寫代碼添加View,也可以使用xib檔案來進行頁面配置的。
  
  到這裡我們就手把手的建立了一個簡單項目,在這個過程中我們將更瞭解了程式中的四個重要對象的關係了,下面在來總結一下:
  
  1、UIAppDelegate類
  
  這個類主要是用來管理應用的生命週期和一些事件的回調方法,每個應用都將有一個這個類。
  
  2、UIWindow類
  
  這個類主要是用來展示應用UI介面的視窗,他其實是一個特殊的UIView,可以像操作控制項一樣來操作它,而每個應用都有一個唯一的主視窗,也就是UIAppDelegate類中的window屬性值。
  
  3、UIViewController類
  
  這個類相當於管理應用中每個頁面的功能類,他和Android中的Activity非常類似,而一個應用一般都是會包含多個控制器的,但是一定有一個根控制器,這個控制器一般要設定到UIWindow的rootViewController屬性值中。同時每個控制器如果要用代碼布局,就在viewDidLoaded方法中進行添加,如果要用xib布局檔案來操作,就需要手動的進行載入操作,使用控制器的initWithNibName:bundle:方法。
  
  4、UIView類
  
  其實這個類是iOS中每個控制項的父類,但是每個控制器都有一個父View,這個就是UIView類,一般要設定到UIViewController的view屬性值中的。
  
  五、知識點補充
  
  第一、解析xib檔案
  
  xib檔案的解析過程:
  
  1> 建立好Objects下面的所有對象
  
  2> 建立好Objects下面的所有對象和File‘s Owner的關聯關係
  
  在上面介紹xib中說到了,xib不僅可以添加控制項視圖,也可以添加各種對象的,比如這裡我們可以添加一個UIWindow和UIViewController對象:
  
  看到了吧,一個xib其實可以管理一個簡單的應用程式的所有對象的,然後我們可以這是這些對象的關係就好了。
  
  第二、應用四大對象設定關係和步驟
  
  1> 調用init方法或者initWithNibName:bundle:方法建立控制器
  
  self.viewController = [[RootViewController alloc] init];(建立好控制器之後,並沒有馬上初始化它內部的view)
  
  2> 設定控制器為UIWindow的根控制器
  
  self.window.rootViewController = self.viewController;(設定完根控制器之後並沒有將控制器的view添加到視窗中)
  
  3> 顯示視窗,並且把控制器的view添加到視窗中
  
  [self.window makeKeyAndVisible];
  
  首先調用控制器的loadView進行初始化控制器的view(可以通過xib檔案\可以通過代碼建立)
  
  第三、UIViewController生命週期方法的調用順序
  
  1> view初始化完畢後,就會調用控制器的viewDidLoad方法
  
  2> view初始化完畢後,就會把這個根控制器的view添加到視窗中
  
  3> 當view即將被添加到視窗中時,就會調用控制器的viewWillAppear:方法
  
  4> 當view已經被添加到視窗中時,就會調用控制器的viewDidAppear:方法
  
  5> 如果控制器的view即將從視窗中移除時,就會調用控制器的viewWillDisappear:方法
  
  6> 如果控制器的view已經從視窗中移除時,就會調用控制器的viewDidDisappear:方法
  
  7> 如果控制器接收到記憶體警告的時候,就會調用控制器的didReceiveMemoryWarning方法
  
  didReceiveMemoryWarning方法的預設實現是:如果控制器的view沒有顯示在視窗中,也就是說controller.view.superview為nil時,系統就會銷毀控制器的view.
  
  8> 銷毀完畢後會調用控制器的viewDidUnload方法
  
  9> 如果控制器的view以前因為記憶體警告被銷毀過,現在需要再次存取控制器的view時,會重複前面的步驟初始化view
  
  六、總結
  
  本文介紹的內容有點多,但是是我們開發iOS的入門,也是我們的第一個iOS程式,我們從這個簡單的程式中可以瞭解到了一個程式涉及到的生命週期以及幾個重要對象,他們之間的關聯關係等。同時也瞭解了iOS中的介面布局功能和兩種方法。後面講繼續介紹iOS中的控制器的內容。

iOS狂暴之路---iOS的第一個應用中能學到哪些知識

聯繫我們

該頁面正文內容均來源於網絡整理,並不代表阿里雲官方的觀點,該頁面所提到的產品和服務也與阿里云無關,如果該頁面內容對您造成了困擾,歡迎寫郵件給我們,收到郵件我們將在5個工作日內處理。

如果您發現本社區中有涉嫌抄襲的內容,歡迎發送郵件至: info-contact@alibabacloud.com 進行舉報並提供相關證據,工作人員會在 5 個工作天內聯絡您,一經查實,本站將立刻刪除涉嫌侵權內容。

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.