做者:AppCoda,原文連接,原文日期:2016-09-16
譯者:ckitakishi;校對:mmoaay;定稿:CMBios
CocoaPods 是一個面向 Xcode 的項目依賴管理工具。當須要向項目添加庫和框架時,它是一項極其有用且值得選擇的服務。git
試想一下,有人開發了一個足以改變遊戲規則、且具備劃時代意義的庫,並想把它分享給這個世界。這時候該怎麼辦?長話短說,我要說的是你須要知道如何發佈本身的 CocoaPod!github
本教程基於 Xcode 8 和 Swift 3。若是你想了解更多關於 Swift 3 的新特性,能夠閱讀這篇很棒的教程。json
譯者注:本站譯做swift
目前,CocoaPods 有一個針對 Swift 3 和 Xcode 8 的預發佈版本。爲了編譯基於 Swift 3 的項目,你應該使用這個版本。在終端執行下述命令便可完成安裝:數組
sudo gem install cocoapods --pre
同時你還須要一點 CocoaPods 的使用經驗。不妨看看這篇 Gregg Mojica 寫的使人驚歎的教程,我相信你會從中瞭解更多相關的內容。xcode
好了,咱們開始!app
從如今開始,讓咱們來作一個具備創造性,值得用 pod 管理的項目。個人想法是作一個會緩慢改變顏色的 UIView。我相信對於背景來講這會十分有用。框架
讓咱們先從最基礎的地方開始。首先,在 Xcode 中建立一個新工程,選擇使用 single view 模版。將工程命名爲 FantasticView。項目建立以後,添加一個同名的 Swift 文件 FantasticView.swift
。編輯器
如今你已經有了 FantasticView.swift
,而後在其中定義一個名爲 FantasticView
的類,它繼承自 UIView
:
import UIKit class FantasticView : UIView { }
下一步,爲上面定義的類添加兩個初始化方法:
override init(frame: CGRect) { super.init(frame: frame) // 核心部分 } required init?(coder aDecoder: NSCoder) { super.init(coder: aDecoder) // 你不須要實現這部分 }
第一個初始化方法是 init(frame: CGRect)
。當一個 frame 被傳給 FantasticView
的構造函數時該方法會被調用。咱們將會在這裏調用顏色更改函數。
接下來,定義一個由 UIColor
對象組成的數組 colors
。在咱們的核心代碼中,將會經過「遍歷」這個數組來改變 UIView
的背景顏色。
let colors : [UIColor] = [.red, .orange, .yellow, .green, .blue, .purple]
除此以外,你還須要添加一個計數器對象,在每次顏色改變時計數。
var colorCounter = 0
可是爲何須要一個計數器呢?難道咱們不是在遍歷顏色數組嗎?
注意我剛剛是怎麼說「遍歷」的
如今我要告訴你如何處理遍歷顏色數組的問題。
你可能會認爲在 UIView
的動畫 block 中設置一系列顏色也是一種方法。然而遺憾的是,這沒法正常工做,由於最終將只有一種顏色生效。
還有一種方法是建立一個 for 循環,而後在其中運行一個動畫 block。這也將遇到先前的問題。要解決這個問題,你可使用 GCD 來等待動畫 block 執行完畢。
可是我堅信有更簡單的方法。沒錯,你可使用 NSTimer
!
在你的 init(frame: CGRect)
方法中添加下述代碼:
let scheduledColorChanged = Timer.scheduledTimer(withTimeInterval: 2.0, repeats: true) { (timer) in //1 UIView.animate(withDuration: 2.0) { //2 self.layer.backgroundColor = self.colors[self.colorCounter % 6].cgColor //3 self.colorCounter+=1 //4 } } scheduledColorChanged.fire() //5
讓咱們逐行看一看上面的代碼:
建立一個 Timer
對象,也就是剛纔說的的 NSTimer
。爲定時器設置一個時間間隔,讓它重複執行某些動做。在設置時間間隔以後,咱們的定時器將會運行一個代碼塊。
調用 animate(withDuration)
函數。
設置 UIView.layer.backgroundColor
。注意,並非 UIView.backgroundColor
,由於 layer
屬性可動,而 UIView
屬性不可。
計數器加 1。
銷燬計時器。
讓咱們看看第三步中我具體作了什麼。經過下標能夠從 colors
中取得一個 UIColor
。colorCounter
應該是一個介於 0 到 5 之間的數字,由於這是 colors
數組的界限。我使用 %
或 mod
操做符來求得 colorCounter
除以 6 的餘數。因此若是 colorCounter
是 10,則求餘得 4,因而此時選擇 colors
數組的第四項。
是時候在咱們的主 View Controller 中使用 Fantastic View 了。我但願個人 View Controller 擁有一個酷炫的背景,因此讓咱們在 ViewController.swift
的 viewDidLoad
方法中插入下列代碼:
let fantasticView = FantasticView(frame: self.view.bounds) self.view.addSubview(fantasticView)
這裏咱們定義了一個 FantasticView
,並使其邊框等於 ViewController
的視圖邊界。而後將 fantasticView
做爲子視圖添加到主 view
。
好了,在模擬器中運行應用吧!你將會看到隨着時間推移,背景也隨之改變。
我知道你必定會問:「爲何不將 fantastic view 公佈於衆呢?人們有必要知道它!」
對,沒錯。讓咱們來建立一個 Pod,而後人們就可使用它了!可是在此以前,須要先將其推送到 GitHub。
CocoaPods 要求 Pod 有一個源。大多數狀況下,開發者使用 GitHub 來完成這一切。咱們來快速過一遍提交項目到 GitHub 的必要步驟。若是你想知道更多 Git 的基礎知識,不妨看一看這篇優秀的教程。
簡單來講,下面這些就是你須要作的:
在 Github 上建立一個名爲 FantasticView
的倉庫。
複製倉庫的 URL。
打開終端,跳轉到你的工程目錄下。
初始化 Git:git init
將全部已修改文件添加到 Git 暫存區中:git add .
提交這些已修改文件:git commit -m "init"
添加一個遠程庫 :git remote add origin <paste your URL here>
推送到遠程分支:git push -u origin master
如今你必須爲你的倉庫建立一個 release。一個 release 對應產品的一個新版本。你能夠在 Github 的操做面板上嘗試建立。首先進入你的倉庫。
點擊 releases
按鈕。
點擊 Create a new release
將版本號設置爲 0.1.0
,而後輸入標題和描述。
點擊 Publish release
,而後你看所看到的應該與下圖類似:
以上是關於 Github 的內容,讓咱們開始建立 Pod 自己吧!
首先,咱們須要確保已經安裝 CocoaPods,並作好在終端使用它的準備。動手吧,打開終端,運行如下命令:
sudo gem install cocoapods --pre
如今 CocoaPods 已經安裝完成,下一步輪到建立 Pod 了。
全部 Pods 都擁有一個 podspec 文件。podspec,顧名思義,用於定義 Pod 規範!讓咱們動手建立一個:
打開終端,進入項目根目錄。
運行 touch FantasticView.podspec
命令以建立文件。
使用編輯器打開文件。
將如下代碼粘貼到 Podspec 文件中:
pod Pod::Spec.new do |s| s.name = 'FantasticView' s.version = '0.1.0' s.summary = 'By far the most fantastic view I have seen in my entire life. No joke.' s.description = <<-DESC This fantastic view changes its color gradually makes your app look fantastic! DESC s.homepage = 'https://github.com/<YOUR GITHUB USERNAME>/FantasticView' s.license = { :type => 'MIT', :file => 'LICENSE' } s.author = { '<YOUR NAME HERE>' => '<YOUR EMAIL HERE>' } s.source = { :git => 'https://github.com/<YOUR GITHUB USERNAME>/FantasticView.git', :tag => s.version.to_s } s.ios.deployment_target = '10.0' s.source_files = 'FantasticView/FantasticView.swift' end
s
後面的這些變量都是 CocoaPods 須要的,提供像是名字,版本,概要,描述,倉庫,源代碼文件等必要信息。
下面介紹幾個須要注意的重要變量:
s.name
– 顯而易見,他人使用時能夠經過該名字將 Pod 添加到項目中。
s.version
– 這是你 Pod 的版本。務必注意,它得和 Github release 的版本號相同。若是二者不匹配,就會報錯。
s.summary
和 s.description
– 這兩個變量最終會顯示在 Cocoapods 頁面上。請確保 description
比 summary
更長,不然將會報錯。
s.homepage
– 這是 Pod 源代碼的 URL。注意將 YOUR GITHUB USERNAME
替換爲你的用戶名喲。
s.author
– 開發者信息,注意替換相應內容。
s.source_files
– 這是最重要的參數。它會告訴 CocoaPods 應該克隆哪些文件。我想要個人 FantasticView.swift
被克隆,它的目錄是 FantasticView/FantasticView.swift
。另外,有不少方法能夠添加多個文件做爲源代碼文件。讓咱們來看一個例子:
├── FantasticView.xcodeproj └── FantasticView ├── ViewController.swift ├── Info.plist ├── FantasticView.swift └── FantasticerView.swift
在這個例子中,我但願包含全部 .swift
文件。爲達到目的,我會將 source_files
變量設置爲洗面這樣:
'FantasticView/*.swift'
星號 *
表示包含任意文件。當星號位於文件類型前時,代表包括全部該類型的文件。
假設你想要在 Pod 下載時包含全部位於 /FantasticView
下的文件,只須要將文件名字和類型用星號代替便可:
'FantasticView/*'
這樣就涵蓋了全部,甚至是其餘目錄。爲了限制文件類型,你也可使用以下語句:
'FantasticView/*.{swift,plist}'
在這個例子中,將會涵蓋全部的 swift
和 plist
文件。
CocoaPods 須要驗證項目有沒有錯誤,這包含對錯誤甚至可疑代碼的限制和要求。也就是說在發佈項目以前 CocoaPods 要求你 lint 你的項目。
lint 一個項目十分簡單,可是絕對是難以置信的麻煩!爲了 lint 你的項目,請在項目目錄下執行如下命令:
pod lib lint
你可能會獲得下述警告:
-> FantasticView (0.1.0) - WARN | description: The description is shorter than the summary. - WARN | url: There was a problem validating the URL https://github.com/<YOUR GITHUB USERNAME>/FantasticView.
警告說的很直接。在這個例子中,你應該增長描述內容的長度,並提交一個合法的源代碼 URL。一旦發生錯誤,甚至僅僅只是隻是一個警告,CocoaPods 的 lint 就會失敗。
再來讓咱們看看你可能會遭遇的錯誤:
-> FantasticView (0.1.0) - ERROR | [iOS] xcodebuild: Returned an unsuccessful exit code. You can use --verbose for more information. - ERROR | [iOS] xcodebuild: /Users/sahandedrisian/Desktop/FantasticView/FantasticView/FantasticView.swift:13:32: error: type 'UIColor' has no member 'red' - ERROR | [iOS] xcodebuild: /Users/sahandedrisian/Desktop/FantasticView/FantasticView/FantasticView.swift:20:37: error: use of unresolved identifier 'Timer'
當真的遇到錯誤的時候,不要着急,嘗試通讀錯誤提示並分析爲何發生這個錯誤。在本例中,你會注意到下述信息:
type UIColor has no member red.
可是爲何不能識別 UIColor
,事實上存在一個名爲 red
的成員呀?
一個合理的猜測是,在 Swift 3.0 中 UIColor.redColor()
已經變爲了 UIColor.red
。由此能夠推測 CocoaPods,或者具體說是 xcodebuild 編譯項目使用的是 swift 2.2 或 2.3。第二個錯誤也驗證了咱們的猜測,由於 NSTimer
已經轉換爲了 Timer
。
那麼究竟能夠如何修復這個問題呢?CocoaPods 爲此發佈了一個修正版。在 lint 時你被要求必須指定 Swift 版本。爲了這麼作,你必須得建立一個名爲 .swift-version
的新文件,並添加編譯器版本。只需簡單地輸出如下命令:
echo "3.0" >> .swift-version
如今再次運行 pod lib lint
,你應該可以獲得一條經過驗證的消息:
-> FantasticView (0.1.0) FantasticView passed validation.
Woohoo!你經過了整個流程中最富挑戰的一部分。
注意:若是出現含義不明的錯誤或警告消息,請嘗試鍵入此命令,pod lib lint -verbose,相比常規的 pod lint 命令,你將獲得更詳細的信息。
噢,是時候將你的 Fantastic View 發佈到 CocoaPods 了。每一個開發者都應該擁有一個 CocoaPods 帳戶,以備發佈之時用。
如今的你應該會以爲,CocoaPods 帳號就是一個 CocoaPods 帳號啊,然而並非,它是一個 Trunk 帳號。我並非在評判 CocoaPods,但我以爲這是一個十分奇怪的決定,着實讓我困惑了一段時間。我這麼說了以後,你會不會想讀一下他們所寫的關於爲何作 Trunk 的博文。
確切地說,Trunk 並非一個帳號;是一個會話。因此從根本上來講並不須要密碼的存在,須要的僅僅是一個郵箱。
建立流程很是簡單:
pod trunk register <Your Email>
你應該很快就會受到一封來自 CocoaPods 的郵件以驗證你發起的「會話」。點擊郵件提供的連接,完成你的帳號驗證。以後 CocoaPods 將會給你發來友好的歡迎信息:好棒,設置完成!
到這一步,就只剩下用 Trunk 將你的 podspec 推送到 CocoaPods 了:
pod trunk push FantasticView.podspec
因爲我已經搶先一步使用了 FantasticView
這個超級酷炫的名字,它就再也不可用了。你應該在 podspec 文件中修改 s.name
,同時不要忘記修改你的 podspec 文件的名字。
完成修改以後,像前一節所演示的同樣 lint 你的 podspec,而後再一次推送你的 trunk。若成功推送了你的 Pod,應該會獲得如下信息:
Updating spec repo `master` Validating podspec -> FantasticView (0.1.0) Updating spec repo `master` - Data URL: https://raw.githubusercontent.com/CocoaPods/Specs/06dcdf13dd11b8c2eb4fd522b25a652fa654b180/Specs/FantasticView/0.1.0/FantasticView.podspec.json - Log messages: - September 24th, 11:08: Push for 'FantasticView 0.1.0' initiated. - September 24th, 11:08: Push for 'FantasticView 0.1.0' has been pushed (0.500379641 s).
恭喜!回顧所作的一切,並不是那麼難,對吧?如今能夠將 Pod ‘FantasticView’ 添加到你的 podfile 了。
事實上,有幾種不一樣的方式來推送你的 Pod。你也可使用 CocoaPods 模版來建立 Pod 工程,其中包含示例項目,readme,license 等等。不過我認爲這稍有些複雜了,由於它包含了一些沒必要要的步驟,繁瑣,還容易讓人困惑。
在本教程中,我建立了一個工程,添加了一個 podspec,解釋了 podspec 文件的不一樣選項,建立了一個 trunk 帳號並推送了 Pod。若是遇到了問題,你能夠在 CocoaPods 的 Github 倉庫提交一個 issue。那是一個很是友好的社區,很酷,他們老是會在最短期內給出答覆。
誠摯地但願你喜歡這篇教程!你能夠在這裏下載完整項目做爲參考。
本文由 SwiftGG 翻譯組翻譯,已經得到做者翻譯受權,最新文章請訪問 http://swift.gg。