Vary's Blog

Android 开发规范

为了利于项目维护以及规范开发,促进成员之间Code Review的效率,故提出以下开发规范,如有更好建议,欢迎提出

另外,BoilerPlate 是一个很好的参考材料和学习项目,你对MVP架构会有一个新的认识。

1 Android Studio规范

  • 尽量使用最新版本的Android Studio开发
  • 编码格式统一为UTF-8
  • 编辑完.java.xml等文件后一定要格式化,一定要格式化,一定要格式化,格式使用IDE默认模板即可(快捷键:Ctrl+Alt+L)
  • 删除多余的import,减少警告出现,可利用IDE的Optimize Imports自动优化(Settings → Keymap → Optimize Imports)
  • Android Studio 常用开发插件可以参考这里~Android Studio插件整理

2 命名规范

代码中的命名严禁使用拼音与英文混合的方式,更不允许直接使用中文的方式。正确的英文拼写和语法可以让阅读者易于理解,避免歧义。

注意:即使纯拼音命名方式也要避免采用。但alibabataobaoyoukuzhihu等国际通用的名称,可视同英文。

2.1 包命名规范

  • 包名全部小写,连续的单词只是简单地连接起来,不使用下划线,采用反域名命名规则,全部使用小写字母。
  • 包名的划分,尽量使用按功能模块的划分方式。按照功能模块划分可能你不是很好区分应该划分在哪个功能中,不过也比你按照层区划分要好找很多。具体可以参考这篇博文~Package by features, not layers
  • 通用功能子包名采用[主包名].[通用名称]的命名方式常见通用功能如下表:
包名 包下的类工作划分
base 基类相关
utils 通用工具类
event 事件载体类(EventBus事件对象)
rx RxJava相关帮助类
pref 用户设置、全局配置、常量等
bean 数据载体类,javaBean
domain model层,业务逻辑
data model层,数据操作、数据提供,等数据相关类
presentation 视图层,包含View层和Present层。如:Activity、Fragment、Presenter
  • 一般功能子包名采用[主包名].[模块名称].[子模块名称]的命名方式,例如:
模块 包名
网络相关 [主包名].data.net
登录模块 [主包名].presentation.login
我的模块 [主包名].presentation.mine
  • 只需导入用到的类,千万不能用 * 导入包下所有类

2.2 Class files 类命名规范

类命名方式采用 大驼峰 命名法。尽量避免缩写,除非该缩写是众所周知的。

对于继承自安卓组件的类来说,类名应该以该组件名结尾,例如 : SignInActivity, SignInFragment, ImageUploaderService, ChangePasswordDialog.
对于工具类来说,命名方式应该以其完成功能开始,以 Utils 结束 ,例如 :HttpUtils , ImageUtils

2.3 Resources files 资源文件命名规范

全部小写,采用下划线命名法,加前缀区分

Layout files

布局文件的命名需要与他所嵌入的安卓组件匹配,但是将组件名称前移到开始处,例如,我们要创建一个名字为 SignInActivity, 其名字应该为 activity_sign_in.xml.

Component 组件 Class Name Layout Name
Activity UserProfileActivity activity_user_profile.xml
Fragment SignUpFragment fragment_sign_up.xml
Dialog ChangePasswordDialog dialog_change_password.xml
ListView Item list_item_person.xml
GridView Item grid_item_person.xml

Drawable files

  • drawable 文件的命名规范
Asset Type Prefix 前缀 Example
Action bar ab_ ab_stacked.9.png
Button btn_ btn_send_pressed.9.png
Dialog dialog_ dialog_top.9.png
Divider divider_ divider_horizontal.9.png
Icon ic_ ic_star.png
Menu menu_ menu_submenu_bg.9.png
Notification notification_ notification_bg.9.png
Tabs tab_ tab_pressed.9.png
  • icons文件的命名规范
Asset Type Prefix 前缀 Example
Icons ic_ ic_star.png
Launcher icons ic_launcher ic_launcher_calendar.png
Menu icons and Action Bar icons ic_menu ic_menu_archive.png
Status bar icons ic_stat_notify ic_stat_notify_msg.png
Tab icons ic_tab ic_tab_recent.png
Dialog icons ic_dialog ic_dialog_info.png
  • 选择器状态文件的命名规范
