1:initWithFrame方法的理解

. initWithFrame方法是什么?
initWithFrame方法用来初始化并返回一个新的视图对象,根据指定的CGRect(尺寸)。
当然,其他UI对象,也有initWithFrame方法,但是,我们以UIView为例,来搞清楚initWithFrame方法。 .什么时候用initWithFrame方法?
简单的说,我们用编程方式申明,创建UIView对象时,使用initWithFrame方法。
在此,我们必须搞清楚,两种方式来进行初始化UIView。
a.使用 Interface Builder 方式。
这种方式,就是使用nib文件。通常我们说的“拖控件” 的方式。
实际编程中,我们如果用Interface Builder 方式创建了UIView对象。(也就是,用拖控件的方式)
那么,initWithFrame方法方法是不会被调用的。因为nib文件已经知道如何初始化该View。(因为,我们在拖该view的时候,就定义好了长、宽、背景等属性)。
这时候,会调用initWithCoder方法,我们可以用initWithCoder方法来重新定义我们在nib中已经设置的各项属性。 b.使用编程方式。
就是我们声明一个UIView的子类,进行“手工”编写代码的方式。
实际编程中,我们使用编程方式下,来创建一个UIView或者创建UIView的子类。这时候,将调用initWithFrame方法,来实例化UIView。
特别注意,如果在子类中重载initWithFrame方法,必须先调用父类的initWithFrame方法。在对自定义的UIView子类进行初始化操作。
比如:
- (id)initWithFrame:(CGRect)frame{
    self = [super initWithFrame:frame];// 先调用父类的initWithFrame方法
    if (self) {
        
        // 再自定义该类(UIView子类)的初始化操作。
        _scrollView = [[UIScrollView alloc] initWithFrame:self.bounds];
        [_scrollView setFrame:CGRectMake(, , , )];
        _scrollView.contentSize = CGSizeMake(*, );
        
        [self addSubview:_scrollView];
    }
    return self;
}

2:layoutSubviews总结

layoutSubviews在以下情况下会被调用:
a、init初始化不会触发layoutSubviews
   但是是用initWithFrame 进行初始化时,当rect的值不为CGRectZero时,也会触发
b、addSubview会触发layoutSubviews
c、设置view的Frame会触发layoutSubviews,当然前提是frame的值设置前后发生了变化
d、滚动一个UIScrollView会触发layoutSubviews
e、旋转Screen会触发父UIView上的layoutSubviews事件
f、改变一个UIView大小的时候也会触发父UIView上的layoutSubviews事件 layoutSubviews, 当我们在某个类的内部调整子视图位置时,需要调用。反过来的意思就是说:如果你想要在外部设置subviews的位置,就不要重写。layoutSubviews对subviews重新布局,layoutSubviews方法调用先于drawRect 刷新子对象布局
-layoutSubviews方法:这个方法,默认没有做任何事情,需要子类进行重写
-setNeedsLayout方法: 标记为需要重新布局,异步调用layoutIfNeeded刷新布局,不立即刷新,但layoutSubviews一定会被调用
-layoutIfNeeded方法:如果,有需要刷新的标记,立即调用layoutSubviews进行布局(如果没有标记,不会调用layoutSubviews)
如果要立即刷新,要先调用[view setNeedsLayout],把标记设为需要布局,然后马上调用[view layoutIfNeeded],实现布局
在视图第一次显示之前,标记总是“需要刷新”的,可以直接调用[view layoutIfNeeded]

3:单元行有其它控件时,行选中时关于控件高亮的问题

此处是cell中的accessoryView放一UIButton,在行被选中的情况下,UIButton同时也被高亮处于被选中的壮态,通过下面这样处理可以解决问题

@interface UCaiTableViewCell : UITableViewCell

@end

@implementation UCaiTableViewCell

@synthesize piosaDelegate = _piosaDelegate;

