//
// ViewController.m
// UIbiaoqingjianpan
//
// Created by 张艳雪 on 15/12/28.
// Copyright (c) 2015年 张艳雪. All rights reserved.
//
#import "ViewController.h"
#import "MyChatText.h"
#import "MyChatCell.h"
#define SCREEN_WIDTH self.view.frame.size.width
#define SCREEN_HEIGHT self.view.frame.size.height
//屏幕的宽高
@interface ViewController ()
@property (nonatomic,strong)UIScrollView *scrollView;
//表情键盘
/**
* 表情键盘和键盘分页视图
*/
@property (nonatomic,strong)UIView *keyView;
//@property (nonatomic,strong)UITextField *textField;
@property (nonatomic,strong)UITextView *textView;
//输入框
@property (nonatomic,strong)UIButton *btn;
//发送按钮
/**
* 表情按钮
*/
@property (nonatomic,strong)UIButton *imageBtn;
/**
* 集合体View
*/
@property (nonatomic,strong)UIView *titleView;
/**
* 表情分页控制器
*/
@property (nonatomic,strong)UIPageControl *pageControl;
/**
* 聊天窗口
*/
@property (nonatomic,strong)UITableView *tableView;
/**
* 聊天数据源
*/
@property (nonatomic,strong)NSMutableArray *dataArray;
///**
// * 记录聊天数据
// */
//@property (nonatomic,strong)NSMutableAttributedString *attString;
/**
* 聊天视图
*/
@property (nonatomic,strong)UIView *chatView;
/**
* add提示
*/
@property (nonatomic,strong) UIAlertView *alertView;
@end
@implementation ViewController
- (void)viewDidLoad {
[super viewDidLoad];
_dataArray = [[NSMutableArray alloc] init];
//-----------------------------集合体titleView此视图上面包括输入框和发送表情键盘调出按钮
_titleView = [[UIView alloc] initWithFrame:CGRectMake(0, SCREEN_HEIGHT - 78, SCREEN_WIDTH, 78)];
_titleView.backgroundColor = [UIColor colorWithRed:230/255.f green:236/255.f blue:232/255.f alpha:1];
[self.view addSubview:_titleView];
// -----------------------键盘出现消失的通知-------------------
//(1)键盘即将显示的通知
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyBoardWillShow:) name:UIKeyboardWillShowNotification object:nil];
//(2)键盘即将隐藏的通知
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(keyBoardWillHide:) name:UIKeyboardWillHideNotification object:nil];
// ------------------------创建表情键盘调用按钮和发送按钮---------------------
[self createView];
// ---------------------控件textView--------------height = 35
[self createTextView];
//调用方法创建scrollView
[self createScrollView];
//调用tableView聊天框
[self createTableView];
//调用额外功能的按钮 height = 43
[self createAdd];
}
#pragma mark ----------第一部分 界面布置-----------------------------------------
- (void)createView{
// ------------------------创建表情按钮---------------------
_imageBtn = [[UIButton alloc] initWithFrame:CGRectMake(13, 0, 35, 35)];
_imageBtn.layer.cornerRadius = 15;
[_imageBtn setBackgroundImage:[UIImage imageNamed:@"icon_05.png"] forState:UIControlStateNormal];
_imageBtn.tintColor = [UIColor blackColor];
[_imageBtn addTarget:self action:@selector(btnImageClick:) forControlEvents:UIControlEventTouchUpInside];
[_titleView addSubview:_imageBtn];
// ==========-===================
//创建发送按钮
_btn = [[UIButton alloc] initWithFrame:CGRectMake(SCREEN_WIDTH - 70, 0, 60, 35)];
[_btn setTitle:@"发送" forState:UIControlStateNormal];
_btn.layer.cornerRadius = 5;
[_btn setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
_btn.backgroundColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:0.2];
[_btn addTarget:self action:@selector(sendBtn:) forControlEvents:UIControlEventTouchUpInside];
[_titleView addSubview:_btn];
}
#pragma mark ------ 创建textView
- (void)createTextView{
//创建textfield
_textView = [[UITextView alloc] initWithFrame:CGRectMake(55, 0, SCREEN_WIDTH - 140, 35)];
// _textField.backgroundColor = [UIColor yellowColor];
_textView.font = [UIFont systemFontOfSize:30];
_textView.layer.borderColor=[UIColor lightGrayColor].CGColor;
_textView.layer.borderWidth =1.0;
_textView.layer.cornerRadius =5.0;
//设置代理 使_btn变色
_textView.delegate = self;
[_titleView addSubview:_textView];
}
#pragma mark --------- 创建scrollView(表情键盘)
- (void)createScrollView{
_keyView = [[UIView alloc] initWithFrame:CGRectMake(0, SCREEN_HEIGHT, SCREEN_WIDTH, 200)];
[self.view addSubview:_keyView];
// ------------------------表情键盘 ---------------------------
//1,创建scrollView
_scrollView = [[UIScrollView alloc] initWithFrame:CGRectMake(0, 0, SCREEN_WIDTH, 200)];
//2,创建viewA
//表情的顺序(序号)
NSInteger count = 1;
UIView *viewA = [[UIView alloc] initWithFrame:CGRectMake(0, 0, SCREEN_WIDTH * 3, 200)];
for (int m = 0; m < 4; m++) {
//每一页的表情
UIView *viewB = [[UIView alloc] initWithFrame:CGRectMake(10 + SCREEN_WIDTH * m, 0, SCREEN_WIDTH, 200)];
for (int i = 0; i < 3; i++) {
for (int j = 0; j < 7; j++) {
UIButton *btn = [[UIButton alloc] initWithFrame:CGRectMake(SCREEN_WIDTH/7 * j, 50 * i, SCREEN_WIDTH/10, SCREEN_WIDTH/10)];
btn.layer.cornerRadius = SCREEN_WIDTH/10;
if (i == 2&&j == 6) {//删除按钮
//删除按钮的点击事件
[btn addTarget:self action:@selector(deleteBtn:) forControlEvents:UIControlEventTouchUpInside];
[btn setBackgroundImage:[UIImage imageNamed:@"DeleteEmoticonBtn_ios7.png"] forState:UIControlStateNormal];
[viewB addSubview:btn];
break;
}else{
//表情按钮添加事件
[btn addTarget:self action:@selector(btnClick:) forControlEvents:UIControlEventTouchUpInside];
[btn setBackgroundImage:[UIImage imageNamed:[NSString stringWithFormat:@"[Expression_%lu].png",count]] forState:UIControlStateNormal];
[viewB addSubview:btn];
count++;
}
}
}
[viewA addSubview:viewB];
}
//隐藏滑动条
_scrollView.showsHorizontalScrollIndicator = NO;
_scrollView.showsVerticalScrollIndicator = NO;
//开启翻页模式
_scrollView.pagingEnabled = YES;
[_scrollView addSubview:viewA];
[self createPageControll];
[_keyView addSubview:_scrollView];
//设置scrollView可以滚动的范围
_scrollView.contentSize = CGSizeMake(SCREEN_WIDTH * 3, 200);
//关闭弹簧效果
_scrollView.bounces = NO;
//设置代理用于改变page
_scrollView.delegate = self;
}
#pragma mark ------- create pageControll(用于表情)
- (void)createPageControll{
//1,创建
_pageControl = [[UIPageControl alloc] initWithFrame:CGRectMake(0, 150, SCREEN_WIDTH, 30)];
//2,设置点数
_pageControl.numberOfPages = 3;
//3,设置背景颜色
_pageControl.backgroundColor = [UIColor clearColor];
//4,选中某个点时候的颜色
_pageControl.currentPageIndicatorTintColor = [UIColor blackColor];
//5,设置页码指示器的颜色
_pageControl.pageIndicatorTintColor = [UIColor colorWithRed:0 green:0 blue:0 alpha:0.2];
[_keyView addSubview:_pageControl];
}
#pragma mark --------- 创建tableView
- (void)createTableView{
_tableView = [[UITableView alloc] initWithFrame:CGRectMake(0, 44, SCREEN_WIDTH, SCREEN_HEIGHT - 122)];
_tableView.delegate = self;
_tableView.dataSource = self;
//隐藏tableView的线
_tableView.separatorStyle = UITableViewCellSeparatorStyleNone;
// ---------测试---------------
//#define COLORS arc4random()%256/255.0
//
// _tableView.backgroundColor = [UIColor colorWithRed:COLORS green:COLORS blue:COLORS alpha:1];
[self.view addSubview:_tableView];
/**
当触摸tableView时候隐藏键盘
*/
UITapGestureRecognizer *tap=[[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(tapDown)];
[_tableView addGestureRecognizer:tap];
}
//=======================附加功能=======================
- (void)createAdd{
UIButton *btn = [[UIButton alloc] initWithFrame:CGRectMake(0, 35, SCREEN_WIDTH, 43)];
[btn setBackgroundImage:[UIImage imageNamed:@"botton.png"] forState:UIControlStateNormal];
[btn setTintColor:[UIColor blackColor]];
[btn addTarget:self action:@selector(AddBtn:) forControlEvents:UIControlEventTouchUpInside];
[_titleView addSubview:btn];
}
#pragma mark第二部分 按钮点击事件部分
#pragma mark ------------- 调用表情出来的按钮点击事件
- (void)btnImageClick:(UIButton *)imageBtn{
imageBtn.selected ^= 1;
//标记imageBtn
imageBtn.tag = 10;
if (imageBtn.selected) {
[self imageBtnUp];
}else{
[self imageBtnDown];
}
}
//============================ 表情通过附件添加到textView=========================
#pragma mark -------- 删除表情按钮图片
- (void)deleteBtn:(UIButton *)deleteBtn{
deleteBtn.selected ^= 1;
/**
* 判断删除按钮被选中并且textView的长度大于0
*/
if (deleteBtn.selected&&(_textView.attributedText.length > 0)) {
//获取表情
NSMutableAttributedString *chatText=[[NSMutableAttributedString alloc]initWithAttributedString:_textView.attributedText];
//删除最后一个
[chatText deleteCharactersInRange:NSMakeRange(chatText.length-1, 1)];
//传回去
_textView.attributedText=chatText;
}
}
#pragma mark ---------表情按钮图片事件
- (void)btnClick:(UIButton *)btn{
btn.selected ^= 1;
//获取原有的AttributedString
NSMutableAttributedString * textChat = [[ NSMutableAttributedString alloc ] initWithAttributedString:_textView.attributedText];
//获取按钮背景图片(即表情)
UIImage *image = [btn backgroundImageForState:UIControlStateNormal];
//创建并且初始化
NSTextAttachment *textAttachment = [[NSTextAttachment alloc] init];
//设置image
textAttachment.image=image;
//附件大小
textAttachment.bounds = CGRectMake(0, 0, 25, 25);
//将附件转化为纯文本
NSAttributedString *textAttachmentString=[NSAttributedString attributedStringWithAttachment:textAttachment];
//增加到原来的基础上
[textChat appendAttributedString:textAttachmentString];
//以文本形式传给textView
_textView.attributedText = textChat;
}
#pragma mark -------- 附加功能按钮
- (void)AddBtn:(UIButton *)btn{
btn.selected ^= 1;
if (btn.selected) {
[self createAlertView];
}
}
#pragma mark ---------- 发送按钮
- (void)sendBtn:(UIButton *)btn{
[_chatView resignFirstResponder];
/**
* 判断textView长度是否为空
*/
if (_textView.attributedText.length > 0) {
MyChatText *txtContent = [[MyChatText alloc] init];
//给对象添加内容
txtContent.content = _textView.attributedText;
_textView.attributedText = [[NSMutableAttributedString alloc]initWithString:@""];
//存储cell所需数据
[_dataArray addObject:txtContent];
//添加新的一行row
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:_dataArray.count-1 inSection:0];
[_tableView insertRowsAtIndexPaths:@[indexPath] withRowAnimation:UITableViewRowAnimationFade];
//自动滚动到最底部
[_tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionBottom animated:YES];
}
}
#pragma mark第三部分代理部分
#pragma mark ------- scrollView代理
- (void)scrollViewDidEndDecelerating:(UIScrollView *)scrollView{
//获取当前是第几页
int page = _scrollView.contentOffset.x/SCREEN_WIDTH;
//给page赋值
_pageControl.currentPage = page;
}
#pragma mark -------- textView代理
- (BOOL)textView:(UITextView *)textView shouldChangeTextInRange:(NSRange)range replacementText:(NSString *)text{
/**
* 当textView有内容的时候让按钮背景颜色变为蓝色
*/
_btn.backgroundColor = [UIColor colorWithRed:51/255.0 green:156/255.0 blue:249/255.0 alpha:1];
return YES;
}
#pragma mark -------- tableView代理
-(CGFloat)tableView:(UITableView *)tableView heightForRowAtIndexPath:(NSIndexPath *)indexPath
{
MyChatText *MyChatText = [_dataArray objectAtIndex:indexPath.row];
//计算content所占用大小
CGSize size=[MyChatText.content boundingRectWithSize:CGSizeMake(150, 1000) options:NSStringDrawingTruncatesLastVisibleLine | NSStringDrawingUsesFontLeading | NSStringDrawingUsesLineFragmentOrigin context:nil].size;
/**
参数
size
宽高限制,用于计算文本绘制时占据的矩形块。
options
文本绘制时的附加选项。可能取值请参考“NSStringDrawingOptions”。
context
context上下文。包括一些信息,例如如何调整字间距以及缩放。最终,该对象包含的信息将用于文本绘制。该参数可为 nil 。
返回值
一个矩形,大小等于文本绘制完将占据的宽和高。
*/
return size.height + 20 + 30+ 15 ;
}
- (NSInteger)tableView:(UITableView *)tableView numberOfRowsInSection:(NSInteger)section{
return _dataArray.count;
}
- (UITableViewCell *)tableView:(UITableView *)tableView cellForRowAtIndexPath:(NSIndexPath *)indexPath{
static NSString *cellID = @"cellID";
MyChatCell *cell = [tableView dequeueReusableCellWithIdentifier:cellID];
if (cell == nil) {
cell = [[MyChatCell alloc] initWithStyle:UITableViewCellStyleDefault reuseIdentifier:cellID];
}
MyChatText *ChatText = [_dataArray objectAtIndex:indexPath.row];
//计算content所占用大小
CGSize size=[ChatText.content boundingRectWithSize:CGSizeMake(150, 1000) options:NSStringDrawingTruncatesLastVisibleLine | NSStringDrawingUsesFontLeading | NSStringDrawingUsesLineFragmentOrigin context:nil].size;
cell.selectionStyle = UITableViewCellSelectionStyleNone;
//头像的位置受聊天气泡起始坐标的变化
cell.rightHeadView.frame=CGRectMake(size.width+50 , 0 , 40 , 40);
cell.rightHeadView.image=[UIImage imageNamed:@"icon.png"];
//聊天视图受文本长度的影响变化frame
cell.rightView.frame = CGRectMake(self.view.frame.size.width-10-size.width-25-63, 20, size.width+40, size.height+30);
cell.rightTextLabel.frame = CGRectMake(15, 10, size.width, size.height);
cell.rightTextLabel.attributedText = ChatText.content;
return cell;
}
#pragma mark ------- 提示对话框
- (void)createAlertView{
// ============================== 自定义警告对话框 ===============================
_alertView = [[UIAlertView alloc] initWithTitle:@"提示" message:@"该功能暂时不支持" delegate:self cancelButtonTitle:@"确定" otherButtonTitles:@"取消", nil];
[self.view addSubview:_alertView];
[_alertView show];
}
#pragma mark -第四部分视图上滑与下滑
#pragma mark -----------表情图起来与收回
- (void)imageBtnUp{
/**
* 取消系统键盘的第一响应
*/
[_textView resignFirstResponder];
CGRect rectKeylUp = _keyView.frame;
CGRect rectViewUp = _titleView.frame;
//tableView的高度变化
CGRect rectTableView = _tableView.frame;
rectKeylUp.origin.y = rectKeylUp.origin.y - 200;
rectViewUp.origin.y = rectViewUp.origin.y - 200;
rectTableView.size.height = rectTableView.size.height - 200;
[UIView animateWithDuration:0.3 animations:^{
_titleView.frame = rectViewUp;
_keyView.frame = rectKeylUp;
_tableView.frame = rectTableView;
}];
_imageBtn.backgroundColor = [UIColor colorWithRed:51/255.0 green:156/255.0 blue:249/255.0 alpha:1];
}
- (void)imageBtnDown{
CGRect rectKeyDown = _keyView.frame;
CGRect rectViewDown = _titleView.frame;
//tableView的高度变化
CGRect rectTableView = _tableView.frame;
rectKeyDown.origin.y = rectKeyDown.origin.y + 200;
rectViewDown.origin.y = rectViewDown.origin.y + 200;
rectTableView.size.height = rectTableView.size.height + 200;
[UIView animateWithDuration:0.3 animations:^{
_titleView.frame = rectViewDown;
_keyView.frame = rectKeyDown;
_tableView.frame = rectTableView;
}];
_imageBtn.backgroundColor = [UIColor clearColor];
}
#pragma mark -- 键盘即将显示的通知方法
- (void)keyBoardWillShow:(NSNotification *)noti{
//判断是否需要收回表情键盘
if (_keyView.frame.origin.y < self.view.frame.size.height) {
[self imageBtnDown];
//取消imageBtn的选中状态,不然就消失了
UIButton *btn = (UIButton *)[self.view viewWithTag:10];
btn.selected = NO;
}
/**
* 键盘滑出所需时间
*/
NSTimeInterval time ;
//time = [[noti.userInfo objectForKey:@"UIKeyboardAnimationDurationUserInfoKey"] doubleValue];
[noti.userInfo[UIKeyboardAnimationDurationUserInfoKey] getValue:&time];
CGRect keyBoardFrame;
//用于记录键盘的坐标
/**
* 获取键盘的frame
*/
[noti.userInfo[UIKeyboardFrameEndUserInfoKey] getValue:&keyBoardFrame];
//获取集合视图的frame
CGRect rect = _titleView.frame;
/**
* tableView的frame
*/
CGRect rectTableView = _tableView.frame;
rectTableView.size.height = rectTableView.size.height - keyBoardFrame.size.height;
rect.origin.y = keyBoardFrame.origin.y - rect.size.height;
/**
添加动画
*/
[UIView animateWithDuration:time animations:^{
/**
* 改变视图位置
*/
_titleView.frame = rect;
_tableView.frame = rectTableView;
}];
}
#pragma mark -- 键盘即将隐藏的通知方法
- (void)keyBoardWillHide:(NSNotification *)noti{
//1.获取动画时间
NSTimeInterval time;
[noti.userInfo[UIKeyboardAnimationDurationUserInfoKey] getValue:&time];
//2.获取键盘frame
CGRect keyBoardFrame;
[noti.userInfo[UIKeyboardFrameEndUserInfoKey] getValue:&keyBoardFrame];
/**
添加动画
*/
[UIView animateWithDuration:time animations:^{
_titleView.frame = CGRectMake(0, SCREEN_HEIGHT - 78, SCREEN_WIDTH, 78);
// 还原tableView
_tableView.frame = CGRectMake(0, 44, SCREEN_WIDTH, SCREEN_HEIGHT - 122);
}];
}
#pragma mark ----------- tableView手势
- (void)tapDown{
[_textView resignFirstResponder];
//取消键盘第一响应
//判断表情键盘是否在屏幕内
if (_keyView.frame.origin.y < self.view.frame.size.height) {
[self imageBtnDown];
//取消imageBtn的选中状态,不然就消失了
UIButton *btn = (UIButton *)[self.view viewWithTag:10];
btn.selected = NO;
}
}
#pragma mark ---------- touchbegain
- (void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{
[_textView resignFirstResponder];
//取消键盘第一响应
//判断表情键盘是否在屏幕内
if (_keyView.frame.origin.y < self.view.frame.size.height) {
[self imageBtnDown];
//取消imageBtn的选中状态,不然就消失了
UIButton *btn = (UIButton *)[self.view viewWithTag:10];
btn.selected = NO;
}
}
- (void)didReceiveMemoryWarning {
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end
//
// MyChatCell.m
// UIbiaoqingjianpan
//
// Created by 张艳雪 on 16/1/3.
// Copyright (c) 2016年 张艳雪. All rights reserved.
//
#import "MyChatCell.h"
@implementation MyChatCell
//创建cell时候调用
- (id)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier
{
self = [super initWithStyle:style reuseIdentifier:reuseIdentifier];
if (self) {
[self makeView];
}
return self;
}
-(void)makeView{
UIImage *rightImage = [UIImage imageNamed:@"SenderTextNodeBkg.png"];
// ==============================按照内容进行不变形拉伸=========================
rightImage = [rightImage stretchableImageWithLeftCapWidth:30 topCapHeight:35];
// ==============================增加气泡图片背景======================
self.rightView = [[UIImageView alloc] init];
self.rightView.image = rightImage;
// _rightView.backgroundColor = [UIColor redColor];
[self.contentView addSubview:_rightView];
// =================================增加头像位于气泡右面==================
self.rightHeadView=[[UIImageView alloc]init];
self.rightHeadView.layer.masksToBounds=YES;
self.rightHeadView.layer.cornerRadius=10;
[_rightView addSubview:_rightHeadView];
// ==============================增加聊天内容================
self.rightTextLabel = [[UILabel alloc] init];
self.rightTextLabel.font = [UIFont systemFontOfSize:14];
self.rightTextLabel.numberOfLines = 0;
self.rightTextLabel.backgroundColor = [UIColor clearColor];
[_rightView addSubview:_rightTextLabel];
}
- (void)awakeFromNib {
// Initialization code
}
- (void)setSelected:(BOOL)selected animated:(BOOL)animated {
[super setSelected:selected animated:animated];
// Configure the view for the selected state
}
@end
//
// MyChatText.h
// UIbiaoqingjianpan
//
// Created by 张艳雪 on 16/1/3.
// Copyright (c) 2016年 张艳雪. All rights reserved.
//
#import
@interface MyChatText : NSObject
@property(nonatomic,assign)BOOL isPic;
@property(nonatomic,copy)NSString *length;
@property(nonatomic,copy)NSString *height;
@property(nonatomic,copy)NSString *sender;
@property(nonatomic,copy)NSAttributedString *content;
@end
iOS中QQ聊天界面发送消息及表情键盘的实现
最新推荐文章于 2020-12-23 11:41:42 发布