State Suffix 尾缀 Example
Normal _normal btn_order_normal.9.png
Pressed _pressed btn_order_pressed.9.png
Focused _focused btn_order_focused.9.png
Disabled _disabled btn_order_disabled.9.png
Selected _selected btn_order_selected.9.png

注意:使用AndroidStudio的插件SelectorChapek可以快速生成selector,前提是命名要规范。

2.4 Inside Code Naming 代码内部命名

2.4.1 常量名

常量名命名模式为CONSTANT_CASE全部字母大写,用下划线分隔单词。那到底什么算是一个常量?

每个常量都是一个静态final字段,但不是所有静态final字段都是常量。在决定一个字段是否是一个常量时,考虑它是否真的感觉像是一个常量。例如,如果任何一个该实例的观测状态是可变的,则它几乎肯定不会是一个常量。只是永远不打算改变对象一般是不够的,它要真的一直不变才能将它示为常量。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
// Constants
static final int NUMBER = 5;
static final ImmutableListNAMES = ImmutableList.of("Ed", "Ann");
static final Joiner COMMA_JOINER = Joiner.on(','); // because Joiner is immutable
static final SomeMutableType[] EMPTY_ARRAY = {};
enum SomeEnum { ENUM_CONSTANT }
// Not constants
static String nonFinal = "non-final";
final String nonStatic = "non-static";
static final Set mutableCollection = new HashSet();
static final ImmutableSet mutableElements = ImmutableSet.of(mutable);
static final Logger logger = Logger.getLogger(MyClass.getName());
static final String[] nonEmptyArray = {"these", "can", "change"};

2.4.2 Class Variable Naming 类变量命名

  • 公有变量按 小驼峰 法命名
  • 私有 & 非静态成员变量以 m 开头
  • 私有 & 静态成员变量以 s 开头
  • 常量以大写字母和下划线 _ 组成
  • 尽量使用 功能/描述 + 类型 的模式 ,如 mNameTextView
  • 类中变量的组件类型请不要使用缩写
  • 自定义异常必须以Exception结尾
  • 注意不要使用 aa bb cc3 这种变态的命名方式 !!
  • 除for循环变量外,一律不得使用i、j、k等单字符作为变量名
  • 类变量过多时请 分块摆放 并且 写好注释
  • 接口类 请直接定义在类的最后

Example:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
public class MyClass {
//静态常量
public static final int SOME_CONSTANT = 42;
//公有变量
public int publicField;
//私有静态变量
private static MyClass sSingleton;
//默认变量
int mPackagePrivate;
//私有变量
private int mPrivate;
//继承型变量
protected int mProtected;
}

注意:如果项目中使用ButterKnife,则不添加m前缀,以小驼峰风格命名。

2.4.3 Class Method Naming 类方法命名

  • 类方法采用 小驼峰 命名法
  • 根据函数所完成功能命名 , 如 changView()
  • 在函数头写对于函数功能、参数和返回值的注释,如:

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    /**
    * 获取两个数中最大的一个
    *
    * @param value1 参与比较的第一个数
    * @param value2 参与比较的第二个数
    * @return 两个参数中最大的一个数
    */
    public int max(int value1, int value2) {
    return (value1 > value2) ? value1 : value2;
    }
  • 一个函数请尽量保持在 50行 之内 !!

2.4.4 layout.xml 布局文件变量命名

  • id 以 类型命名所在组件 的模式,例如: @+id/tv_name_main@id/btn_send_chat,多数情况 _所在模块可省略,如:@id/btn_send
  • 布局多处重用的请使用 <include> 标签
  • 所有文本请定义在 strings.xml 中 , 如 @string/app_name
  • 重用dp请定义在 dimens.xml 中 , 如 @dimen/entry_item_height
Component 组件 Abbreviation 缩写
ListView lv
TextView tv
ImageView iv
Button btn
EditText et
LinearLayout ll
ReleativeLayout rl
ViewPager vp

2.4.5 colors.xml

colorsname命名使用下划线命名法,在你的colors.xml文件中应该只是映射颜色的名称一个ARGB值,而没有其它的。不要使用它为不同的按钮来定义ARGB值。

不要这样做

