Objective-c——UI基础开发第八天(QQ聊天界面)
一、知识点:
QQ聊天界面
双模型的使用(dataModel和frameModel)
UITextField的使用
通知的使用
拉伸图片的两种方法(slicing/image对象的resizeableImageWithCapInsets属性)
枚举
方法的抽取(相同的拿出,不同的部分作为参数)
二、设置tableview的基本格式
1)定义tableview基本
numberOfSectionsInTableView:设置块
numberOfRowsInSection:设置每块对应的行数
cellForRowAtIndexPath:设置cell样式
2)cell的重用
设置cell
satic NSString *identifier =@"QQCell";
先从缓存池中寻找
QQCell *cell =[_tableview dequeuesableCellWithIdentifier:identifier];
如果缓存池中找不到cell 就创建
if(cell==nil)
{cell =[[QQCell alloc]initWithStyle:UITableViewCellStyleDefault reuserIndentiier:identifier];}
3)设定自定义的cell格式(注意为什么消息框是button:因为既可以设置文本,又可以设置图片)
a、定义需要用到的属性及样式
@property(nonatomic,weak)UILabel *timeLabel;
@property(nonatomic,weak)UIButton *textButton;
@property(nonatomic,weak)UIImageView *iconImage;
b、定义初始化方法,注意与viewController中cell创建时调用的方法要一致
-(instancetype)initWithStyle:(UITableViewCellStyle)style reuseIdentifier:(NSString *)reuseIdentifier{
if(self =[super initWithStyle:style reuseIdentifier:reuseIdentifier]{
[self setupUI];//在内部设置button、label之类的样式
}}return self;
c、双模型(在懒加载中将数据模型传递给frame模型:原因:
1、懒加载中,方法只需要执行一次
2、行高rowheight 方法必须在cell方法调用前调用,所以要在cell中实现frame的计算,传递出来顺序是有问题的
传递方式: 在frameModel中定义QQModel这一属性
a、定义model属性
@class QQModel;
@property (nonatomic ,strong) QQModel *qqModel;
b、在懒加载中实现赋值
QQModel *model =[QQModel QQmodelWithDictionary:dict];
QQFrameModel *frameModel =[QQFrameModel alloc]init];
frameModel.qqModel =model;//传递成功
c、把frameModel的值传入dataArray数组中,因为这会frameModel中既有(数据model也包含各个控件的Frame)
[_dataArray addObject:frameModel];
d、如何根据文本数据内容,设置frame
1)、设置最大可变动区域(如果无限制则:MAXFLOAT)
CGSize maxArea =CGSizeMake(textMaxA,MAXFLOAT);
2)、设置属性字典(注意属性字体大小的设置一定要和原先控件中字体大小一致,否则,可能文本中以省略号带过)
NSDictionary *dict =@{NSFontAttributeName:[UIFont systemFontOfSize:17};
3)、设置对象数据的真实大小boundingRectWithSize
CGSize RealSize =[_qqModel.text boundingRectWithSize :maxArea options:NSStringDrawingUsesLineFragmentOrigin attributes:dict context :nil].size;
e、在cell的设置类中调用frameModel和数据模型并设置
1)重写FrameModel的set方法:
@property(nonatomic,strong) QQFrameModel *frameModel;
-(void)setFrameModel:(QQFrameModel *)frameModel{
2)必须对模型进行实例化
_frameModel =frameModel;
3)设置模型中的数据和Frame
}
怎么获取qqModel
#import “QQModel.h”
QQModel *qqModel =_frameModel.qqModel;
f、代码实现图片拉伸
/**
1、获取图片
2、设置拉伸 线条构成的中心区域(区域越小越好,所以将宽高都设成其中心线)
3、调用image对象的resizableImageWithCapInSets属性
*/
UIImage *image =[UIImage imageNamed:imageName];
CGFloat *halfWidth =image.size.width/2;
CGFloat *halfHeight =image.size.height/2;
UIImage *resizeImage =[image resizableImageWithCapInsets:UIEdgeInsetsMake(halfHeight,halfWidth,halfHeight,halfWidth) resizingMode:UIImageResizingModeStretch];
g、注意图片拉伸之后,文本可能不在图片内部,可以通过增加button的frame大小,同时设置文本的那边距(contentEdgeInsets UIEdgeInsetsMake)
textButton.contentEdgeInsets =UIEdgeInsetsMake(20,20,20,20);
h、设置行高
heightForRowAtIndexPath
QQ FrameModel *frameModel =self.dataArray[indexPath.row];
return frameModel.cellHeight
三、比较时间(两两比较,同一时间内的label只显示一遍,可以知道,只要比较一次,而且又要获得上一次的时间,最好在懒加载中实现)
/**
0、在qqModel中设置一个HiddenTimeLabel属性 存储比较完的结果
1、取出上一次的数据
2、进行比较,如果一样的话,就往qqModel 中传入HiddenTimeLabel=YES
*/
@property (nonatomic,assign,getter = isHiddenTimeLabel) BOOL HiddenTimeLabel;
QQFrameModel *latFrameModel =self.dataArray.lastObject;
if([lastFrameModel.qqModel.time isEqualToString :frameModel.qqModel.time])
{
qqModel.HiddenTimeLabel=YES;
}
调用:
_timeLabel.hidden =qqModel.isHiddenTimeLabel;(在hidden属性中直接调用重写的get方法即可)
四、补充使用枚举(内部的值类别,枚举的值名称,默认从0开始)
typedef NS_ENUM(NSInteger,QQUserType)
{
QQUserTypeOther=0;
QQuserTypeMe,
};
枚举的好处:将无意义的数字转化成有意义的字符,增加代码可读性
五、设置底部的弹框(了解textField属性和通知概念)
五.1 TextField 的使用
textField.placeholder=@"占位符"
UIView *left =[[UIView alloc]initWithFrame:CGRectMake(100, 0, 10, 10)];
left.backgroundColor=[UIColor orangeColor];
text.leftView=left;
text.leftViewMode = UITextFieldViewModeAlways;
(添加leftview的时候必须要设置UITextFieldViewMode否则无法显示
leftview/rightview/leftViewMode/rightViewMode
密码:
text.secureTextEntry=YES;
text.cleanButtonMode =UITextFieldViewModeWhileEditing;
五、2)通知的使用
/**
1、注册监听者
2、通知中心发布通知
3、将销毁的监听者移除监听
*/
1
/**
addObserver: 监听对象
selector:监听对象收到通知之后调用的方法
name:通知的名称
object: 通知的发布者
*/
[[NSNotificationCenter defaultCenter] addObserver:ZhangSan selector:@selector(recieveNotification:) name:@"HuoYing" object:souhuHuoYing];
2
/**
接受通知之后,要执行的方法
*/
-(void) recieveNotification:(NSNotification *)noti
{
NSDictionary *c = noti.userInfo;
Company *company = c[@"company"];
NSLog(@"%@ 订阅了 %@公司的 %@视频已经更新了",self.personname,company.companyname,company.moviename);
// NSLog(@"%@",noti);
}
3
-(void) dealloc
{
[[NSNotificationCenter defaultCenter]removeObserver:self.personname];
}
五、3)设置键盘监听,通过监听传递出的通知,改变底部输入框的frame和tableview的frame
1、// 添加监听, 键盘即将隐藏的时候, 调用
[[NSNotificationCenter defaultCenter] addObserver:self
selector:@selector(keyboardWillDisAppear:)
name:UIKeyboardWillHideNotification
object:nil];
调用的监听通知名称包括:UIKeyboardWillHideNotification /键盘即将隐藏的通知名
name:UIKeyboardWillChangeFrameNotification/键盘隐藏或出现的通知名
UIKeyboardWillShowNotification/键盘出现的通知名
2、收到通知消息时要执行的动画:(UIView animateWithDuration)
[UIView animateWithDuration:interval animations:^{
self.view.transform = CGAffineTransformMakeTranslation(0, (keyboardEndY - keyboardBeginY));
}];
3、用户如果滚动tableview的时候,或者用户输入完成按return的时候,键盘都需要消失
- (void)scrollViewWillBeginDragging:(UIScrollView *)scrollView {
// 撤销textField 的第一响应者身份
[_textField resignFirstResponder];
}
4、默认的时候,tableview都应该滚动到最后一行(UITableView scrollToRowAtIndexPath)
- (void)scrollToBottom {
NSIndexPath *indexPath = [NSIndexPath indexPathForRow:self.dataArray.count - 1 inSection:0];
[_tableView scrollToRowAtIndexPath:indexPath atScrollPosition:UITableViewScrollPositionBottom animated:YES];
}
5、既然是聊天框,那么cell就不应该有被选中时候的颜色(selectionStyle)
// 选中cell后不改变颜色
cell.selectionStyle = UITableViewCellSelectionStyleNone;
6、撤销监听
#warning 一定不要忘记移除监听者
- (void)dealloc {
[[NSNotificationCenter defaultCenter] removeObserver:self];
}
六、设置时间格式
/**
1、取出时间(NSDate date)
2、初始化格式NSDateFormatter (NASDateFormatter) formatter.dateformat(属性)
3、日期转字符 formatter stringFromDate:currentDate
*/
// 取出当前的时间
NSDate *currentDate = [NSDate date];
// 设置时间的格式
NSDateFormatter *formatter = [[NSDateFormatter alloc] init];
// 时间格式
// yyyy-MM-dd HH:mm:ss 时间格式
formatter.dateFormat = @"HH:mm";
NSString *dateString = [formatter stringFromDate:currentDate];
七、通知和代理的区别
共同:都可以传递消息
区别:代理是一对一传递,通知是多对多,可以有多个消息发布者和多个消息接收者
例如,代理可以知道textfiled什么时候开始输入值,什么时候结束输入值,但是像键盘这种弹入弹出它的时间都是不可控的,需要实时监测这个就需要通知中心发布消息。
Objective-c——UI基础开发第八天(QQ聊天界面)的更多相关文章
- WPF开发实例——仿QQ登录界面
原文:WPF开发实例--仿QQ登录界面 版权声明:本文为博主原创文章,如需转载请标明转载地址 http://blog.csdn.net/u013981858 https://blog.csdn.net ...
- QQ聊天界面的布局和设计(IOS篇)-第一季
我写的源文件整个工程会再第二季中发上来~,存在百度网盘, 感兴趣的童鞋, 可以关注我的博客更新,到时自己去下载~.喵~~~ QQChat Layout - 第一季 一.准备工作 1.将假数据messa ...
- QQ聊天界面的布局和设计(IOS篇)-第二季
QQChat Layout - 第二季 本来第二季是快写好了, 也花了点功夫, 结果gitbook出了点问题, 给没掉了.有些细节可能会一带而过, 如有疑问, 相互交流进步~. 在第一季中我们完成了Q ...
- 高仿qq聊天界面
高仿qq聊天界面,给有需要的人,界面效果如下: 真心觉得做界面非常痛苦,给有需要的朋友. chat.xml <?xml version="1.0" encoding=&quo ...
- IOS开发学习笔记043-QQ聊天界面实现
QQ聊天界面实现 效果如下: 实现过程: 1.首先实现基本界面 头像使用 UIImageView : 文字消息使用 UIButton 标签使用 UILable :水平居中 所有元素在一个cell中,在 ...
- 在WEB项目中调用QQ通讯组件打开QQ聊天界面
在很多WEB项目中,需要提供在线服务的功能,加上自己的联系方式,例如:QQ,不用添加QQ好友也可以交谈,那这到底是怎么实现的呢? 对于这个功能,需要提到一个组件,即“QQ通讯组件”.QQ通讯组件是一种 ...
- WPF和Expression Blend开发实例:模拟QQ登陆界面打开和关闭特效
不管在消费者的心中腾讯是一个怎么样的模仿者抄袭者的形象,但是腾讯在软件交互上的设计一直是一流的.正如某位已故的知名产品经理所说的:设计并非外观怎样,感觉如何.设计的是产品的工作原理.我觉得腾讯掌握了其 ...
- Android 根据QQ号跳转到QQ聊天界面
从自己开发的应用中根据QQ号跳转到QQ应用的聊天界面,实现起来很方便: 即: startActivity(new Intent(Intent.ACTION_VIEW, Uri.parse(" ...
- Android—简单的仿QQ聊天界面
最近仿照QQ聊天做了一个类似界面,先看下界面组成(画面不太美凑合凑合呗,,,,):
随机推荐
- UVA 10294 等价类计数
题目大意: 项链和手镯都是若干珠子穿成的环形首饰,手镯可以旋转和翻转,但项链只能旋转,给n个珠子,t种颜色,求最后能形成的手镯,项链的数量 这里根据等价类计数的polya定理求解 对于一个置换f,若一 ...
- 宜家的幸福生活,源于K2 BPM的支撑
很久很久以前,有一篇很火的文章在各大网站被疯狂转载<一个在北欧生活10年的MM,告诉你为什么北欧全球幸福指数第一>,开头第一段就已经让人羡慕嫉妒恨了. "下午的四.五点钟,北欧人 ...
- 关于BIOS的一点东西
关于BIOS的一点东西 编辑删除转载2016-05-20 00:36:36 去把BIOS的每个单词意思都有道一遍就都明白了,BOOT是更改 启动顺序的(台式机一直按del键就会进入BIOS界面,用上下 ...
- xlistview的(java)
package com.bwie.xlistviews; import java.text.SimpleDateFormat;import java.util.Date; import com.bwi ...
- PHP ceil() 函数
定义和用法 ceil() 函数向上舍入为最接近的整数. 语法 ceil(x) 参数 描述 x 必需.一个数. 说明 返回不小于 x 的下一个整数,x 如果有小数部分则进一位.ceil() 返回的类型仍 ...
- http://182.92.241.20/mypro/login 偶的点金项目细化分包管理平台即将上线!!
http://182.92.241.20/mypro/login 偶的点金项目细化分包管理平台即将上线!! 敬请期待! 项目外包利器 项目管理利器
- 在android的spinner中,实现取VALUE值和TEXT值。 ZT
在android的spinner中,实现取VALUE值和TEXT值. 为了实现在android的 spinner实现取VALUE值和TEXT值,我尝试过好些办法,在网上查的资料,都是说修改适配器, ...
- C# DataContract DataMember
Windows Communication Foundation (WCF) uses a serialization engine called the Data Contract Serializ ...
- IOS 作业项目(2) 画图(保存,撤销,笔粗细设定功能)
先上效果图
- Windows桌面快捷方式图标全部变成同一个图标的解决方法
今天来个客人,说是电脑的所有程序打开都变成 Adobe Reader 了,打开看了下,刚开始是以为EXE文件关联被修改了,用注册表修复工具弄了下,重启电脑,还是老样子.仔细看了下,原来只是快捷方式变成 ...