需求
1.以N宫格的形式展示应用信息
2.APP信息包括图标、名字、下载按钮
3.使用尽可能少的代码,从plist读取app信息,计算每个app图标的位置尺寸信息
 
 
A.思路
1.UI布局:N宫格
2.事件监听
3.动态添加 (by plist)
4.整体封装,组合每个应用信息,使用View的层级包装帮助布局
 
B.实现 (使用纯代码方式)
 
  1 //
2 // ViewController.m
3 // 01-应用管理
4 //
5 // Created by hellovoidworld on 14/11/24.
6 // Copyright (c) 2014年 hellovoidworld. All rights reserved.
7 //
8
9 #import "ViewController.h"
10
11 #define APP_WIDTH 85
12 #define APP_HEIGHT 90
13 #define MARGIN_HEAD 20
14 #define ICON_WIDTH 50
15 #define ICON_HEIGHT 50
16 #define NAME_WIDTH APP_WIDTH
17 #define NAME_HEIGHT 20
18 #define DOWNLOAD_WIDTH (APP_WIDTH - 20)
19 #define DOWNLOAD_HEIGHT 20
20
21 @interface ViewController ()
22
23 /** 存放应用信息 */
24 @property(nonatomic, strong) NSArray *apps; // 应用列表
25
26 @end
27
28 @implementation ViewController
29
30 - (void)viewDidLoad {
31 [super viewDidLoad];
32 // Do any additional setup after loading the view, typically from a nib.
33
34 [self loadApps];
35 }
36
37 - (void)didReceiveMemoryWarning {
38 [super didReceiveMemoryWarning];
39 // Dispose of any resources that can be recreated.
40 }
41
42 #pragma mark 取得应用列表
43 - (NSArray *) apps {
44 if (nil == _apps) {
45 NSString *path = [[NSBundle mainBundle] pathForResource:@"app.plist" ofType:nil];
46 _apps = [NSArray arrayWithContentsOfFile:path];
47 }
48
49 return _apps;
50 }
51
52 #pragma mark 加载全部应用列表
53 - (void) loadApps {
54 int appColumnCount = [self appColumnCount];
55 int appRowCount = [self appRowCount];
56
57 CGFloat marginX = (self.view.frame.size.width - APP_WIDTH * appColumnCount) / (appColumnCount + 1);
58 CGFloat marginY = (self.view.frame.size.height - APP_HEIGHT * appRowCount) / (appRowCount + 1) + MARGIN_HEAD;
59
60 int column = 0;
61 int row = 0;
62 for (int index=0; index<self.apps.count; index++) {
63 NSDictionary *appData = self.apps[index];
64
65 // 每个app信息
66 UIView *appView = [[UIView alloc] init];
67
68 CGFloat appX = marginX + column * (marginX + APP_WIDTH);
69 CGFloat appY = marginY + row * (marginY + APP_HEIGHT);
70
71 appView.frame = CGRectMake(appX, appY, APP_WIDTH, APP_HEIGHT);
72
73 // 1.设置APP图片
74 UIImageView *iconView = [[UIImageView alloc] init];
75
76 CGFloat iconMarginX = (appView.frame.size.width - ICON_WIDTH) / 2;
77 CGFloat iconMarginY = 0;
78 iconView.frame = CGRectMake(iconMarginX, iconMarginY, ICON_WIDTH, ICON_HEIGHT);
79
80 iconView.image = [UIImage imageNamed:appData[@"icon"]];
81 [appView addSubview:iconView];
82
83 // 2.设置APP名字
84 UILabel *nameLabel = [[UILabel alloc] init];
85 nameLabel.text = appData[@"name"];
86 CGFloat nameMarginX = (appView.frame.size.width - NAME_WIDTH) / 2;
87 CGFloat nameMarginY = iconMarginY + ICON_HEIGHT;
88 nameLabel.frame = CGRectMake(nameMarginX, nameMarginY, NAME_WIDTH, NAME_HEIGHT);
89 [nameLabel setFont:[UIFont systemFontOfSize:16]];
90 [nameLabel setTextAlignment:NSTextAlignmentCenter];
91 [appView addSubview:nameLabel];
92
93 // 3.设置下载按钮
94 UIButton *downloadButton = [UIButton buttonWithType:UIButtonTypeCustom];
95 CGFloat downloadMarginX = (appView.frame.size.width - DOWNLOAD_WIDTH) / 2;
96 CGFloat downloadMarginY = nameMarginY + NAME_HEIGHT;
97 downloadButton.frame = CGRectMake(downloadMarginX, downloadMarginY, DOWNLOAD_WIDTH, DOWNLOAD_HEIGHT);
98
99 UIImage *downloadNormalImage = [UIImage imageNamed:@"buttongreen"];
100 [downloadButton setBackgroundImage:downloadNormalImage forState:UIControlStateNormal];
101
102 UIImage *downloadHighlightedImage = [UIImage imageNamed:@"buttongreen_highlighted"];
103 [downloadButton setBackgroundImage:downloadHighlightedImage forState:UIControlStateHighlighted];
104
105 [downloadButton setTitle:@"下载" forState:UIControlStateNormal];
106
107 // 不要直接取出titleLabel属性进行操作,因为这样就不能为全部状态进行设置
108 [downloadButton.titleLabel setFont:[UIFont systemFontOfSize:13]];
109
110 [appView addSubview:downloadButton];
111
112
113 [self.view addSubview:appView];
114
115 column++;
116 if (column == appColumnCount) {
117 column = 0;
118 row++;
119 }
120 }
121 }
122
123 #pragma mark 计算列数
124 - (int) appColumnCount {
125 int count = 0;
126 count = self.view.frame.size.width / APP_WIDTH;
127
128 if ((int)self.view.frame.size.width % (int)APP_WIDTH == 0) {
129 count--;
130 }
131
132 return count;
133 }
134
135 #pragma mark 计算行数
136 - (int) appRowCount {
137 int count = 0;
138 count = (self.view.frame.size.height - MARGIN_HEAD) / APP_HEIGHT;
139
140 if ((int)(self.view.frame.size.height - MARGIN_HEAD) % (int)APP_HEIGHT == 0) {
141 count--;
142 }
143
144 return count;
145 }
146 @end
#1. 放入了Images.xcassets中的文件只能通过[UIImage imageNamed:(NSString *) imageName] 访问吗?

