iOS开发规范
项目主体架构
企业微信截图_9a1e4b28-1533-4633-aeaa-ef3b866e3e97.png公共类
企业微信截图_3c88564b-cf76-450b-988a-5851aed1479d.png资源文件类
企业微信截图_5ec8310b-dac8-4fbb-966a-eab2fb5ac5c3.png我们的VC 也就是Src
企业微信截图_42a428af-6f6f-4a88-a4b7-998c39c18a2b.png以城市列表视图控制器cityViewController为例
这也是我们MVVM缩影
企业微信截图_ba26dbf5-e649-4cfd-bcfc-b0266ac8efed.png具体的内容分布
企业微信截图_01dac792-d944-474f-8b25-94542fc04856.png还有首页(这里面多了一些布局Layout文件和DataSource文件)
企业微信截图_9a3158a8-4cfd-4463-92a3-1ba114d84f61.png各种类设计
说明:TF属于封装在底层TFUILib_iOS通过pod管理
VC基类 = TFViewController , View基类 = TFView 等等
中间类如 CXViewController、 CXTableViewController、CXView、CXModel、CXViewModel等这些放在公共(Common目录里面)
WeChat9769acdb3131f9202dfe32d80a351b9a.png
1.1 ViewController设计(这里 “->” 代表继承)
1) VC(列表需要tableview) -> CXTableViewController -> TFTableViewController -> TFViewController(基类VC)
2) VC(普通VC) -> TFViewController
TFViewController 设计:定义viewModel,控制器结果回调(TFViewControllerResultBlock)
WeChatc66ba9e8ccd8abba43fcfe25ed35032a.png
TFTableViewController 设计: 定义tableview样式、 HeaderView、FooterView、headerViewHeight、footerViewHeight,以及上下拉刷新
WeChat16f36a30554c1c1eaaeb08b4e6e816cf.png
CXTableViewController 设计:定义 初始化视图、自动布局视图、绑定数据方法
- (void)initViews;
- (void)autolayoutViews;
- (void)bindData;
1.2 自定义View设计
1)自定义View -> CXView -> TFView
TFView 设计:定义 从XIB获取视图、 初始化视图、自动布局视图、绑定数据等方法
+ (id)loadViewFromXib;
- (void)initViews;
- (void)autolayoutViews;
- (void)bindData;
CXView设计: 暂定
1.3 Model设计
1) 业务model -> CXModel -> TFModel
2) 一些公共字段model -> CXActionModel(所有列表项模型的基类)-> TFModel
WeChatd521d32155efbff572e5e53757c7bba1.png
1.4 ViewModel设计
如:HomeViewModel -> CXViewModel -> TFViewModel()
这里先以常用的四种类为例
缓存设计 (通过url缓存对应的接口数据)
说明:把有需要缓存的接口放在plist文件管理
WeChat33bc434bec12ca86aaae54bee8efc035.png
WeChat3f54eded8ea3f5bd3f871b24736976bd.png
1 命名规范
1.大驼峰规则:每个单词的首字母大写。例:NameTextField。
2.小驼峰原则:第一个单词首字母小写,其余都大写。例:nameTextField。
1.1 变量和方法
变量和方法的命名都遵循小驼峰命名。
- 变量:myName,
- 方法 -(void)myNameClick响应事件。
1.2 常量
宏:大写 + “_”, 如:
#define COLOR_RED_NORMAL HEXCOLOR(0XFF5555, 1)
#define COLOR_RED_HIGHLIGHT HEXCOLOR(0XE23438, 1)
#define COLOR_RED_DISABLE HEXCOLOR(0XFFD2D2, 1)
全局常量:工程前+缀全大写,下划线隔开 即为:
const NSString YH_USER_AGE_KEY = @"user_age_key"
1.3 参数名
参数名以小驼峰命名,尽量参考苹果原生方法风格编写。尽量可读性好,看到方法名就知道这个方法是用来干什么的。参数应该避免用单个字符命名。例:
- (void)setDataImageUrl:(NSString *)imageUrl name:(NSString *)nameStr content:(NSString *)contentStr
1.4 资源文件命名
App 里的拥有 4 种属性,分別为一般、点击、不能点击、选中。 _selected _highlight _disabled,一般提供普通状态 不带后缀 全部小写,采用下划线命名法,加前缀区分
1. icon icon_xxx.png
2. 导航栏 nav_xxx.png。
3. 标签栏 tab_xxx.png tab_xxx_selected.png。
按钮
btn_xxx.png
btn_xxx_selected.png
btn_xxx_highlight.png
btn_xxx_disabled.png
背景图
bg_xxx.png bg_xxx_selected.png
1.5 类名
1.类名用大写字母开头的单词组合而成(大驼峰规则)
所有的类名,接口名(Protocol)均以大写字母开头,多单词组合时,后面的单词首字母大写。类,接口名必须是有意义的。
2. 类名必须符合规范
继承自UIView的类以View结尾。其他类似。
继承自ViewController的类以viewController结尾。
所有保存数据的实体以Model结尾。
2 注释规范
1.1 类
类明注释当前类用途
11606121082_.pic.jpg1.2 方法注释
方法注释,方法外部统一用option + command + /,方法内部统一用//注释。
31606121737_.pic.jpg
1.3 类属性,模型等注释
用///注释
21606121462_.pic_hd.jpg
3 书写规则
1 建议使用“#pragma mark”,方便阅读代码
2 不要把过多逻辑写在viewDidLoad
3 方法当参数过长时,每个参数占用一行,以冒号对齐
4 如果类声明中包含多个protocal,每个protocal占用一行,缩进2个字符
5 相关的赋值语句等号对齐。如:
tPDBRes.wHead = 0;
tPDBRes.wTail = wMaxNumOfPDB - 1;
tPDBRes.wFree = wMaxNumOfPDB;
tPDBRes.wAddress = wPDBAddr;
tPDBRes.wSize = wPDBSize;
6 多元运算符和它们的操作数之间至少需要一个空格,如:
fValue = fOldValue;
fTotal + fValue
iNumber += 2;
7 关键字之后要留空格。
说明:if、for、while等关键字之后应留一个空格再跟左括号‘(’,以突出关键字。
8 函数名之后不要留空格。
9 方法名与形参不能留空格,返回类型与方法标识符有一个空格。如:
- (BOOL)shouldAutorotateToInterfaceOrientation:(UIInterfaceOrientation)interfaceOrientation
{
return YES;
}
10 注释符与注释内容之间要用一个空格进行分隔如:/* 注释内容 */ // 注释内容 反例:/*注释内容*/ //注释内容
11 宏定义中如果包含表达式或变量,表达式和变量必须用小括号括起来。(括号,可以避免可能发生的计算错误。)
#define HANDLE(A, B) (( A ) / ( B ))
12 宏常量要指定类型。不同的编译器,默认类型不一样。 #define BUTTON_WIDTH (int)320
13 应当将指针变量用“==”或“!=”与nil比较
if (pHead == nil) // pHead与NULL显式比较,强调pHead是指针变量
if (pHead != nil)
反例:
if (pHead == 0) // 容易让人误解pHead是整型变量
if (pHead) // 容易让人误解pHead是布尔变量
4 内存使用
1. 防止内存操作越界
说明:内存操作主要是指对数组、指针、内存地址等的操作,内存操作越界是软件系统主要错误之一,后果往往非常严重,所以当我们进行这些操作时一定要仔细。
2. 必须对动态申请的内存做有效性检查,并进行初始化;动态内存的释放必须和分配成对以防止内存泄漏,释放后内存指针置为nil。
3. 变量在使用前应初始化,防止未经初始化的变量被引用。
不同的编译系统,定义的变量在初始化前其值是不确定的。有些系统会初始化为0,而有些不是。
5 其它补充
1.避免过多直接使用立即数。如:
ViewBounds.size.height = VIEW_BOUNDS_HEIGHT;
反例:
ViewBounds.size.height = 150;
6 文件布局
1. 遵循统一的顺序来书写类的实现。
说明:以下内容如果某些节不需要,可以忽略。但是其它节要保持该次序。
实现文件布局:
#pragma mark – init
#pragma mark - View lifecycle
#pragma mark – Notification
#pragma mark – Delegate
#pragma mark - 按钮事件
#pragma mark – 自定义方法
#pragma mark – get set方法
2. 每个功能块放入一个Group,在目录里建立实际文件夹管理,不能虚拟目录
View
ViewController
Model
ViewModel
3. 建立Library文件夹,所有第三方库放入其中
4. 建立Common文件夹,所有模块公用的放入其中
5. 建立Resources文件夹,资源文件放入其中
6. 引入其它类时,若要作为实例变量的在.h中引入。否则在.m中引入。
a:声明实例变量一律以属性声明。
b:其它类要访问的实例变量和方法在.h文件中声明,否则声明于.m文件中。
c:实例变量及方法以功能块放在一起,实现一个功能的连续着放在一起,另一个功能的空一行开始声明。
最后举例
#import "ViewController.h"
#define HEIGHT_HEADER_ALL H(250) // 顶部总高
#define HEIGHT_SECTION_ORDER H(115) // 我的订单
#define HEIGHT_SECTION_NOR H(68) // 其他服务
@interface PersonalCenterViewController ()
/// 文本按钮
@property (nonatomic, strong)UIButton * textBtn;
@end
@implementation PersonalCenterViewController
#pragma mark - life cycle
- (void)viewDidLoad {
[super viewDidLoad];
@weakify(self);
// 刷新消息红点
[RACObserve(kCXCacheManager, hasNewMessage) subscribeNext:^(NSNumber *hasNewMessage) {
@strongify(self);
self.narView.showMessageBadgeView = hasNewMessage.boolValue;
}];
[self.view addSubview:self.textBtn];
}
#pragma mark - UITableViewDelegate && UITableViewDataSource
//(代理顺序往下排列)
#pragma mark UIScrollViewDelegate
#pragma mark - 按钮事件
- (void)textBtnClick{
}
#pragma mark 自定义方法
-(void)gotoNextController {
}
- (void)_privateMethod {
}
#pragma mark - getters and setters
- (UIButton *)textBtn
{
if (_textBtn == nil) {
_textBtn = [UIButton buttonWithType:UIButtonTypeCustom];
_textBtn.frame = CGRectMake(300, 250, 100, 100);
_textBtn.backgroundColor = [UIColor yellowColor];
_textBtn.titleLabel.text = @"text";
[_textBtn addTarget:self action:@selector(textBtnClick) forControlEvents:UIControlEventTouchUpInside];
}
return _textBtn;
}
@end
网友评论