iOS tableviewcell裡點選文字展開與收起功能

明似水發表於2020-10-11

做專案遇到動態列表中需要做文字展開與收起功能,有空單獨抽出一個demo給大家參考。
1、效果圖如下:
在這裡插入圖片描述
在這裡插入圖片描述

2、建立tableview與新增資料

- (void)viewDidLoad {
    [super viewDidLoad];
    self.view.backgroundColor = [UIColor whiteColor];
    self.title = @"在tablecell中文字的展開與收起";
    self.allData = [NSMutableArray array];
    //新增子檢視
    [self addSubViewUI];
    //請求資料
    [self requestMessageListData];
    //增加重新整理
    [self addRefresh];
}

模擬請求資料

#pragma mark ==========請求資料==========
-(void)requestMessageListData{
    NSArray *arr = @[ ];
    for (int i = 0; i<10; i++) {
        HBTextChangeModel *model = [HBTextChangeModel new];
        model.content = arr[arc4random_uniform(10)];
        [self.allData addObject:model];
    }
    [self endRefresh];
    [self.tableView reloadData];
}

設定上拉載入,下拉重新整理

- (void)endRefresh{
    if (self.tableView.mj_header.refreshing) {
        [self.tableView.mj_header endRefreshing];
    }
    if (self.tableView.mj_footer.refreshing) {
        [self.tableView.mj_footer endRefreshing];
    }
}
- (void)addRefresh{
    WEAKSELF;
    self.tableView.mj_header = [MJRefreshNormalHeader headerWithRefreshingBlock:^{
        //請求資料
       // weakSelf.pageNo = 1;
        [weakSelf.allData removeAllObjects];
        [weakSelf requestMessageListData];
    }];
    self.tableView.mj_footer = [MJRefreshBackNormalFooter footerWithRefreshingBlock:^{
        //請求資料
        //weakSelf.pageNo++;
        [weakSelf requestMessageListData];
    }];
}

新增子檢視

#pragma mark ==========新增子檢視==========
-(void)addSubViewUI{
    [self.view addSubview:self.backBtn];
    [self.backBtn mas_makeConstraints:^(MASConstraintMaker *make) {
        make.top.equalTo(self.view).offset(20);
        make.left.equalTo(self.view).offset(15);
        make.size.mas_equalTo(CGSizeMake(100, 25));
    }];
    
    [self.view addSubview:self.tableView];
    [self.tableView mas_makeConstraints:^(MASConstraintMaker *make) {
        make.top.equalTo(self.backBtn.mas_bottom);
        make.bottom.equalTo(self.view);
        make.left.right.equalTo(self.view);
    }];
}
#pragma mark ==========tableViewDelegate==========
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView{
    return self.allData.count;
}

- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
    return 1;
}

