UI之 09-靜態(tài)單元格\好友列表

靜態(tài)單元格

效果演示:

Snip20160409_2.png

我們看到這個界面之后, 其實我們可以利用我們之前的知識來完成, 但是今天我們講的是利用靜態(tài)單元格完成(這樣就不需要寫任何的代碼)

靜態(tài)單元格的處理環(huán)境就是對于和我們應(yīng)用的服務(wù)器沒有任何關(guān)系的(只有程序更新該界面才會改變的界面)

首先, 按照我們以前的方式: 讓我們的控制器繼承自tableViewController
然后將我們的storyboard中的view換成tableView

Snip20160409_4.png

我們上面的右邊一個小框框上面那個是代表的是動態(tài)的cell就是數(shù)據(jù)可以動態(tài)的

小框框的是靜態(tài)的, 里面的數(shù)據(jù)是死的, 沒有辦法改變的.

然后我們cell的style是Groups

Snip20160409_3.png

這上面的小框框里面表示的是有多少組, 但是首先我們要先寫一個1組, 這樣當(dāng)我們完成了這一個cell之后, 在改成3組時, 他會自動復(fù)制我們之前設(shè)置好的這一組 .

Snip20160409_5.png

這里面的row是每一組cell里面有幾個cell

Snip20160409_6.png

這個框框可以選擇我們cell的類型, 以及下面可以添加圖片

我們只需要將我們的圖片名稱填到里面就可以了

然后, 我們的文字, 只需要我們連續(xù)點擊兩次這個位置:

Snip20160409_7.png

就可以顯示出這種樣式, 這樣我們就可以修改里面的內(nèi)容了. 最后我們再直接將以前的那個多少組, 再改成3組依次就可以了.

好友列表- 01加載數(shù)據(jù)模型

效果演示;

Snip20160409_8.png

我們注意到, 在我們的這個界面中, 一個是好友列表, 一個是好友組列表

所以我們不妨創(chuàng)建兩個模型, 一個是好友信息數(shù)據(jù)模型, 一個是好友組信息數(shù)據(jù)模型

在這加載數(shù)據(jù)模型, 是為了復(fù)習(xí) 我就直接將代碼拿出來了好吧:

FriendGroups.h文件

    #import <Foundation/Foundation.h>
    
    @interface GJFriendGroup : NSObject
    @property (nonatomic, copy) NSString *name;
    /**
     *  數(shù)組中裝的都是GJFriend模型
     */
    @property (nonatomic, strong) NSArray *friends;
    @property (nonatomic, assign) int online;
    
    + (instancetype)groupWithDict:(NSDictionary *)dict;
    - (instancetype)initWithDict:(NSDictionary *)dict;
    @end

FriendGroups.m文件

    #import "GJFriendGroup.h"
    #import "GJFriend.h"
    
    @implementation GJFriendGroup
    + (instancetype)groupWithDict:(NSDictionary *)dict
    {
        return [[self alloc] initWithDict:dict];
    }
    
    - (instancetype)initWithDict:(NSDictionary *)dict
    {
        if (self = [super init]) {
            // 1.注入所有屬性
            [self setValuesForKeysWithDictionary:dict];
            
            // 2.特殊處理friends屬性
            NSMutableArray *friendArray = [NSMutableArray array];
            for (NSDictionary *dict in self.friends) {
                GJFriend *friend = [GJFriend friendWithDict:dict];
                [friendArray addObject:friend];
            }
            self.friends = friendArray;
        }
        return self;
    }
    @end

friend.h文件

    #import <Foundation/Foundation.h>
    
    @interface GJFriend : NSObject
    @property (nonatomic, copy) NSString *name;
    @property (nonatomic, copy) NSString *icon;
    @property (nonatomic, copy) NSString *intro;
    @property (nonatomic, assign, getter = isVip) BOOL vip;
    
    + (instancetype)friendWithDict:(NSDictionary *)dict;
    - (instancetype)initWithDict:(NSDictionary *)dict;
    @end

