仿网易彩票思路

仿网易彩票思路

第一步、  项目的配置
   
1 > 新建项目:项目前缀:把项目名称里面的大写抽出来。
   
2 > 支持项目部署,支持 ios6,ios7
   
3 > 不支持横竖屏
   
4 > 导入图标和启动图片
   
5 > 程序启动的时候,隐藏状态栏, ios6 需要恢复状态栏显示
   
6 > 设置状态栏颜色 ios7 默认状态栏交给控制器管理,修改 info.plist 文件,让状态栏交给 application 管理
   
6 > 项目文件夹按模块划分, Main:( 主框架,自定义 tab 控制器 ),Other: 存放其他头文件和 .m 文件 (main ,代理, pch( 头文件 ))

第二步、  搭建项目主框架
   
1 > 修改窗口的根控制器。
       
原因 : 主窗口的根控制器是 TabBar 控制器, TabBar 里面的子控制器是导航控制器?为什么,因为每个导航条的标题不一样。

第三步、 设置 tabBar 上按钮的图片
   
存在的问题 :
   
1 > 设置 tabBar 上面的按钮图片不好使, tabBarButton 的图片有规格,用不了。
   
解决方式 :
   
1 > 自定义 tabBar ,系统自带的 tabBar 上的 tabBarButton 都不好使,自定义的 tabBar 添加 UIButton ,注意继承 UIView, 因为 UITabBar 里面的子控件根本用不上。
   
2 > 自定义 tabBar ,添加 5 个按钮,显示图片

     存在的问题?
    
1 > tabBar 里面的按钮应该由控制器决定
    
2 > push 控制器的时候底部条,隐藏不了。
    
解决方法 :
    
1 提供一个方法,给控制器添加按钮。系统自带的 tabBar 里有多少按钮也是根据控制器个数决定的。
    
2 把自定义 tabBar 添加到系统自带的 tabBar