#pragma mark ==========tableview代理方法==========
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
    HBTextChangeTabCell *cell = [tableView dequeueReusableCellWithIdentifier:@"HBTextChangeTabCell"];
    if (cell == nil) {
        cell = [[HBTextChangeTabCell alloc]initWithStyle:UITableViewCellStyleDefault reuseIdentifier:@"HBTextChangeTabCell"];
    }
    cell.selectionStyle = UITableViewCellSelectionStyleNone;
    cell.backgroundColor = [UIColor clearColor];
    HBTextChangeModel *model = self.allData[indexPath.section];
    cell.model = model;
    WEAKSELF;
    cell.updateMessageCellBlock = ^(NSString * _Nonnull str) {
        [weakSelf.tableView reloadRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationAutomatic];
    };
    [cell layoutIfNeeded];
    return cell;
}
- (CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath{
    return UITableViewAutomaticDimension;
}

- (CGFloat)tableView:(UITableView *)tableView heightForHeaderInSection:(NSInteger)section {
    return 15;
}
-(UIView *)tableView:(UITableView *)tableView viewForHeaderInSection:(NSInteger)section{
    //全部商品
    UIView *headerView = [[UIView alloc]initWithFrame:CGRectMake(0, 0, SCREEN_WIDTH, 15)];
    headerView.backgroundColor = [UIColor grayColor];
    return headerView;
}
- (CGFloat)tableView:(UITableView *)tableView heightForFooterInSection:(NSInteger)section {
    return 0.01;
}
-(UIView *)tableView:(UITableView *)tableView viewForFooterInSection:(NSInteger)section{
    //全部商品
    UIView *footerView = [[UIView alloc]initWithFrame:CGRectMake(0, 0, SCREEN_WIDTH, 0.01)];
    footerView.backgroundColor = [UIColor clearColor];
    return footerView;
}


-(void)tableView:(UITableView *)tableView didSelectRowAtIndexPath:(NSIndexPath *)indexPath{
 
}

#pragma mark ==========tableViewGetter==========
-(UITableView *)tableView{
    if (!_tableView) {
        _tableView = ({
            UITableView *tableView = [[UITableView alloc]initWithFrame:CGRectZero style:UITableViewStylePlain];
            tableView.dataSource = self;
            tableView.delegate = self;
            tableView.backgroundColor = [UIColor clearColor];
            //設定分割線樣式
            tableView.separatorStyle = UITableViewCellSeparatorStyleSingleLine;
            //cell的分割線距檢視距離
            tableView.separatorInset=UIEdgeInsetsMake(0, 0, 0, 0);
            //隱藏底部多餘分割線
            tableView.tableFooterView = [[UIView alloc] initWithFrame:CGRectZero];
            //iOS11預設開啟Self-Sizing,需關閉才能設定Header,Footer高度
            tableView.estimatedRowHeight = 66;
            tableView.estimatedSectionHeaderHeight = 0;
            tableView.estimatedSectionFooterHeight = 0;
            tableView.rowHeight = 50 ;
            tableView.tableHeaderView = [[UIView alloc] initWithFrame:CGRectZero];;
            tableView ;
        }) ;
    }
    return _tableView;
}
-(UIButton *)backBtn{
    if (!_backBtn) {
        _backBtn = ({
            //建立按鈕
            UIButton * button = [UIButton buttonWithType:UIButtonTypeCustom];
            //設定標題
            [button setTitle:@"返回" forState:UIControlStateNormal];
            //設定字型大小
            button.titleLabel.font = [UIFont systemFontOfSize:14];
            //設定title顏色
            [button setTitleColor:[UIColor blackColor] forState:UIControlStateNormal];
            //新增點選事件
            [button addTarget:self action:@selector(clickBackButton:) forControlEvents:UIControlEventTouchUpInside];
            
            button;
        });
    }
    return _backBtn;
}
#pragma mark ==========點選返回==========
-(void)clickBackButton:(UIButton *)button{
    [self dismissViewControllerAnimated:YES completion:nil];
}

3、cell中的核心程式碼:

-(void)setModel:(HBTextChangeModel *)model{
    _model = model;
    NSString *desc = model.content;
    if (desc) {
        //計算文字高度
        CGFloat height = [desc heightWithStrAttri:@{NSFontAttributeName:FONT(15), NSForegroundColorAttributeName: Color_label_DataTitle,NSParagraphStyleAttributeName:[self paragraphStyle]} withLabelWidth:SCREEN_WIDTH];
        if (height > 67) { //超過3行
            if (model.showAll) {
                //拼接再算高度
                height = [[NSString stringWithFormat:@"%@...收起",desc] heightWithStrAttri:@{NSFontAttributeName:FONT(15), NSForegroundColorAttributeName: Color_label_DataTitle,NSParagraphStyleAttributeName:[self paragraphStyle]} withLabelWidth:SCREEN_WIDTH];
                
                [self.contentBaseView mas_updateConstraints:^(MASConstraintMaker *make) {
                    make.height.mas_equalTo(height+5);
                }];
                self.contentLabel.truncationToken = nil;
                [self setShowTextWithDesc:desc];
            } else {
                
                [self.contentBaseView mas_updateConstraints:^(MASConstraintMaker *make) {
                    make.height.mas_equalTo(67);
                }];
                [self setAdjustableTextWithDesc:desc];
            }
        } else {
            [self.contentBaseView mas_updateConstraints:^(MASConstraintMaker *make) {
                make.height.mas_equalTo(height+10);
            }];
            NSMutableAttributedString *text = [[NSMutableAttributedString alloc] initWithString:desc attributes:@{ NSFontAttributeName:FONT(15), NSParagraphStyleAttributeName : [self paragraphStyle]}];
            self.contentLabel.attributedText = text;
        }
    }
}
- (void)setShowTextWithDesc:(NSString *)desc
{
    NSMutableAttributedString *text = [[NSMutableAttributedString alloc] initWithString:[NSString stringWithFormat:@"%@...收起",desc] attributes:@{ NSFontAttributeName:FONT(15), NSParagraphStyleAttributeName : [self paragraphStyle]}];
    
    WEAKSELF;
    //設定高亮色和點選事件
    [text setTextHighlightRange:[[text string] rangeOfString:@"收起"] color:[UIColor colorWithHexString:@"#0099FF"] backgroundColor:[UIColor clearColor] tapAction:^(UIView * _Nonnull containerView, NSAttributedString * _Nonnull text, NSRange range, CGRect rect) {
        weakSelf.model.showAll = NO;
        if (self.updateMessageCellBlock) {
            self.updateMessageCellBlock(@"");
        }

    }];
    self.contentLabel.attributedText = text;
}

- (NSMutableParagraphStyle *)paragraphStyle {
    NSMutableParagraphStyle *para = [NSMutableParagraphStyle new];
    para.lineSpacing = 5.f;
    return para;
}

- (void)setAdjustableTextWithDesc:(NSString *)desc
{
    NSMutableAttributedString *text = [[NSMutableAttributedString alloc] initWithString:desc attributes:@{ NSFontAttributeName:FONT(15), NSParagraphStyleAttributeName : [self paragraphStyle]}];
    self.contentLabel.attributedText = text;
    
    WEAKSELF;
    NSMutableAttributedString *showAll = [[NSMutableAttributedString alloc] initWithString:@"...展開" attributes:nil];
    YYTextHighlight *hi = [YYTextHighlight new];
    [hi setColor:[UIColor colorWithHexString:@"#009900"]];
    hi.tapAction = ^(UIView *containerView,NSAttributedString *text,NSRange range, CGRect rect) {
        weakSelf.model.showAll = YES;
        if (self.updateMessageCellBlock) {
            self.updateMessageCellBlock(@"");
        }
    };
    
    NSRange range = [showAll.string rangeOfString:@"展開"];
    [showAll setColor:[UIColor colorWithHexString:@"#0099FF"] range:range];
    [showAll setTextHighlight:hi range:range];
    showAll.font = FONT(15);
    YYLabel *seeMore = [YYLabel new];
    seeMore.attributedText = showAll;
    [seeMore sizeToFit];
    seeMore.height += 2.f;
    NSAttributedString *truncationToken = [NSAttributedString attachmentStringWithContent:seeMore contentMode:UIViewContentModeCenter attachmentSize:seeMore.frame.size alignToFont:FONT(15) alignment:YYTextVerticalAlignmentTop];
    self.contentLabel.truncationToken = truncationToken;
}

最後附上demo連線

END.

相關文章