friend.m文件

    #import "GJFriend.h"
    
    @implementation GJFriend
    + (instancetype)friendWithDict:(NSDictionary *)dict
    {
        return [[self alloc] initWithDict:dict];
    }
    
    - (instancetype)initWithDict:(NSDictionary *)dict
    {
        if (self = [super init]) {
            [self setValuesForKeysWithDictionary:dict];
        }
        return self;
    }
    @end

控制器.m文件

- (NSArray *)groups
{
    if (_groups == nil) {
        NSArray *dictArray = [NSArray arrayWithContentsOfFile:[[NSBundle mainBundle] pathForResource:@"friends.plist" ofType:nil]];
        
        NSMutableArray *groupArray = [NSMutableArray array];
        for (NSDictionary *dict in dictArray) {
            GJFriendGroup *group = [GJFriendGroup groupWithDict:dict];
            [groupArray addObject:group];
        }
        
        _groups = groupArray;
    }
    return _groups;
}

好友列表 - 02顯示好友數(shù)據(jù)

我們首先將所有的數(shù)據(jù)給弄到界面里面去, 然后再考慮其他的, 所以這個又是直接上代碼:

- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView
{
    return self.groups.count;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    GJFriendGroup *group = self.groups[section];
    return group.friends.count;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    // 1.創(chuàng)建cell
    static NSString *ID = @"friend";
    UITableViewCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
    if (cell == nil) {
        cell = [[UITableViewCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:ID];
    }
    
    // 2.設(shè)置cell的數(shù)據(jù)
    GJFriendGroup *group = self.groups[indexPath.section];
    GJFriend *friend = group.friends[indexPath.row];
    cell.imageView.image = [UIImage imageNamed:friend.icon];
    cell.textLabel.text = friend.name;
    cell.detailTextLabel.text = friend.intro;
    return cell;
}

- (NSString *)tableView:(UITableView *)tableView titleForHeaderInSection:(NSInteger)section
{
    GJFriendGroup *group = self.groups[section];
    return group.name;
}
@end

好友列表 -03添加頭部控件

之前我們在做汽車品牌展示的 時候就已經(jīng)知道了, 他有一個頭部的label用來顯示我我們的頭部標(biāo)題的, 現(xiàn)在其實我們的這個頭部不僅僅可以使label同時也可以是UIView當(dāng)然 他的命名可不是這個, 他的命名是: UITableViewHeaderFooterView

觀察上面的效果圖, 我們發(fā)現(xiàn), 如果讓他作為我們每一個好友列表的頭部就需要具備四個控件(UIImage, UILabel, UILablel, UIButton), 當(dāng)然,這種方法是不可取的, 因為 當(dāng)我們點擊我們那個小箭頭的時候, 我們的好友列表也會展開, 所以我們采用的措施是:

用一個大的UIButton覆蓋整個UITableViewHeaderFooterView, 然后再在UIButton上面添加一個UILabel, 這樣我們的UITableViewHeaderFooterView就具備了以上四個控件(UIButton自身還具備了UIImage, UILabel)

下面開始寫:

首先, 我們要有一個繼承自UITableViewHeaderFooterView的類(GJHeaderView)

然后在這個類中設(shè)置我們的UITableViewHeaderFooterView

  1. 寫一個方法, 方便我們的控制器調(diào)用這個方法來創(chuàng)建頭部控件
+ (instancetype)headerViewWithTableView:(UITableView *)tableView;

2 . 在該方法里面設(shè)置我們headerView

其實我們的頭部也是和我們的UIViewCell一樣可以重復(fù)利用的, 所以他在創(chuàng)建的時候, 類似于我們的UIViewCell:

    + (instancetype)headerViewWithTableView:(UITableView *)tableView
    {
        static NSString *ID = @"header";
        GJHeaderView *header = [tableView dequeueReusableHeaderFooterViewWithIdentifier:ID];
        if (header == nil) {
            header = [[GJHeaderView alloc] initWithReuseIdentifier:ID];
        }
        return header;
    }

注意這個方法的調(diào)用: header = [[GJHeaderView alloc] initWithReuseIdentifier:ID]; 我們?nèi)绻朐趧?chuàng)建頭部的時候, 自動為我們添加我們說的幾個子控件 就需要改寫這個方法(直接在這個方法里面創(chuàng)建)

