購物車01-搭建基本骨架
購物車02-圓角按鈕處理
購物車03-顯示數據
是什么?
- 點擊 ? /? 按鈕, 數量會相應的更改。
思路:
-
點擊 ? 按鈕,直接修改控件的顯示,有什么不妥的地方?
- 會引發 Cell循環利用的問題
-
為什么通過模型修改控件的顯示,點擊? 按鈕'購買數量'開始沒有改變,需要滑出屏幕后,再次滑入屏幕,'購買數量'才會改變 ?
如下圖: Cell - 德拉克 連續點擊7次? ,沒有反應。滑出再滑入才顯示購買數量。
代碼如下:
- 問題關鍵, 就是沒有"強制刷新",那怎么強制刷新呢?
- 代碼是寫在自定義cell里面,不是在VC里面。所以不能用
[self.tableView reloadData]; // 全局刷新
// 局部刷新
[self.tableView reloadRowsAtIndexPaths: withRowAnimation:];
-
強制刷新的本質,就是重新調用一遍
setWine
,所以我在點擊? 按鈕時,手動調用一遍,其實就等于強制刷新。-
[self setWine:_wine];
?? -
self.wine = self.wine;
?? // 挺有意思, 1 = 1是這樣嗎?
其實不是, 等號左邊是set方法, 等號右邊是get方法。
所以是, "set方法 = get方法" - 因為僅僅是需要刷新一個"購買數量",所以以上2種方法都很消耗性能, 它們都是刷新整個模型。(直接賦值一遍"購買數量"即可)
- (IBAction)plusClick:(id)sender { self.wine.count ++; //[self setWine:_wine]; //self.wine = self.wine; self.countLabel.text = [NSString stringWithFormat:@"%d",self.wine.count]; }
-
- 代碼是寫在自定義cell里面,不是在VC里面。所以不能用
-
在哪些情況下,需要更改? / ? 的狀態 ?
- 當數量為 0 時,? 按鈕不能點擊。
- 點擊 ? 按鈕后, ? 按鈕則可以點擊。
- 需注意'Cell循環利用'的問題。
第一個Cell "德國...." 的? 按鈕變成灰色。
第N個Cell "人頭馬" 的? 按鈕也變成了灰色, 說明"人頭馬"Cell是引用了"德國..."Cell。
- 代碼如下:
- (IBAction)minusClick:(id)sender { self.wine.count --; self.countLabel.text = [NSString stringWithFormat:@"%d",self.wine.count]; if(self.wine.count <= 0){ self.minusButton.enabled = NO; } }
- 為避免"Cell循環引用"需要在
setWine
方法里面,加上設置? 按鈕狀態的代碼。( OC 語法: 非0則為YES )
當wine.count
為 0 時,minusButton.enabled = NO
-(void)setWine:(Wine *)wine{ self.minusButton.enabled = wine.count; }
? 的處理 (只是一些思路,不推薦實際使用)
需求
- 點擊? 按鈕, "總價"能夠發生對應的改變 ?
- "總價"在VC里, ? 按鈕在Cell里面。
- 點擊? 按鈕,在VC里面的"總價"怎么知道呢?
解決方案
-
暴力破解 (不推薦)
- 通過Automatic,得知當前
總價Label
僅僅只能在VC里訪問. - 假設,在Cell類里面把VC設置為屬性
@class ViewController; @interface WineCell : UITableViewCell @property (nonatomic, strong) ViewController *vcTemp; @end
- 并且,在VC類里告訴
Cell里面的VC屬性
,它關聯的是當前VC。
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{ .... WineCell *cell = [tableView dequeueReusableCellWithIdentifier:ID]; cell.vcTemp = self; .... }
- 那么就可以在Cell里面訪問VC了,但這樣有幾點不好?
- Cell和VC之間太緊密了,不利于后期擴展。
- Cell依賴于VC-A,但如果需要使用其他VC時,用不了。
- 這種設計,違背了MVC / MVVM設計思想。
- 通過Automatic,得知當前
-
更改"監聽事件的位置"(不推薦)
- 將在自定義Cell里面的? 點擊事件,放在VC里面
這樣,總價Label
在VC里, ? 按鈕點擊事件,也在VC里面
所以,可以實現點擊? ,更改總價Label
- 現在只需要在? 按鈕點擊事件里面,獲取到
自定義Cell
, 就能實現,根據'購買數量 * 單價',得到對應的 總價 - 怎么獲取
自定義Cell
?-
sender
傳遞的是當前的按鈕. - 根據設計的UI結構,可以看出
sender.superview
是UITableViewCellContentView
sender.superview.superview
是WineCell
,
所以就得到了自定義的Cell
-
- 代碼如下:
- (IBAction)plusClick:(UIButton *)sender { NSLog(@"grandfather:%@",sender.superview.superview); WineCell * wineTemp = (WineCell*)sender.superview.superview; wineTemp.wine.count ++; int money = [wineTemp.wine.money intValue]; int num = wineTemp.wine.count; self.totalLabel.text = [NSString stringWithFormat:@"%d",money*num]; [self.tableView reloadData]; // 全局刷新 }
- 缺陷:
- 太依賴于,層次結構了! 如果在UI界面,再次"添加 / 減少 View"
那么sender.superview.superview
得到的就不是自定義Cell
- 太依賴于,層次結構了! 如果在UI界面,再次"添加 / 減少 View"
- 將在自定義Cell里面的? 點擊事件,放在VC里面