[iOS基础控件 - 4.1] APP列表的更多相关文章

  1. [iOS基础控件 - 4.2] APP列表 字典转模型Model

    A.使用字典加载数据的缺点 1.用户自行指定key,容易出错 2.存入.取出都需要key,容易混乱   B.模型 (MVC中的model) 1.字典与模型对比: (1)字典:存储数据,通过字符串类型的 ...

  2. [iOS基础控件 - 4.3] APP列表 xib的使用

    A.storyboard和xib 1.storyboard: 相对xib较重量级,控制整个应用的所有界面 2.xib: 轻量级,一般用来描述局部界面   B.使用 1.新建xib文件 New File ...

  3. [iOS基础控件 - 5.5] 代理设计模式 (基于”APP列表"练习)

    A.概述      在"[iOS基础控件 - 4.4] APP列表 进一步封装,初见MVC模式”上进一步改进,给“下载”按钮加上效果.功能      1.按钮点击后,显示为“已下载”,并且不 ...

  4. [iOS基础控件 - 4.4] 进一步封装"APP列表”,初见MVC模式

    A.从ViewController分离View 之前的代码中,View的数据加载逻辑放在了总的ViewController中,增加了耦合性,应该对控制器ViewController隐藏数据加载到Vie ...

  5. [iOS基础控件 - 6.9.3] QQ好友列表Demo TableView

    A.需求 1.使用plist数据,展示类似QQ好友列表的分组.组内成员显示缩进功能 2.组名使用Header,展示箭头图标.组名.组内人数和上线人数 3.点击组名,伸展.缩回好友组   code so ...

  6. [iOS基础控件 - 6.1] 汽车品牌列表 UITableView多项显示

    A.实现思路 1.拖入UITableView 2.拖曳.连线UITableView控件 3.Controller遵守UITalbeViewDataSource协议 4.设置UITableView的da ...

  7. [iOS基础控件 - 6.11.3] 私人通讯录Demo 控制器的数据传递、存储

    A.需求 1.搭建一个"私人通讯录"Demo 2.模拟登陆界面 账号 密码 记住密码开关 自动登陆开关 登陆按钮 3.退出注销 4.增删改查 5.恢复数据(取消修改)   这个代码 ...

  8. iOS 基础控件(下)

    上篇介绍了UIButton.UILabel.UIImageView和UITextField,这篇就简短一点介绍UIScrollView和UIAlertView. UIScrollView 顾名思义也知 ...

  9. [iOS基础控件 - 5.4] 广告分页代码(UIScrollView制作)

    A.概念 例子就是桌面的APP列表,当APP数量超过一个屏幕,自动进行分页   B.实现思路 1.创建一个UIScrollView,这里设置为宽度跟屏幕相同,高度1/4屏幕高度左右 2.使用代码在UI ...

随机推荐

  1. FileZilla Server 防火墙端口开启设置 windows 2008 win

    入站规则 添加21端口, 程序FileZilla server.exe 出站规则 %SystemRoot%\System32\ftp.exe

  2. java:比较对象

    对象内容相等条件:1.对象类型相同(可用instanceof操作符比较)2.对象的成员变量的值完全相同 instanceof 判断对象类型 //a是否为Child对象类型 boolean b = a ...

  3. linux netcat命令

    netcat是网络工具中的“瑞士军刀”,它能通过TCP和UDP在网络中读写数据.通过与其他工具结合和重定向,你可以在脚本中以多种方式使用它.使用netcat命令所能完成的事情令人惊讶. netcat所 ...

  4. C++中const小结

    1.const修饰普通变量(非指针变量)const修饰变量,一般有两种写法:const TYPE value;TYPE const value;对于一个非指针的类型TYPE,这两种写法在本质上是一样的 ...

  5. J2EE中你必须了解的13种技术规范

    1)JDBC(Java Database Connectivity): JDBC API为访问不同的数据库提供了一种统一的途径,象ODBC一样,JDBC对开发者屏蔽了一些细节问题,另外,JDCB对数据 ...

  6. [原]Unity3D深入浅出 - 认识开发环境中的自带的Package资源包

    Character Controller:角色控制器 Glass Refraction(pro only):玻璃反射资源包 Image Effects :图像效果资源包 Light Cookies:光 ...

  7. Vim Vundle 插件管理器

    /********************************************************************** * Vim Vundle 插件管理器 * 说明: * 话 ...

  8. vim 退出保留显示的内容

    /*************************************************************************** * vim 退出保留显示的内容 * 声明: * ...

  9. 【转】1.5 起步 - 初次运行 Git 前的配置

    原文网址:http://git-scm.com/book/zh/v1/%E8%B5%B7%E6%AD%A5-%E5%88%9D%E6%AC%A1%E8%BF%90%E8%A1%8C-Git-%E5%8 ...

  10. jQuery.Validate验证库

    一.用前必备官方网站:http://bassistance.de/jquery-plugins/jquery-plugin-validation/ API: http://jquery.bassist ...