- (void)setHighlighted:(BOOL)highlighted animated:(BOOL)animated{
[super setHighlighted:highlighted animated:animated]; if (highlighted) {
[(UIButton *)self.accessoryView setHighlighted:NO];
}
} - (void)setSelected:(BOOL)selected animated:(BOOL)animated{
[super setSelected:selected animated:animated]; if (selected) {
[(UIButton *)self.accessoryView setHighlighted:NO];
}
}

4:UIButton高亮效果去除

继承UIButton然后可以重写setHighlighed方法,里面什么内容也不写;

.H文件:

#import <UIKit/UIKit.h>

@interface HWEmotionTabBarButton : UIButton

@end

.M文件:

#import "HWEmotionTabBarButton.h"

@implementation HWEmotionTabBarButton

- (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
// 设置文字颜色
[self setTitleColor:[UIColor whiteColor] forState:UIControlStateNormal];
[self setTitleColor:[UIColor darkGrayColor] forState:UIControlStateDisabled];
// 设置字体
self.titleLabel.font = [UIFont systemFontOfSize:];
}
return self;
} - (void)setHighlighted:(BOOL)highlighted {
// 按钮高亮所做的一切操作都不在了
}
@end

5:一个选项卡的封装

.H文件内容

#import <UIKit/UIKit.h>

typedef enum {
HWEmotionTabBarButtonTypeRecent, // 最近
HWEmotionTabBarButtonTypeDefault, // 默认
HWEmotionTabBarButtonTypeEmoji, // emoji
HWEmotionTabBarButtonTypeLxh, // 浪小花
} HWEmotionTabBarButtonType; @class HWEmotionTabBar; @protocol HWEmotionTabBarDelegate <NSObject> @optional
- (void)emotionTabBar:(HWEmotionTabBar *)tabBar didSelectButton:(HWEmotionTabBarButtonType)buttonType;
@end @interface HWEmotionTabBar : UIView
@property (nonatomic, weak) id<HWEmotionTabBarDelegate> delegate;
@end 注意:这边主要是要引入@class .M文件内容: @interface HWEmotionTabBar()
@property (nonatomic, weak) HWEmotionTabBarButton *selectedBtn;
@end @implementation HWEmotionTabBar - (id)initWithFrame:(CGRect)frame
{
self = [super initWithFrame:frame];
if (self) {
[self setupBtn:@"最近" buttonType:HWEmotionTabBarButtonTypeRecent];
[self setupBtn:@"默认" buttonType:HWEmotionTabBarButtonTypeDefault];
// [self btnClick:[self setupBtn:@"默认" buttonType:HWEmotionTabBarButtonTypeDefault]];
[self setupBtn:@"Emoji" buttonType:HWEmotionTabBarButtonTypeEmoji];
[self setupBtn:@"浪小花" buttonType:HWEmotionTabBarButtonTypeLxh];
}
return self;
} /**
* 创建一个按钮
*
* @param title 按钮文字
*/
- (HWEmotionTabBarButton *)setupBtn:(NSString *)title buttonType:(HWEmotionTabBarButtonType)buttonType
{
// 创建按钮
HWEmotionTabBarButton *btn = [[HWEmotionTabBarButton alloc] init];
[btn addTarget:self action:@selector(btnClick:) forControlEvents:UIControlEventTouchDown];
btn.tag = buttonType;
[btn setTitle:title forState:UIControlStateNormal];
[self addSubview:btn]; // 设置背景图片
NSString *image = @"compose_emotion_table_mid_normal";
NSString *selectImage = @"compose_emotion_table_mid_selected";
if (self.subviews.count == ) {
image = @"compose_emotion_table_left_normal";
selectImage = @"compose_emotion_table_left_selected";
} else if (self.subviews.count == ) {
image = @"compose_emotion_table_right_normal";
selectImage = @"compose_emotion_table_right_selected";
} [btn setBackgroundImage:[UIImage imageNamed:image] forState:UIControlStateNormal];
[btn setBackgroundImage:[UIImage imageNamed:selectImage] forState:UIControlStateDisabled]; return btn;
} - (void)layoutSubviews
{
[super layoutSubviews]; // 设置按钮的frame
NSUInteger btnCount = self.subviews.count;
CGFloat btnW = self.width / btnCount;
CGFloat btnH = self.height;
for (int i = ; i<btnCount; i++) {
HWEmotionTabBarButton *btn = self.subviews[i];
btn.y = ;
btn.width = btnW;
btn.x = i * btnW;
btn.height = btnH;
}
} - (void)setDelegate:(id<HWEmotionTabBarDelegate>)delegate
{
_delegate = delegate; // 选中“默认”按钮
[self btnClick:(HWEmotionTabBarButton *)[self viewWithTag:HWEmotionTabBarButtonTypeDefault]];
} /**
* 按钮点击
*/
- (void)btnClick:(HWEmotionTabBarButton *)btn
{
//转换被选中的效果
self.selectedBtn.enabled = YES;
btn.enabled = NO;
self.selectedBtn = btn; // 通知代理
if ([self.delegate respondsToSelector:@selector(emotionTabBar:didSelectButton:)]) {
[self.delegate emotionTabBar:self didSelectButton:btn.tag];
}
} @end 注意:当增加完控件后,self.subviews.count这个值就是从1开始,而setDelegate则是为了用来显示默认被选中,因为有枚举所以可以很准确定位到想设置默认的那个UIButton,UIControlStateDisabled这个状态是为了当被选中后就不能再点击,配合着enabled设置,代码中创建的一个属性用于存放当前被选中的UIButton,在事件btnClick中对它进行转换赋值;

 6:UITextField实现获取光标但第一次不弹出键盘