- (id)initWithReuseIdentifier:(NSString *)reuseIdentifier
{
    if (self = [super initWithReuseIdentifier:reuseIdentifier]) {
        // 添加子控件
        // 1.添加按鈕
        UIButton *nameView = [UIButton buttonWithType:UIButtonTypeCustom];
        [self.contentView addSubview:nameView];
        self.nameView = nameView;
        
        // 2.添加好友數(shù)
        UILabel *countView = [[UILabel alloc] init];
        [self.contentView addSubview:countView];
        self.countView = countView;
    }
    return self;
}

大家注意到了吧, 就是我們的控件的創(chuàng)建并沒有設(shè)置我們每一個子控件的frame

原因:

首先, 我們子控件的創(chuàng)建一定需要我們這個HeaderView的frame
其次, 其實由于我們的這個HeaderView在init....方法中, 他一開始初始化時沒有任何值的, 所以當(dāng)我們在這個方法里面設(shè)置我們子控件的frame(需要調(diào)用HeaderView的frame)時 , 是沒有值的, 所以蘋果公司為我們提供了一個方法: - (void)layoutSubviews 而且這個方法是不需要我們自己刻意調(diào)用的而是 **當(dāng)一個控件的frame發(fā)生改變的時候就會調(diào)用. **

所以我們一般是在這個方法中設(shè)置我們子控件的frame:

- (void)layoutSubviews
{
#warning 一定要調(diào)用super的方法
    [super layoutSubviews];
    
    // 1.設(shè)置按鈕的frame
    self.nameView.frame = self.bounds;
    
    // 2.設(shè)置好友數(shù)的frame
    CGFloat countY = 0;
    CGFloat countH = self.frame.size.height;
    CGFloat countW = 150;
    CGFloat countX = self.frame.size.width - 10 - countW;
    self.countView.frame = CGRectMake(countX, countY, countW, countH);
}

而在控制器中我們是這么調(diào)用這個方法來創(chuàng)建headerView的:

