自定义键盘实现类似微信聊天界面

自从上次重构完项目后,一直在思考客户端的架构问题,总觉得不管是MVC,还是MVVM,VIPER都会有些许问题,最主要是把握一个度做到各个层雨露均沾,说这些好像和今天要记录的东西没什么关系,结构是根据这几天看的架构优化的,接下来就进入正题.只介绍表情键盘和系统键盘的切换部分.
首先自定义一个表情键盘view

//重写初始化方法
-(instancetype)initWithFrame:(CGRect)frame{
    self = [super initWithFrame:frame];
    if (self) {
        [self makeUI];
    }
    return self;
}
//表情键盘页面布局
-(void)makeUI{
    self.userInteractionEnabled = YES;
    UICollectionViewFlowLayout *layout = [[UICollectionViewFlowLayout alloc]init];
    layout.scrollDirection = UICollectionViewScrollDirectionHorizontal;
    layout.minimumLineSpacing = 2;//行间距
    layout.minimumInteritemSpacing = 2;//item间距
    layout.itemSize = CGSizeMake(35, 35);
    layout.sectionInset = UIEdgeInsetsMake(1, 1, 1, 1);
    self.collectionView = [[UICollectionView alloc]initWithFrame:CGRectMake(0, 0, self.frame.size.width, self.frame.size.height) collectionViewLayout:layout];
    _collectionView.delegate = self;
    _collectionView.dataSource = self;
    _collectionView.backgroundColor = [UIColor whiteColor];
    [_collectionView registerClass:[ExpressionCollectionViewCell class] forCellWithReuseIdentifier:@"ExpressionCell"];
    [self addSubview:_collectionView];
}
//代理方法
-(UICollectionViewCell *)collectionView:(UICollectionView *)collectionView cellForItemAtIndexPath:(NSIndexPath *)indexPath{
    ExpressionCollectionViewCell *cell = [collectionView dequeueReusableCellWithReuseIdentifier:@"ExpressionCell" forIndexPath:indexPath];
    if (!cell) {
        cell = [[ExpressionCollectionViewCell alloc]initWithFrame:CGRectMake(0, 0, 35, 35)];
    }
//主要是因为我的图片源命名规则前18张和之后的格式不一样,所以进行区分赋值
    if (indexPath.row<18) {
        cell.imageView.image = [UIImage imageNamed:[NSString stringWithFormat:@"%ld.png",indexPath.row+1]];
    }
    else{
        cell.imageView.image = [UIImage imageNamed:[NSString stringWithFormat:@"0%ld.png",indexPath.row+1]];
    }
    return cell;
}

.h中声明代理方法或block,点击表情进行回传显示

@protocol ExpressionKeyBordViewDelegate 
-(void)didSelectExpression:(UIImage *)image;
@end

typedef void(^didSelectExpression)(UIImage *image);

@interface ExpressionKeyBordView : UIView
//声明代理
@property(nonatomic,weak)iddelegate;
//使用block来回传值
@property(nonatomic,copy)didSelectExpression selecBlock;
@end

//点击表情进行传值
-(void)collectionView:(UICollectionView *)collectionView didSelectItemAtIndexPath:(NSIndexPath *)indexPath{
    ExpressionCollectionViewCell *cell = (ExpressionCollectionViewCell *)[collectionView cellForItemAtIndexPath:indexPath];
    //使用block回传值
    _selecBlock(cell.imageView.image);
    //使用代理进行回传
    [_delegate didSelectExpression:cell.imageView.image];
}

使用自定义键盘时的操作

self.expressionView = [[ExpressionKeyBordView alloc]initWithFrame:CGRectMake(0, 0, self.view.frame.size.width, 200)];
_expressionView.delegate = self;
_expressionView.backgroundColor = [UIColor blackColor];
//注意只是初始化了表情键盘view,并没有把他添加到当前控制器的view上,因为切换键盘时会通过inputView来进行添加
  

点击按钮进行键盘切换

//实现效果点击按钮弹出自定义表情键盘,再点一次变成系统键盘
-(void)expressionBtTouched:(UIButton *)bt{
      if ([_chatBottomView.textView.inputView isEqual:self.expressionView]){
            _chatBottomView.textView.inputView = nil;
            [_chatBottomView.textView reloadInputViews];
        }
        else{
            _chatBottomView.textView.inputView = self.expressionView;
            [_chatBottomView.textView reloadInputViews];
        }
        
        if (![_chatBottomView.textView isFirstResponder]){
            [_chatBottomView.textView becomeFirstResponder];
        }
}

在textView上显示选择的表情

//block
        _expressionView.selecBlock = ^(UIImage *image){
        NSTextAttachment *atacchment = [[NSTextAttachment alloc]init];
        atacchment.image = image;
        //图片在textview中显示的大小
        atacchment.bounds = CGRectMake(0, 0, 20, 20);
        NSAttributedString *attributedStr = [[NSAttributedString alloc]initWithString:@""];
        attributedStr = [NSAttributedString attributedStringWithAttachment:atacchment];
        //textStorage装载内容的容器,继承自NSMutableAttributedString,其里面保存的东西决定了textview的富文本显示方式
        [weakSelf.chatBottomView.textView.textStorage appendAttributedString:attributedStr];
    };
//代理
-(void)didSelectExpression:(UIImage *)image{
    NSTextAttachment *atacchment = [[NSTextAttachment alloc]init];
    atacchment.image = image;
    //图片在textview中显示的大小
    atacchment.bounds = CGRectMake(0, 0, 20, 20);
    NSAttributedString *attributedStr = [[NSAttributedString alloc]initWithString:@""];
    attributedStr = [NSAttributedString attributedStringWithAttachment:atacchment];
    //textStorage装载内容的容器,继承自NSMutableAttributedString,其里面保存的东西决定了textview的富文本显示方式
    [self.chatBottomView.textView.textStorage appendAttributedString:attributedStr];
}

在lable中展示

cell.label.attributedText = textView.attributedText;

效果图如下:

1.png
2.png
3.png
4.png

你可能感兴趣的:(自定义键盘实现类似微信聊天界面)