实现原理如下先在上面的盖一层视图,然后增加点击事件,主要代码如下:

    if (!_myTextField) {
_myTextField=[UITextField new];
_myTextField.font=[UIFont fontWithName:@"Helvetica-Bold" size:];
_myTextField.textColor=[UIColor blackColor];
_myTextField.delegate=self;
_myTextField.tintColor=[UIColor blackColor];
_myTextField.text=self.billing_amount;
_myTextField.textAlignment=NSTextAlignmentLeft;
_myTextField.keyboardType=UIKeyboardTypeNumberPad;
_myTextField.userInteractionEnabled=YES;
_myTextField.inputView=[[UIView alloc]initWithFrame:CGRectZero];
[_myTextField becomeFirstResponder];
[self addSubview:_myTextField];
[_myTextField mas_makeConstraints:^(MASConstraintMaker *make) {
make.left.mas_equalTo(_myPriceBadgeLabel.right).offset(AdaptedSize());
make.top.mas_equalTo(_myPriceBadgeLabel.top);
make.right.mas_equalTo(-AdaptedSize());
}];
} if (!_topTextFieldView) {
_topTextFieldView=[UIView new];
[_topTextFieldView bk_whenTapped:^{
_myTextField.inputView=nil;
[_topTextFieldView removeFromSuperview];
[_myTextField reloadInputViews];
}];
[self addSubview:_topTextFieldView]; [_topTextFieldView mas_makeConstraints:^(MASConstraintMaker *make) {
make.edges.mas_equalTo(_myTextField);
}];
}