第四步、 点击按钮 , 切换控制器( UITabBarController.selectedIndex
   
存在的问题?
   
1 > 只有 UITabBarController 设置 selectedIndex 才可以切换控制器,但是 UITabBarController 不知道当前选中哪个按钮
   
解决方式 :
   
2 > 用代理或者 block 把角标传给控制器

第五步、 设置导航条的外观 ( 背景图片和文字 ) ,只需要设置一次 .
   
1 > 为什么要获取整个应用程序的导航条外观?避免拿到一个一个导航控制器去设置导航条的外观
   
2 > 怎么获取? UINavigationBar *navBar  = [UINavigationBar appearance] 只要遵守 UIAppearance 这个协议,都可以这样获取。
   
3 > 设置导航条的背景颜色 ?ios7 ios6 是不一样的。
   
4 > 运行 ios6 ,适配 ios6 的导航条。
   
5 > ios7 ios6 导航条图片的区别?
       ios7:
控制器包括状态栏 20 的高度 , 导航条的高度为 64 ,会自动把状态栏 20 的高度填充
       ios6:
状态栏 20 的高度不属于控制器,导航条高度 44 。用 44 高度的图片
   
6 > 定义宏,方便适配 #define iOS7 ([[UIDevice currentDevice].systemVersion floatValue] >= 7.0 )
   
7 > 设置导航条文字颜色

第六步、 自定义导航控制器
   
1 > 为什么要自定义导航控制器 ? 拦截 push 操作,重写 push 方法,在 push 的时候,隐藏底部条,就不需要一个控制器一个控制器的勾选 Hide Bottom Bar on Push
   
2 > 在自定义导航控制器设置导航条外观
   
3 > initialize 里设置 : 导航条外观只需要设置一次
   
4 > initialize: 在第一次使用这个类或者子类的时候调用
   
5 > initialize 里判断下是否是本类调用,是才需要设置导航条,保证设置一次主题。 self == [ILNavgationController class]

第七步、  完成每个模块的导航条
   
购彩大厅:系统自带的 UIBarButton 不能同时设置图片和文字 , 拖一个按钮同时设置文字和图片,还需要设置按钮宽度,资讯和图片中间有间距。
// 设置按钮标题的位置
- (
CGRect )titleRectForContentRect:( CGRect )contentRect;
// 设置按钮图片的位置
- (
CGRect )imageRectForContentRect:( CGRect )contentRect;
   
合买跟单: titleView 需要自定义按钮,设置内部的位置

第八步、 自定义按钮 : 修改内部子控件的尺寸
   
1. 获取当前文字: self .currentTitle
   
2. 获取当前文字尺寸 . 计算内部 Label 的尺寸。
   
3. 图片尺寸:假设图片宽度 30. w = contentRect.size.width - 30
   
注意点:
    * titleRectForContentRect
内部不能调用 self .titleLabel, 会造成死循环。因为 self .titleLabel 内部会调用 titleRectForContentRect
    * boundingRectWithSize
ios7 才有, ios6 没有这个方法,需要判断使用。

第九步、  自定义按钮尺寸计算 - 多版本处理
   
1 > 理解编译时报错和运行时报错? #import <Availability.h>
   
2 > 运行时报错:在 SDK7 .0 的环境 (xcode5) 编译 boundingRectWithSize ,是不会报错的,但是运行在 ios6 的系统上会报错, ios6 没有这个方法。需要判断当前运行在哪个系统,用 ios7 宏判断。
   
3 > 编译时报错:在 SDK6 .0 的环境 (xcode4 .6 ) 编译 boundingRectWithSize ,是直接报编译错误,因为 sdk6 .0 没有这个方法。

第十步、  我的彩票 ( 登录界面 )-ios7 ios6 简单适配
   
存在问题
   
1 > 观察 UIImageView y
   
1 > UIImageView y 值在 ios6 ios7 不一样。
   
原因:
   
0 > ios6,ios7 控制器 view 的尺寸不一样。
   
1 > ios6 里主流框架中,导航控制器的根控制器 view 的尺寸,很小。 PPT 演示, ios6 控制器从导航条开始, ios7 从屏幕左上角开始,包含状态栏。
   
2 > ios7 多了一个 edgesForExtendedLayout 属性,才让导航控制器的根控制器 view 的尺寸和屏幕一样大 .
   
3 > edgesForExtendedLayout 可以让控制器上下左右扩展
   
解决 :
   
1 > 通过代码判断下,调整在 ios7 ios6 UIImageView 的位置,这种方式麻烦。因为界面是固定的,用 xib 或者 storyboard 描述更省时间。
   
2 > 找到我的彩票控制器,告诉他不要上下扩展就好了,找到 Extend Edages ,把 Under Top Bars Under Bottom Bars 取消选中
   
2 > 一般开发中,如果不需要滚动的控制器,就不需要扩展,因为不需要有穿透效果。
   
3 > ios7 取消我的彩票控制器的上下扩展。这时候 ios7 导航控制器的根控制器 view 的尺寸就和 ios6 一样的了。
   
4 > autolayout 解决运行在 3.5 上图片被压扁。

13 > 登录按钮图片拉伸(按钮尺寸: 300 * 40
   
1 > 拉伸图片中间一个像素点。
   
2 > 通过 storyboard 只能拉伸 UIImageView
   
3 > storyboard x: 表示左边多少不拉伸 y: 表示上边多少不拉伸 w: 表示宽度拉伸多少个像素 h: 表示高度拉伸多少个像素 x: 0.5 ( 左边一半不拉伸 ) y: 0.5 ( 顶部一半不拉伸 ) w: 0 ( 宽度拉伸一个像素 ) h: 0 ( 高度拉伸一个像素 )
   
4 > 拉伸按钮,必须通过代码。
   
5 > 自定义登录控制器 loginController
   
6 > UIImage 抽分类 resizableImageWithName

14 > 我的彩票 ( 右上角设置按钮的颜色和返回按钮的颜色默认是蓝色,需要设置为白色 )
   
1 > 应用程序所有导航条上的 UIBarButton 都需要设置白色的。
   
2 > UIBarButton 在导航条上,所以我们设置导航条的主题颜色就好了。
   
3 > 获取整个应用程序的外观设置主题颜色 UINavigationBar setTintColor( 主题颜色 )
   
3 > 只需要设置一次,并且跟导航控制器有关系,在导航控制器里的 initialize 里设置,并且之前在导航控制器拿到了整个应用程序的导航条

15 > 设置 ios6 上应用程序所有导航条上的按钮背景
   
1 > 导航条白色主题只有在 ios7 才需要设置。
   
2 > 设置导航条上的 UIBarButton 背景 , 只有在 ios6 才需要设置
   
3 > UIBarButton UIBarButtonItem 决定。
   
4 > 获取整个应用程序的 UIBarButtonItem ,设置整个应用程序的 UIBarButton 。避免一个控制器一个控制器的设置
   
5 > UIBarButtonItem setBackgroundImage  // 设置按钮背景
   
6 > UIBarButtonItem setBackButtonBackgroundImage // 设置返回按钮背景


/* 彩票第二天 */
1 > 搭建设置界面分析
   
1 > 静态单元格 : 一个 cell 一个 cell 的改,太麻烦,而且不灵活
   
2 > plist 文件 : 配置 plist 文件太费时间

2 > 自定义设置控制器 ( 代码跳转 )
   
1 > group 样式
   
2 > 分析数据结构 : 大数组里面存放两个小数组,小数组存放每一行的模型
   
3 > 实现数据源方法
    *
大数组:告诉 tableView 有多少组 tableView:numberOfSectionsInTableView:
    *
小数组 : 告诉 tableView 每一组有多少行 tableView:numberOfRowsInSection:
    *
小数组里存:每一行长什么样 tableView:cellForRowAtIndexPath:
3 > 自定义 cell 模型 ,ILSettingItem(title,icon)
   
1 > 运用模型,展示 tableView 数据

4 > tableView 里面的所有显示都交给模型去管理 ? 怎么做
   
1 > 自定义组模型, ILSettingGroup(header,footer,items): 每一组有头部标题和尾部标题和有多少行 cell

5 > 模型差不多设计好了,该封装视图了。设计步骤:先设计模型,在封装视图。因为视图是根据模型展示的。
   
1 > 自定义 cell ,传一个模型,就展示数据。
   
2 > accessoryView: 由模型决定。 tableView 上的所有显示,由模型决定。
   
3 > item 模型添加一个枚举。不够面向对象,应该把每一个 cell 的类型都对应一个模型,因为不同的 cell 类型不同的操作。箭头的 cell 一般需要跳转,开关的不需要跳转。箭头应该比开关多添加一个属性,跳转的控制器类型 Class
   
4 > 自定义箭头模型 (ILSettingArrowItem) ,继承 ILSettingItem ,添加一个跳转的控制器的属性 , 并提供一个类方法
       
1 > Class assign 因为不是都系类型,不需要管理内存在的问题
       
2 > 为什么用 Class, 因为 Class 写错类型就会报错。
   
5 > 自定义开关模型 (ILSettingSwitchItem) ,继承 ILSettingItem

6 > 设置 cell accessoryView
   
1 > 完善 tableView 模型,弄真实数据。
   
2 > 在重写 set 模型的方法里,根据 item 的类型判断 cell 上显示什么样的 accessoryView
   
3 > cell 懒加载 UIImageView UISwitch, 注意用 strong, 否则会被销毁,没有其他视图强引用他,没有 addSubviews
   
4 > 总结:只要没有 add 的控件,都需要强引用

7 > 完善 cell 的跳转功能
   
1 > 点击 cell 就跳转
   
2 > 实现 tableView 代理方法 didSelectRowAtIndexPath
       
1. 根据模型判断是否需要跳转
       
2. 是否有 destVcClass 属性
       
3. 通过类名创建控制器对象,跳转。 [[arrowItem.destVcClass alloc] init];


8 > 检查新版本 cell( 完善 cell 操作功能 )
   
1 > 点击更新 cell ,做一些事情,而不是跳转,怎么做 ?
   
2 > 最蠢的办法根据角标去判断,点击了哪一行
   
3 > 更新操作交给模型去管理。让模型保存一个功能,功能及代码。
   
4 > 怎么保存代码 ? ILSettingItem 添加一个 block 属性,用 block 保存一段代码 .
   
5 > 每一行 cell 应该都会有操作,因此给 ILSettingItem 添加 block 属性,这样子类都有这个 block 属性
   
6 > 完善更新模型
       
1. 思路:只有服务器才知道是否有最新数据,因此需要发送网络请求
       
2. 更新功能步骤 : 发送网络请求 ( 当前手机版本 ) -> 服务器返回数据 ( 是否需要更新 ) -> 弹框提示用户。
       
3. 如果需要更新跳到 appstory 更新
   
7 > 点击 cell 的时候调用 block
   
8 > 更新 cell 一直选中状态,应该点击一行的时候,立即取消

9 > 产品推荐 (UICollectionViewController)
   
1 > 使用 UICollectionViewController ,跳入头文件,发现和 UITableViewController 一样,有数据源和代理
   
2 > UITableView 每一行是 UITableViewCell,UICollectionView 每一个是 UICollectionViewCell
   
2 > 实现数据源,
        * numberOfSectionsInCollectionView
返回 UICollectionView 有多少组
        * numberOfItemsInSection
返回一组多少个
        * cellForItemAtIndexPath 
返回一个 cell 长什么样
   
3 > 解释 section,item, 循环利用。 section :哪一组   item :哪一个
   
4 > 怎么使用 UICollectionViewCell? 必须先注册, init 方法没有提供标识符的构造方法
   
5 > 注册 cell ,在 viewDidLoad 注册一次
   
6 > 必须传入布局,告诉他怎么布局。这么多格子,他怎么知道怎么布局啊。
   
7 > 使用流水布局 UICollectionViewFlowLayout , 封装到控制器里面
   
8 > 怎么设置 UICollectionViewCell 的尺寸和位置,通过 layout 布局设置

10 > 完成产品推荐 ( 分析产品 json 数据 ) 以后的思路都是这样的,
   
思路:解析数据,转换模型,描述界面,传递模型给界面,展示到视图。
   
1 > 解析 json 数据 ,json 最外面是 [] ,表示这是个 json 数组,解析出来也是数组
   
2 > 创建模型 , 提供类方法,不能用 KVC id 比较特殊
   
3 > 自定义 cell, 传递模型
   
4 > 注册 xib cell
   
5 > 设置 cell UIImageView 的圆角属性,设置 cell 的尺寸。
   
6 > 监听点击
   
7 > 导航条的标题:在 push 之前的时候就设置,拿到模型的 title 直接设置 vc.title = arrowItem.title;

10 > 推送和提醒模块 ( 抽取父控制器 )
   
1 > 分析界面外观:跟设置界面一样的 cell, 只需要给 cell 传递一个模型,就自动生成一个界面了。
   
2 > 配置模型
   
3 > 抽取父控制器 ILBaseTableViewController
   
4 > 配置中奖提醒,中奖动画,比分直播 (ILAwardPushViewController,ILAwardAnimationViewController,ILScorNoticeViewController)
   
5 > ILScorNoticeViewController 控制器比较特殊, cell 右边有 label
   
6 > 根据模型,显示 cell
   
7 > 自定义 ILSettingLabelItem ,添加 text 属性,用于显示 label 文字
   
8 > 修改 ILSettingCell ,根据模型,判断是否懒加载 UILabel,label 必须设置尺寸
   
9 > 配置比分直播的模型

11 > 比分直播 label 处理
   
1 > 从下往上钻的是什么?键盘才有这样的效果,也就是点击 label 弹出键盘
   
2 > 什么东西能弹出键盘 ?textField 成为第一响应者
   
3 > 创建一个 textField ,不需要显示,目的就是弹出键盘
   
4 > 修改键盘 inputView UIDatePicker
        *
设置 UIDatePicker 的默认时间
           
// 日期格式对象
            NSDateFormatter *fmt = [[NSDateFormatter alloc] init];
            fmt.dateFormat =
@"HH:mm" ;
           
// 字符串转日期
            NSDate *date = [fmt dateFromString:_startItem.text];
            _datePicker.date = date;

        * UIDatePicker
的模式
           
// 模式
            _datePicker.datePickerMode = UIDatePickerModeTime;

        * UIDatePicker
的地区
           
// 地区
            _datePicker.locale = [NSLocale localeWithLocaleIdentifier:
@"zh_CN" ];
   
5 > 监听 UIDatePicker 的滚动,改变 ILSettingLabelItem 的值
        *
日期转字符串
            NSDateFormatter *fmt = [[NSDateFormatter alloc] init];
            fmt.dateFormat =
@"HH:mm" ;

            _startItem.text = [fmt stringFromDate:datePicker.date];
   
6 > 刷新表格,更新界面

12 > 数据存储
   
1 > 存储 cell accessoryView 的状态,用 [NSUserDefaults standardUserDefaults] 快速存储,别忘记同步 synchronize
   
2 > ILSettingLabelItem text
        *
重写模型 setText 方法,在设置的 text 的时候就存储。
        * key:
用模型的 title 属性,目的知道是哪个 cell 存储了,每个 cell 都有 title
   
3 > ILSettingSwitchItem 开关的状态
        *
监听 switch 的改变
        *
给模型添加一个属性,开关属性 off
        *
重写 setOff 方法,设置的时候就存储
   
4 > 怎么读取,重写两个模型的 setTitle 方法,在设置 title 的时候就读取一次,给对应的属性赋值。
            * ILSettingLabelItem
存储代码
            - (
void )setTitle:(NSString *)title
            {
               
// 这里不能拿到 _title 赋值,只能调用父类的 set 方法赋值
                [
super setTitle:title];
               
                _text = [ILSettingTool objectForKey:
self .title];
               
            }
            - (
void )setTitle:(NSString *)title
            {
               
// 这里不能拿到 _title 赋值,只能调用父类的 set 方法赋值
                [
super setTitle:title];
               
                _off = [ILSettingTool boolForKey:
self .title];
               
            }

            * ILSettingSwitchItem
存储代码
                - (
void )setOff:( BOOL )off
                {
                    _off = off;
                   
                    [ILSettingTool setBool:off forKey:
self .title];
                }

                - (
void )setTitle:(NSString *)title
                {
                   
// 这里不能拿到 _title 赋值,只能调用父类的 set 方法赋值
                    [
super setTitle:title];
                   
                    _off = [ILSettingTool boolForKey:
self .title];
                   
                }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值