實作一個可拖曳評分的 rating control

Tay’s Log
5 min readOct 3, 2017

--

最近工作上需要用到ratingBar 但是iOS不像Android 已經有內建的ratingBar control可以使用,所以自己建了一個,主要是參考apple官方的這篇文章,

然後改善了一些靈活性,讓更多的rating control屬性可以在design interface上去做設定,還有新增讓使用者按著拖曳評分的功能。

新增一個Cocoa Touch Class

這裡override init(frame:)跟實作init(coder:)

init(frame:) 是在程式碼創建時,會去執行setupButtons()

因為我們override init(frame:) 自動喪失繼承所有init的特性,必須在實作super class 標記成required的init也就是init(coder:)

init(coder:) 是在storyboard創建時,會去執行setupButtons()

setupButtons()是我們等下要設定button也就是在畫面上星星的function

拉一個Horizontal Stack View到StoryBoard上,設定class為我們剛剛創建的RatingControl

接下來宣告Properties

ratingButtons是用來儲存待會會用到的星星Button

rating是給使用者輸入一開始評分的起始值,之後也可以藉由這個屬性取得目前評分值

fillImage、halfImage、emptyImage是全顆星、半顆星、空星星的圖片設定屬性

starSize 是設定我們星星Size

starCount是設定我們星星的數量

以上的屬性都是@IBInspectable,在每個Properties設定didSet去執行setupButtons()使得我們在design interface上做設定時,能得到畫面上立即的反應,增加靈活度,可視性

接著新增一個setupButtons() Method

setupButtons方法主要是把Button加入到我們剛剛的View中

10行是根據starCount這個屬性去生成幾個button

12,13行是限制button的寬高,使用到starSize這個屬性

15~22行是根據rating這個屬性去判斷輸入的Star起始值

25行是因為待會要做讓使用者能TouchMove以拖曳的方式設定分數,所以要把button的isUserInteractionEnabled設為false,如果不設為false,使用者點到button進行拖曳時會無法觸發TouchMove 的事件。

接下來要做當使用者按著RatingBar 時左右滑動rating也會跟著做動

先override兩個方法touchesBegan 和 touchesMoved

在這兩個方法中我們主要會去取得到使用者按下和按下不放時的(x,y)座標然後去執行updateButtonSelectionStates這個方法去更新畫面

這個方法主要是根據我們剛剛在TouchMove and TouchBegan抓到的point去做畫面上圖片的更新

2行是取得我們設定的button寬度一半的size,因為我們要做半顆星判斷

3~13 行我們每個button去判斷在TouchMove and TouchBegan取到的point座標去判斷目前滑到的分數,存入ratingTemp中,在指定給rating觸發didset 的setButtons。

最後宣告一個public 方法getRating去取得分數

到這就完成,我們看一下storyBoard上的畫面

Rating Control那欄可以設定rating你的起始分數,fill Image 、half Image、empty Image跟星星的大小還有數量,Stack View的spacing可以調整星星之間的距離。

最後給點小提示,因為有宣告IBInspectable 的property,使得Xcode會一直去rebuild相當煩人,可以在這裡去關掉他Automatically Refresh Views 他就不會一直rebuild了。

sample:

https://github.com/Wei789/iOSComponent.git

--

--

Tay’s Log
Tay’s Log

Written by Tay’s Log

這個Blog是為了讓有一顆金魚腦的宅宅工程師,用來記錄用的。

No responses yet