IOS开发基础知识--碎片18的更多相关文章

  1. IOS开发基础知识碎片-导航

    1:IOS开发基础知识--碎片1 a:NSString与NSInteger的互换 b:Objective-c中集合里面不能存放基础类型,比如int string float等,只能把它们转化成对象才可 ...

  2. IOS开发基础知识--碎片19

    1:键盘事件顺序 UIKeyboardWillShowNotification // 键盘显示之前 UIKeyboardDidShowNotification // 键盘显示完成后 UIKeyboar ...

  3. IOS开发基础知识--碎片33

    1:AFNetworking状态栏网络请求效果 直接在AppDelegate里面didFinishLaunchingWithOptions进行设置 [[AFNetworkActivityIndicat ...

  4. IOS开发基础知识--碎片42

    1:报thread 1:exc_bad_access(code=1,address=0x70********) 闪退 这种错误通常是内存管理的问题,一般是访问了已经释放的对象导致的,可以开启僵尸对象( ...

  5. IOS开发基础知识--碎片50

      1:Masonry 2个或2个以上的控件等间隔排序 /** * 多个控件固定间隔的等间隔排列,变化的是控件的长度或者宽度值 * * @param axisType 轴线方向 * @param fi ...

  6. IOS开发基础知识--碎片3

    十二:判断设备 //设备名称 return [UIDevice currentDevice].name; //设备型号,只可得到是何设备,无法得到是第几代设备 return [UIDevice cur ...

  7. IOS开发基础知识--碎片11

    1:AFNetwork判断网络状态 #import “AFNetworkActivityIndicatorManager.h" - (BOOL)application:(UIApplicat ...

  8. IOS开发基础知识--碎片14

    1:ZIP文件压缩跟解压,使用ZipArchive 创建/添加一个zip包 ZipArchive* zipFile = [[ZipArchive alloc] init]; //次数得zipfilen ...

  9. IOS开发基础知识--碎片16

    1:Objective-C语法之动态类型(isKindOfClass, isMemberOfClass,id) 对象在运行时获取其类型的能力称为内省.内省可以有多种方法实现. 判断对象类型 -(BOO ...

随机推荐

  1. 如何用Excel直接查询Oracle中的数据

    将Oracle中查询的数据保存为Excel文件,通常使用的是PL/SQL Developer. 其实,Excel可直接写SQL语句查询Oracle中数据,在这里,用到ODBC驱动.详细步骤如下: 一. ...

  2. Quartz 在 Spring 中如何动态配置时间--转

    原文地址:http://www.iteye.com/topic/399980 在项目中有一个需求,需要灵活配置调度任务时间,并能自由启动或停止调度. 有关调度的实现我就第一就想到了Quartz这个开源 ...

  3. grape动态PHP结构(一)——目录结构与配置文件

    一.结构介绍 结构的名字grape,中文名叫葡萄,因为最近一个同事经常带葡萄到公司给我们吃,受到启发想到了这个名字. 1)本结构需要在PHP5.5中运行,如果要在5.4中运行,有些地方就要做些修改 2 ...

  4. Unity调用Android类方法

    Unity调用Android类方法 1.  添加Unity的classes.jar文件 创建一个Android工程AndroidUnityDemo. 由于Unity的版本不同,直接在Unity安装包文 ...

  5. Macaca自动化测试之PC端测试

    Macaca是一套完整的自动化测试解决方案.由阿里巴巴公司开源: http://macacajs.github.io/macaca/ 特点: 同时支持PC端和移动端(Android.iOS)自动化测试 ...

  6. 初次体验百度eCharts遇到的问题和解决方法

    前言 上周在厌烦Highchart下,体验了下百度的eCharts,支持IE6.7.8+外,对数据在线编辑还有工具栏支持,体验时遇到了几个小问题,最近两天在尝试得到了一个解决方法. Tooltip时单 ...

  7. html5 canvas 画图表

    (function () { var canvas = document.createElement("canvas"); canvas.width = 800; canvas.h ...

  8. 你的程序支持复杂的时间调度嘛?如约而来的 java 版本

    你的程序支持复杂的时间调度嘛? 这篇文章介绍了时间适配器的c#版本,是给客户端用的,服务器自然也要有一套对应的做法,java版本的 [年][月][日][星期][时间] [*][*][*][*][*] ...

  9. Windows下80端口被pid为4的System进程占用解决方法

    前言 之前是Windows 7系统,前段时间装了Windows 10,php环境还没来得及搭建.今天折腾了一下,是用nginx+php,端口是80(已经停止了iis服务),nginx就是起不来,十之八 ...

  10. JS检查是否支持Storage

    查看效果:http://hovertree.com/code/html5/q69kvsi6.htm 代码: <!DOCTYPE html> <html> <head> ...