1
2
3
4
5
6
7
8
9
10
<resources>
<color name="button_foreground">#FFFFFF</color>
<color name="button_background">#2A91BD</color>
<color name="comment_background_inactive">#5F5F5F</color>
<color name="comment_background_active">#939393</color>
<color name="comment_foreground">#FFFFFF</color>
<color name="comment_foreground_important">#FF9D2F</color>
...
<color name="comment_shadow">#323232</color>
<resources>

使用这种格式,你会非常容易的开始重复定义ARGB值,这使如果需要改变基本色变的很复杂。同时,这些定义是跟一些环境关联起来的,如button或者comment, 应该放到一个按钮风格中,而不是在color.xml文件中。

相反,这样做

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
<resources>
<!--主色-->
<color name="colorPrimary">#ff149BCC</color><!--主色调-->
<color name="colorPrimaryDark">#ff1976D2</color><!--在Material Design,对应状态栏颜色-->
<color name="colorAccent">#ff0EC7F0</color> <!--强调色 -->
<color name="colorGrounding">#ffF4F3F1</color><!--界面底色-->
<color name="colorRipple">#B2EBF2</color><!--点击时水波纹颜色-->
<!--文字颜色-->
<color name="textPrimary">#172434</color>
<color name="textSecondary">#666666</color>
<color name="textPrimaryInverted">@color/white</color>
<color name="textSecondaryInverted">@color/white_A50</color>
<!--通用颜色-->
<color name="blue">#ff1976D2</color>
<color name="blue_light">#ff149BCC</color>
<color name="white">#ffffffff</color>
<color name="white_A50">#80ffffff</color><!--50%透明度-->
<color name="yellow">#f59800</color>
</resources>

向应用设计者那里要这个调色板,名称不需要跟greenblue等等相同。brand_primarybrand_secondarybrand_negative这样的名字也是完全可以接受的。 像这样规范的颜色很容易修改或重构,会使应用一共使用了多少种不同的颜色变得非常清晰。 通常一个具有审美价值的UI来说,减少使用颜色的种类是非常重要的。

2.4.6 dimens.xml

像对待colors.xml一样对待dimens.xml文件 与定义颜色调色板一样,你同时也应该定义一个空隙间隔和字体大小的“调色板”。 一个好的例子,如下所示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
<resources>
<!--font sizes-->
<dimen name="font_micro">10.0sp</dimen>
<dimen name="font_small">12.0sp</dimen>
<dimen name="font_medium">14.0sp</dimen>
<dimen name="font_large">16.0sp</dimen>
<dimen name="font_xlarge">18.0sp</dimen>
<dimen name="font_extra_large">22.0sp</dimen>
<!-- typical spacing between two views -->
<dimen name="spacing_huge">40dp</dimen>
<dimen name="spacing_large">24dp</dimen>
<dimen name="spacing_normal">14dp</dimen>
<dimen name="spacing_small">10dp</dimen>
<dimen name="spacing_tiny">4dp</dimen>
<!--布局规范-->
<dimen name="toolbar_height">48dp</dimen>
<dimen name="bottomBar_height">56dp</dimen>
<dimen name="tab_height">40dp</dimen>
<dimen name="row_view_height">48dp</dimen>
</resources>

布局时在写marginspaddings时,你应该使用spacing_xxxx尺寸格式来布局,而不是像对待string字符串一样直接写值。 这样写会非常有感觉,会使组织和改变风格或布局是非常容易。

2.4.7 styles.xml

style的name命名使用大驼峰命名法例如:

1
2
3
4
<style name="ContentText">
<item name="android:textSize">@dimen/font_normal</item>
<item name="android:textColor">@color/basic_black</item>
</style>

将一个大的style文件分割成多个文件, 你可以有多个styles.xml 文件。Android SDK支持其它文件,styles这个文件名称并没有作用,起作用的是在文件 里xml的<style>标签。因此你可以有多个style文件styles.xmlstyle_home.xmlstyle_item_details.xmlstyles_forms.xml。 不同于资源文件路径需要为系统构建起的有意义,在res/values目录下的文件可以任意命名。

参考资料

Android-Code-Style

Android开发规范

Android开发规范和架构总结

Vary Zhao wechat
欢迎你扫描上面的二维码,加我微信