- (UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section
{
    // 1.創(chuàng)建頭部控件
    GJHeaderView *header = [GJHeaderView headerViewWithTableView:tableView];
    
    // 2.給header設(shè)置數(shù)據(jù)(給header傳遞模型)
    return header;
}

好友列表 -04設(shè)置頭部數(shù)據(jù)

關(guān)于我們添加頭部控件的數(shù)據(jù) , 其實也是很簡單的, 只是注意的是, 我們的關(guān)于頭部控件的子控件的排放問題

當(dāng)我們直接將我們的子控件添加到我們的頭部控件時, 他會居中擺放, 這樣不是我們想要的結(jié)果, 所以我們就要自己設(shè)置
// 設(shè)置按鈕的內(nèi)容左對齊 nameView.contentHorizontalAlignment = UIControlContentHorizontalAlignmentLeft;

這個方法就是 直接設(shè)置我們每一個子控件都要左對齊, 然后, 我們的控件也不能直接擺放到里面, 最好是有一些空隙 所以這就需要另一個方法:

// 設(shè)置按鈕的內(nèi)邊距
//        nameView.imageEdgeInsets
        nameView.titleEdgeInsets = UIEdgeInsetsMake(0, 10, 0, 0);
        nameView.contentEdgeInsets = UIEdgeInsetsMake(0, 10, 0, 0);

所以這樣我們的上面一個頭部標(biāo)題和箭頭都解決了, 剩下的就是關(guān)于右邊的好友數(shù)了

    - (void)setGroup:(GJFriendGroup *)group
    {
        _group = group;
        
        // 1.設(shè)置按鈕文字(組名)
        [self.nameView setTitle:group.name forState:UIControlStateNormal];
        
        // 2.設(shè)置好友數(shù)(在線數(shù)/總數(shù))
        self.countView.text = [NSString stringWithFormat:@"%d/%d", group.online, group.friends.count];
    }

這樣就完成了我們的頭部數(shù)據(jù)的添加, 具體的代碼如下:

// 添加子控件
        // 1.添加按鈕
        UIButton *nameView = [UIButton buttonWithType:UIButtonTypeCustom];
        // 背景圖片
        [nameView setBackgroundImage:[UIImage imageNamed:@"buddy_header_bg"] forState:UIControlStateNormal];
        [nameView setBackgroundImage:[UIImage imageNamed:@"buddy_header_bg_highlighted"] forState:UIControlStateHighlighted];
        // 設(shè)置按鈕內(nèi)部的左邊箭頭圖片
        [nameView setImage:[UIImage imageNamed:@"buddy_header_arrow"] forState:UIControlStateNormal];
        [nameView setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
        // 設(shè)置按鈕的內(nèi)容左對齊
        nameView.contentHorizontalAlignment = UIControlContentHorizontalAlignmentLeft;
        // 設(shè)置按鈕的內(nèi)邊距
//        nameView.imageEdgeInsets
        nameView.titleEdgeInsets = UIEdgeInsetsMake(0, 10, 0, 0);
        nameView.contentEdgeInsets = UIEdgeInsetsMake(0, 10, 0, 0);
        [self.contentView addSubview:nameView];
        self.nameView = nameView;
        
        // 2.添加好友數(shù)
        UILabel *countView = [[UILabel alloc] init];
        countView.textAlignment = NSTextAlignmentRight;
        countView.textColor = [UIColor grayColor];
        [self.contentView addSubview:countView];
        self.countView = countView;

然而設(shè)置我們的好友數(shù), 就是我們上面的一個方法.

還有一點就是關(guān)于我們的封裝:

在我們的上面的控制器牽扯到一個cell的創(chuàng)建:

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath

其實我們完全可以自定義一個cell來將原先的創(chuàng)建cell的過程封裝起來

該自定義cell的名稱就叫做: friendCell

注意的是, 我們的這個cell是需要我們的friend這個模型數(shù)據(jù)的, 因為我們這個cell在創(chuàng)建的時候需要的數(shù)據(jù)都是從這個模型中取出來的

**friendCell.h文件: **

    #import <UIKit/UIKit.h>
    @class GJFriend;
    
    @interface GJFriendCell : UITableViewCell
    + (instancetype)cellWithTableView:(UITableView *)tableView;
    // friend是C++的關(guān)鍵字,不能用friend作為屬性名
    @property (nonatomic, strong) GJFriend *friendData;
    @end

friendCell.m文件

    #import "GJFriendCell.h"
    #import "GJFriend.h"
    
    @implementation GJFriendCell
    
    + (instancetype)cellWithTableView:(UITableView *)tableView
    {
        static NSString *ID = @"friend";
        GJFriendCell *cell = [tableView dequeueReusableCellWithIdentifier:ID];
        if (cell == nil) {
            cell = [[GJFriendCell alloc] initWithStyle:UITableViewCellStyleSubtitle reuseIdentifier:ID];
        }
        return cell;
    }
    
    - (void)setFriendData:(MJFriend *)friendData
    {
        _friendData = friendData;
        
        self.imageView.image = [UIImage imageNamed:friendData.icon];
        self.textLabel.text = friendData.name;
        self.detailTextLabel.text = friendData.intro;
    }
    @end

這個就是我們封裝的代碼:

好友列表 -05展開合并好友列表

其實, 我們可以換一種思路去想如果讓我們的好友列表合并, 原來模式下, 我們的好友列表是自動展開的, 所以我們在想如何將他合并

其實我們可以這樣做:

當(dāng)我們的好友列表展開時 , 我們就不動 , 一旦需要合并的時候, 我們將我們的friend模型改成0, 然后在重新刷新表格, 這樣就做到我們想要的那個效果

**1. 我們要監(jiān)聽按鈕的點擊: **

[nameView addTarget:self action:@selector(nameViewClick) forControlEvents:UIControlEventTouchUpInside];

這樣當(dāng)我們的按鈕被點擊的時候, 它就會調(diào)用我們的nameViewClick這個方法, 然后我們只需要在這個方法里面完成展開合并好友列表的這個功能

2 . 思考: 如何使我們的列表里面的好友有時候顯示, 有時候不顯示???

很簡單, 我們利用BOOL類型判斷我們的列表是否展開, 如果是YES(表示是展開的)就顯示好友, 如果是NO就在這個方法里面返回一個0, 就代表著, 所有組的好友數(shù)為0:

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section

如何寫: 利用三目運算:

return (group.isOpened ? group.friends.count : 0);

3 . 在我們friendGroup里面添加一個BOOL類型的屬性: (是否要顯示好友列表)

    /**
     *  標(biāo)識這組是否需要展開,  YES : 展開 ,  NO : 關(guān)閉
     */
    @property (nonatomic, assign, getter = isOpened) BOOL opened;

4 . 在headerView的nameViewClick方法中按位取反

意思就是每當(dāng)我們點擊頭部控件的時候, 如果這個isOpened是YES就取反為NO, 這樣就可以完成我們第一次點擊頭部控件, 為展開, 再點一次isOpened變?yōu)镹O了, 就合并, 然后又是展開

// 1.修改組模型的標(biāo)記(狀態(tài)取反)
    self.group.opened = !self.group.isOpened;

**5. 刷新表格: **

對于我們整個的文件來說, 誰最適合刷新表格???當(dāng)然是控制器了, 所以我們當(dāng)我們的按鈕被點擊的時候, 我們要通知我們的控制器, 按鈕被人點了, 所以我們就需要用到** 代理**

先寫好協(xié)議:

    @protocol GJHeaderViewDelegate <NSObject>
    
    @optional
    - (void)headerViewDidClickedNameView:(GJHeaderView *)headerView;
    @end

然后再創(chuàng)一個協(xié)議屬性:

@property (nonatomic, weak) id<MJHeaderViewDelegate> delegate;


- (void)nameViewClick
{
    // 1.修改組模型的標(biāo)記(狀態(tài)取反)
    self.group.opened = !self.group.isOpened;
    
    // 2.刷新表格
    if ([self.delegate respondsToSelector:@selector(headerViewDidClickedNameView:)]) {
        [self.delegate headerViewDidClickedNameView:self];
    }

其次 , 在這個方法中告訴我么你的代理, 按鈕被點擊了, 把自己傳給代理, 告訴代理是自己被人點擊了

最后, 控制器遵守協(xié)議,成為我們頭部控件的代理 然后實現(xiàn)協(xié)議方法:

@interface GJViewController () <GJHeaderViewDelegate>

實現(xiàn)方法:

    #pragma mark - headerView的代理方法
    /**
     *  點擊了headerView上面的名字按鈕時就會調(diào)用
     */
    - (void)headerViewDidClickedNameView:(GJHeaderView *)headerView
    {
        [self.tableView reloadData];
    }

**6 關(guān)于左邊下箭頭的旋轉(zhuǎn) **

當(dāng)我們的列表展開后, 我們的小箭頭應(yīng)該向下旋轉(zhuǎn)90°, 但是,首先提示我們的這個工能是不可以在nameClick這個方法中寫的, 因為, 每當(dāng)我們調(diào)用這個方法時, 我們的表格就會重新刷新一次, 所以就算我們在這里修改, 也無濟于事

所以, 蘋果官方又給我們推薦了一個新的方法, 該方法不需要我們?nèi)フ{(diào)用, 他會在合適的時間自動調(diào)用

    /**
     *  當(dāng)一個控件被添加到父控件中就會調(diào)用
     */
    - (void)didMoveToSuperview
    {
        if (self.group.opened) {
            self.nameView.imageView.transform = CGAffineTransformMakeRotation(M_PI_2);
        } else {
            self.nameView.imageView.transform = CGAffineTransformMakeRotation(0);
        }
    }

注釋寫的就是我們這個方法是在什么時候調(diào)用的

**但是: **

就算我們這樣弄好了, 圖片也可以旋轉(zhuǎn)了, 但是效果不是很好, 圖片會變形, 因為我們的UIImage會自動拉伸, 以及裁剪, 所以我們需要在設(shè)置圖片的代碼里添加這樣兩句代碼:

    // 設(shè)置按鈕內(nèi)部的imageView的內(nèi)容模式為居中
    nameView.imageView.contentMode = UIViewContentModeCenter;
    // 超出邊框的內(nèi)容不需要裁剪
    nameView.imageView.clipsToBounds = NO;

這樣, 我們的這個程序, 就到了最后一步, 設(shè)置顯示會員:

好友列表- 06 標(biāo)識會員

很簡單, 在我們的friendCell里面直接來個三目運算就可以了:

self.textLabel.textColor = friendData.isVip ? [UIColor redColor] : [UIColor blackColor];

APP管理

現(xiàn)在我們又回到我們一開始的那一項, 單元格, 我們刪掉原來的UIView, 重新拖入一個UITableView, 他會自動在上面生成一個單元格(Prototype Cells), 上面我們介紹的是靜態(tài)單元格, 現(xiàn)在我們要利用他做一個動態(tài)的單元格 (需要寫代碼的) 利用動態(tài)單元格做一個以前做過的應(yīng)用管理 :

效果展示:

Snip20160409_9.png

然后, 由于我們系統(tǒng)自帶的Prototype Cells 沒有自帶我們的這種格式,而且, 在系統(tǒng)中原有的格式中 ,我們再添加任何子控件, 所以我們只有選擇, 自定義:

Snip20160409_10.png

其次, 原來的那個數(shù)據(jù)轉(zhuǎn)模型代碼我就不寫了, 直接寫一個appCell

其實, 我們可以將我們的這個動態(tài)單元格看成一個Xib 只是他要比Xib方便的多

對于我們在創(chuàng)建一個新的cell時候 , 我們一般會給cell一個標(biāo)識, 這樣方便我們以后從緩存池中找, 所以, 同樣的我們的動態(tài)單元格, 也有一個標(biāo)識:

Snip20160409_11.png

然后我們在控制器里面創(chuàng)建的代碼就變成這樣了:

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section
{
    return self.apps.count;
}

- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath
{
    GJAppCell *cell = [tableView dequeueReusableCellWithIdentifier:@"app"];
    cell.delegate = self;
    cell.app = self.apps[indexPath.row];
    return cell;
}

對比以前的代碼, 下奶在看看現(xiàn)在的代碼:

GJAppCell *cell = [tableView dequeueReusableCellWithIdentifier:@"app"];

只要這一句代碼就完成了, 以前我們還需要用一個判斷語句來判斷緩存池中是否有cell, 現(xiàn)在不需要了

而且, 可以發(fā)現(xiàn), 一個cell的創(chuàng)建是只需要表示(Identifier), 那么我們完全可以多創(chuàng)建幾個Prototype Cells 只需要寫上不同的標(biāo)識而已, 例如:

Snip20160409_12.png

利用代理, 顯示已下載, 和彈出框框

首先我們設(shè)置代理的方法已經(jīng)說過很多次了, 今天就不說了,

  • 首先, 我們需要得到我們的下載按鈕(同時也要設(shè)置一個參數(shù), 用來告訴他的代理是誰被點擊了) , 利用方法監(jiān)聽他的點擊事件:
- (IBAction)downloadClick:(UIButton *)btn;



    /**
     *  點擊了下載按鈕
     */
    - (IBAction)downloadClick:(UIButton *)btn {
        // 1.讓按鈕失效
        self.app.downloaded = YES;
        btn.enabled = NO;
        
        // 2.通知代理
        if ([self.delegate respondsToSelector:@selector(appCellDidClickedDownloadBtn:)]) {
            [self.delegate appCellDidClickedDownloadBtn:self];
        }
    }
  • 然后讓我們的控制器成為我們的代理

* 遵守協(xié)議: <GJAppCellDelegate>

*實現(xiàn)方法:

    #pragma mark - cell的代理方法
    - (void)appCellDidClickedDownloadBtn:(MJAppCell *)cell
    {
        // 1.添加標(biāo)簽
        UILabel *label = [[UILabel alloc] init];
        label.text = [NSString stringWithFormat:@"成功下載%@", cell.app.name];
        label.font = [UIFont systemFontOfSize:12];
        label.textAlignment = NSTextAlignmentCenter;
        label.textColor = [UIColor whiteColor];
        label.backgroundColor = [UIColor blackColor];
        label.frame = CGRectMake(0, 0, 150, 25);
        label.center = CGPointMake(160, 240);
        label.alpha = 0.0;
        label.layer.cornerRadius = 5;
        label.clipsToBounds = YES;
        [self.view addSubview:label];
        
        // 2.動畫
        [UIView animateWithDuration:0.5 animations:^{
            label.alpha = 0.5;
        } completion:^(BOOL finished) {
            [UIView animateWithDuration:0.5 delay:0.5 options:UIViewAnimationOptionCurveLinear animations:^{
                label.alpha = 0.0;
            } completion:^(BOOL finished) {
                [label removeFromSuperview];
            }];
        }];
    }

但是, 注意的是, 一旦我們讓現(xiàn)在按鈕失效, 在后面的當(dāng)我們的cell從緩存池去的時候, 我們的cell中的下載按鈕還是失效的, 所以我們的解決方法就是在重寫cell的setter方法里面加上這么一句代碼:

// 覆蓋按鈕的狀態(tài)
self.downloadView.enabled = (self.app.isDownloaded == NO);

至于這個應(yīng)用的數(shù)組轉(zhuǎn)模型, 數(shù)據(jù)的加載等等我就不寫了, 和我們以前的代碼一樣的

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末客峭,一起剝皮案震驚了整個濱河市才顿,隨后出現(xiàn)的幾起案子步脓,更是在濱河造成了極大的恐慌前弯,老刑警劉巖,帶你破解...
    沈念sama閱讀 218,941評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件憔古,死亡現(xiàn)場離奇詭異罢坝,居然都是意外死亡鳖擒,警方通過查閱死者的電腦和手機溉浙,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,397評論 3 395
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來蒋荚,“玉大人戳稽,你說我怎么就攤上這事∑谏” “怎么了惊奇?”我有些...
    開封第一講書人閱讀 165,345評論 0 356
  • 文/不壞的土叔 我叫張陵,是天一觀的道長播赁。 經(jīng)常有香客問我颂郎,道長,這世上最難降的妖魔是什么容为? 我笑而不...
    開封第一講書人閱讀 58,851評論 1 295
  • 正文 為了忘掉前任乓序,我火速辦了婚禮,結(jié)果婚禮上坎背,老公的妹妹穿的比我還像新娘替劈。我一直安慰自己,他們只是感情好得滤,可當(dāng)我...
    茶點故事閱讀 67,868評論 6 392
  • 文/花漫 我一把揭開白布陨献。 她就那樣靜靜地躺著,像睡著了一般懂更。 火紅的嫁衣襯著肌膚如雪眨业。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,688評論 1 305
  • 那天沮协,我揣著相機與錄音龄捡,去河邊找鬼。 笑死慷暂,一個胖子當(dāng)著我的面吹牛聘殖,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播呜呐,決...
    沈念sama閱讀 40,414評論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼悍募!你這毒婦竟也來了蘑辑?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,319評論 0 276
  • 序言:老撾萬榮一對情侶失蹤坠宴,失蹤者是張志新(化名)和其女友劉穎洋魂,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,775評論 1 315
  • 正文 獨居荒郊野嶺守林人離奇死亡副砍,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點故事閱讀 37,945評論 3 336
  • 正文 我和宋清朗相戀三年衔肢,在試婚紗的時候發(fā)現(xiàn)自己被綠了。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片豁翎。...
    茶點故事閱讀 40,096評論 1 350
  • 序言:一個原本活蹦亂跳的男人離奇死亡角骤,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出心剥,到底是詐尸還是另有隱情邦尊,我是刑警寧澤,帶...
    沈念sama閱讀 35,789評論 5 346
  • 正文 年R本政府宣布优烧,位于F島的核電站蝉揍,受9級特大地震影響,放射性物質(zhì)發(fā)生泄漏畦娄。R本人自食惡果不足惜又沾,卻給世界環(huán)境...
    茶點故事閱讀 41,437評論 3 331
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望熙卡。 院中可真熱鬧杖刷,春花似錦、人聲如沸再膳。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,993評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽喂柒。三九已至不瓶,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間灾杰,已是汗流浹背蚊丐。 一陣腳步聲響...
    開封第一講書人閱讀 33,107評論 1 271
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留艳吠,地道東北人麦备。 一個月前我還...
    沈念sama閱讀 48,308評論 3 372
  • 正文 我出身青樓,卻偏偏與公主長得像昭娩,于是被迫代替她去往敵國和親凛篙。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點故事閱讀 45,037評論 2 355

推薦閱讀更多精彩內(nèi)容