AnkiDroid Code ConventionsVersion 1.0, September 2010AnkiDroid Copyright © 2010 This document is available for download at http://code.google.com/p/ankidroid/downloads/list |
![]() |
If you find any error on this document or any inconsistency between the recommendations presented here and the automatic checkstyle and formatter, please send an email to ankidroid@gmail.com.
Layout for the recommendations is as follows:
n. Guideline short description |
Example if applicable |
1. Any violation to the guide is allowed if it enhances one of the following, by order of importance (higher levels cannot be sacrificed for lower levels): |
- Logical Structure - Consistency - Readability - Ease of modifications |
2. All names should be written in English. |
3. Package names should be in all lower case. |
com.company.application.ui com.sun.eng edu.cmu.cs.bovik.cheese |
4. Class names must be nouns, in mixed case with the first letter of each internal word capitalized. |
class Line; class AudioSystem; |
5. Variable names must be in mixed case starting with lower case. |
int age; float availableWidth; |
6. Non-public, non-static field names should start with m. |
private long mLongVariable; private int mIntVariable; |
7. Static field names should start with s. |
private static MyClass sSingleton; |
8. Constant (final variables) names must be all uppercase using underscore to separate words. |
public static final int SOME_CONSTANT = 42; |
9. Associated constants (final variables) should be prefixed by a common type name. |
public static final int COLOR_RED = 1; public static final int COLOR_GREEN = 2; public static final int COLOR_BLUE = 3; |
10. Method names should be verbs in mixed case, with the first letter in lowercase and with the first letter of each internal word capitalized. |
getName(); computeTotalWidth(); |
11. Functions (methods with a return) should be named after what they return and procedures (void methods) after what they do. |
12. In a method name, the name of the object is implicit and should be avoided. |
employee.getName(); // NOT: employee.getEmployeeName(); |
13. Negated boolean variable names must be avoided. |
boolean isLoaded; // NOT: boolean isNotLoaded; boolean isError; // NOT: boolean isNotError; |
14. Abbreviations in names should be avoided. |
computeAverage(); // NOT: compAvg(); ActionEvent event; // NOT: ActionEvent e; catch (Exception exception) { // NOT: catch (Exception e) { |
15. Abbreviations and acronyms should not be uppercase when used in a name. |
getCustomerId(); // NOT: getCustomerID(); exportHtmlSource(); // NOT: exportHTMLSource(); |
16. Generic variables should have the same name as their type. |
void setView(View view); // NOT: void setView(View v); // NOT: void setView(View aView); void close(Database database); // NOT: void close(Database db); // NOT: void close(Database sqliteDB); |
17. The terms get/set must be used where a class attribute is accessed directly. |
author.getName(); author.setName(name); point.getX(); point.setX(3); |
18. is prefix should be used for boolean variables and methods. Alternatively and if it fits better, has, can and should prefixes can be used. |
boolean isVisible; boolean isOpen(); boolean hasLicense(); boolean canEvaluate(); boolean shouldAbort = false; |
19. The term compute can be used in methods where something is computed. |
valueSet.computeAverage(); matrix.computeInverse(); |
20. The term find can be used in methods where something is looked up. |
vertex.findNearestVertex(); matrix.findSmallestElement(); node.findShortestPath(Node destinationNode); |
21. The term initialize can be used where an object or a concept is set up. |
initializeViews(); |
22. Variables with a large scope should have very descriptive (and usually long) names, variables with a small scope can have short names. |
23. Iterator variables can be called i, j, k, m, n... |
for (int i = 0; i < downloads.size(); i++) { statements; } |
24. Plural form should be used on names representing a collection of objects. |
ArrayList |
25. num prefix should be used for variables representing a number of objects. |
int numPoints = points.length(); |
26. Number suffix should be used for variables representing an entity number. |
int employeeNumber; int comicNumber; |
27. Exception classes should have Exception like a suffix. |
class CustomException extends Exception { ... } |
28. Singleton classes should return their unique instance through the getInstance method. |
class MySingletonClass { private final static MySingletonClass sInstance = new MySingletonClass(); private MySingletonClass() { ... } public static MySingletonClass getInstance() { // NOT: get() or instance()... return sInstance; } } |
29. String key resources must be all lowercase using underscore to separate words. |
<string name="good_example_key">Example value</string> // NOT: <string name="badExampleKey">Example value</string> |
30. XML elements identifiers must be all lowercase using underscore to separate words. |
<TextView android:id="@+id/good_id_example" // NOT: <TextView android:id="@+id/badIdExample" android:layout_width="wrap_content" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_height="wrap_content" /> /> |
31. Activiy names can have Activity like a suffix. |
public class ExampleActivity extends Activity { ... } |
32. Test method names should be composed by a name representing what is being tested and a name stating which specific case is being tested, separated with underscore. |
testMethod_specificCase1 testMethod_specificCase2 void testIsDistinguishable_protanopia() { ColorMatcher colorMatcher = new ColorMatcher(PROTANOPIA) assertFalse(colorMatcher.isDistinguishable(Color.RED, Color.BLACK)) assertTrue(colorMatcher.isDistinguishable(Color.X, Color.Y)) } |
33. File content must be kept within 120 columns. |
34. Basic indentation should be 4 spaces, without using tabs. |
if (condition) { statements; ... } |
35. Indentation of any wrapping line should be 8 spaces, without using tabs. |
if ((condition1 && condition2) || (condition3 && condition4) ||!(condition5 && condition6)) { doSomethingAboutIt(); } |
36. 1TBS (One True Brace Style) must be used. That means: - Opening brace "{" appears at the end of the same line as the declaration statement. - Ending brace "}" takes up an entire line by itself and it is intended at the same level that its correspondent opening statement. - Braces are mandatory, even for single-statements or empty blocks. |
class MyClass { int func() { if (something) { // ... } else if (somethingElse) { // ... } else { // ... } } } // NOT: if (condition) body(); if (condition) body(); |
37. White space should be used in the following cases: - After and before operators. - Before an opening brace. - After Java reserved words. - After commas. - After semicolons in for statements. - After any comment identifier. |
a = (b + c) * d; // NOT: a=(b+c)*d if (true) { // NOT: if (true){ ... while (true) { // NOT: while(true) { ... doSomething(a, b, c, d); // NOT: doSomething(a,b,c,d); for (i = 0; i < 10; i++) { // NOT: for(i=0;i<10;i++){ ... // This is a comment // NOT: //This is a comment /** // NOT: /** * This is a javadoc *This is a javadoc * comment *comment */ */ |
38. Three blank lines should be used in the following circumstances: - Between sections of a source file. - Between class and interface definitions. |
39. Two blank lines should be used between methods. |
40. One blank line should be used in the following circumstances: - Between the local variables in a method and its first statement. - Before a block or single-line comment. - Between logical sections inside a method, to improve readability |
41. The if-else class of statements should have the following form: |
if (condition) { statements; } if (condition) { statements; } else { statements; } if (condition) { statements; } else if (condition) { statements; } else { statements; } |
42. The for statement should have the following form: |
for (initialization; condition; update) { statements; } |
43. The while statement should have the following form: |
while (condition) { statements; } |
44. The do-while statement should have the following form: |
do { statements; } while (condition); |
45. The switch statement should have the following form: |
switch (condition) { case ABC: statements; // falls through case DEF: statements; break; case XYZ: statements; break; default: statements; break; } |
46. A try-catch statement should have the following form: |
try { statements; } catch (Exception exception) { statements; } try { statements; } catch (Exception exception) { statements; } finally { statements; } |
47. All comments should be written in English. |
48. Comments should not be used to compensate for or explain bad code. Tricky or bad code should be rewritten. |
49. There should be a white space after any comment identifier. |
// This is a comment NOT: //This is a comment /** NOT: /** * This is a javadoc *This is a javadoc * comment *comment */ */ |
50. Comments should be indented relative to their position in the code. |
while (true) { // NOT: while (true) { // Do something // Do something something(); something(); } } |
51. Javadoc comments should have the following form: |
/** * Return lateral location of the specified position. * If the position is unset, NaN is returned. * * @param x X coordinate of position. * @param y Y coordinate of position. * @param zone Zone of position. * @return Lateral location. * @throws IllegalArgumentException If zone is <= 0. */ public double computeLocation(double x, double y, int zone) throws IllegalArgumentException { ... } |
52. // should be used for all non-Javadoc comments, including multi-line comments. |
// Comment spanning // more than one line. |
53. All public classes and all public and protected methods within public classes should be documented using Javadoc conventions. |
54. If a collection of objects can not be qualified with its type, it should be followed by a comment stating the type of its elements. |
private Vector points; // of Point private Set shapes; // of Shape |
55. For separation comments within differents parts of a file, the following forms should be used (depending on its level of importance): |
//********************* // //********************* //--------------------- // //--------------------- |
56. TODO and FIXME must be written all in capitals and followed by a colon. |
// TODO: Calculate the new order // NOT: // TODO -> Calculate the new order // FIXME: Fix the synchronization algorithm // NOT: fixme: Fix the synchronization algorithm |
57. The TODO comment should be used to indicate pending tasks, code that is temporary, a short-term solution or good enough but not perfect code. |
58. The FIXME comment should be used to flag something that is bogus and broken. |
59. All logs should be written in English. |
60. The use of logs in release should be strictly restricted to the necessary ones. |
61. Logs should be terse but still understandable. |
62. Logs must never contain private information or protected content. |
63. System.out.println() or printf (in native code) must never be used. |
64. The ERROR level should only be used when something fatal has happened. |
65. The WARNING level should be used when something serious and unexpected happened. |
66. The INFORMATIVE level should be used to note something interesting to most people. |
67. The DEBUG level should be used to note what is happening on the device that could be relevant to investigate and debug unexpected behaviours. |
68. The VERBOSE level should be used for everything else. |
69. A DEBUG log should be inside an if (LOCAL_LOGD) block. |
if (LOCAL_LOGD) { Log.d(TAG, "Debugging application"); } |
70. A VERBOSE log should be inside an if (LOCAL_LOGV) block. |
if (LOCAL_LOGV) { Log.v(TAG, "Infroming about current state"); } |
71. The package statement must be the first statement of the file. |
72. The import statements must follow the package statement.
import statements should be sorted by importance, grouped together by packages and leaving one blank line between groups. The ordering of packages according to their importance is as follows:
|
import android.widget.TextView; import android.widget.ToggleButton; import com.ichi2.utils.DiffEngine; import com.tomgibara.android.veecheck.util.PrefSettings; import java.io.IOException; import java.util.regex.Matcher; import java.util.regex.Pattern; |
73. Imported classes should always be listed explicitly. |
import android.app.Activity; // NOT: import android.app.*; import android.app.ProgressDialog; import android.content.BroadcastReceiver; |
74. Class and Interface declarations should be organized in the
following manner:
|
75. Android Components (Activity, Service, BroadcastReceiver and ContentProvider) declarations should be organized in the
following manner:
|
76. Methods should be vertically ordered following the two following criteria: |
- Dependency: If one function calls another, they should be vertically close, and the caller should be above the callee, if at all possible. - Conceptual Affinity: Methods that perform similar tasks or have similar naming should be vertically close. |
77. Method modifiers should be given in the following order: - access modifier: public, protected or private - abstract - static - final - transient - volatile - synchronized - native - strictfp |
public static double square(double a); // NOT: static public double square(double a); |
78. Each declaration should take up an entire line. |
int level; // NOT: int level, size; int size; |
79. Each statement should take up an entire line. |
i++; // NOT: i++; j++; j++; |
80. Static variables or methods must always be accessed through the class name and never through an instance variable. |
AClass.classMethod(); // NOT: anObject.classMethod(); |
81. The incompleteness of split lines must be made obvious. |
totalSum = a + b + c + d + e; method(param1, param2, param3); setText("Long line split" + "into two parts."); |
82. Special characters like TAB and page break must be avoided. |
83. Type conversions must always be done explicitly. Never rely on implicit type conversion. |
floatValue = (int) intValue; // NOT: floatValue = intValue; |
84. Arrays should be declared with their brackets next to the type. |
int[] points = new int[20]; // NOT: int points[] = new int[20]; |
85. Variables should be initialized where they are declared and they should be declared in the smallest scope possible. |
86. Variables must never have dual meaning. |
87. Floating point variables should always be written with decimal point and at least one decimal. |
double total = 0.0; // NOT: double total = 0; double speed = 3.0e8; // NOT: double speed = 3e8; double sum; ... sum = (a + b) * 10.0; |
88. Floating point variables should always be written with a digit before the decimal point. |
double probability = 0.5; // NOT: double probability = .5; |
89. Numerical constants (except, in some cases, -1, 0 and 1) should not be coded directly. Use constants instead. |
private static final int TEAM_SIZE = 11; ... Player[] players = new Player[TEAM_SIZE]; // NOT: Player[] players = new Player[11]; |
90. Embedded assignments must be avoided. |
a = b + c; // NOT: d = (a = b + c) + r; d = a + r; |
91. The assignment operator should not be used in a place where it can be easily confused with the equality operator. |
// NOT: if (c++ = d++) { ... } |
92. Parenthesis should be used liberally in expressions involving mixed operators in order to make the precedence clear. |
if ((a == b) && (c == d)) // NOT: if (a == b && c == d) |
93. If an expression containing a binary operator appears before the ? in the ternary ?: operator, it should be parenthesized. |
(x >= 0) ? x : -x; // NOT: x >= 0 ? x : -x; |
94. Complex conditional expressions must be avoided. Introduce temporary boolean variables instead. |
bool isFinished = (elementNo < 0) || (elementNo > maxElement); bool isRepeatedEntry = elementNo == lastElement; if (isFinished || isRepeatedEntry) { ... } // NOT: if ((elementNo < 0) || (elementNo > maxElement)|| elementNo == lastElement) { ... } |
95. In an if statement, the normal case should be put in the if-part and the exception in the else-part |
boolean isOk = openDatabase(databasePath); if (isOk) { ... } else { ... } |
96. Executable statements in conditionals should be avoided. |
InputStream stream = File.open(fileName, "w"); if (stream != null) { ... } // NOT: if (File.open(fileName, "w") != null)) { ... } |
97. Only loop control statements must be included in the for() construction. |
maxim = -1; // NOT: for (i = 0, maxim = -1; i < 100; i++) { for (i = 0; i < 100; i++) { maxim = max(maxim, value[i]); maxim = max(maxim, value[i]); } } |
98. Loop variables should be initialized immediately before the loop. |
boolean isFound = false; // NOT: boolean isFound = false; while (!isFound) { ... ... while (!isFound) { } ... } |
99. do-while loops can be avoided. |
100. The use of break and continue in loops should be avoided. |
101. Exceptions must not be ignored without a good explanation. |
// NOT: void setServerPort(String value) { try { serverPort = Integer.parseInt(value); } catch (NumberFormatException e) { } } |
102. Generic Exception should not be caught except at the root of the stack. |
try { someComplicatedIOFunction(); // may throw IOException someComplicatedParsingFunction(); // may throw ParsingException someComplicatedSecurityFunction(); // may throw SecurityException } catch (IOException exception) { handleIOError(); } catch (ParsingException exception) { handleParsingError(); } catch (SecurityException exception) { handleSecurityError(); } // NOT: try { someComplicatedIOFunction(); // may throw IOException someComplicatedParsingFunction(); // may throw ParsingException someComplicatedSecurityFunction(); // may throw SecurityException } catch (Exception exception) { handleError(); } |
103. Finalizers should be avoided. |
104. At the same level of the element's name, it should only appear the xmlns attribute or the id attribute, in this order. |
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/example_id" android:layout_width="fill_parent" android:layout_height="wrap_content" > <RelativeLayout android:id="@+id/example_id" android:layout_width="fill_parent" android:layout_height="wrap_content" > <RelativeLayout android:layout_width="fill_parent" android:layout_height="wrap_content" > // NOT: <RelativeLayout android:layout_width="fill_parent" android:layout_height="wrap_content" > <RelativeLayout android:id="@+id/example_id" xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="fill_parent" android:layout_height="wrap_content" > |
105. Each attribute should take up an entire line. |
<EditText android:id="@+id/answer_field" // NOT: <EditText android:id="@+id/answer_field" android:layout_width="fill_parent" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_height="wrap_content" android:maxLines="2" android:visibility="gone"/> android:maxLines="2" android:visibility="gone" /> |
106. Attributes should be grouped by type (layout properties, text properties…) and within the same type, they should be ordered alphabetically. |
<TextView android:id="@+id/example_id" android:layout_height="wrap_content" android:layout_width="fill_parent" android:textColor="#ffffff" android:textSize="24sp" /> // NOT: <TextView android:id="@+id/example_id" android:layout_height="wrap_content" android:textColor="#ffffff" android:layout_width="fill_parent" android:textSize="24sp" /> <TextView android:id="@+id/example_id" android:layout_height="wrap_content" android:layout_width="fill_parent" android:textSize="24sp" android:textColor="#ffffff" /> |
107. LinearLayout elements must explicity state the orientation attribute. |
<LinearLayout // NOT: <LinearLayout android:layout_width="fill_parent" android:layout_width="fill_parent" android:layout_height="wrap_content" android:layout_height="wrap_content" android:orientation="horizontal" > > |
What | Naming Convention | GOOD Examples | BAD Examples |
---|---|---|---|
Package | lower case | com.company.application.ui | com.company.Application.Ui |
Class | nouns, mixed case, starting with uppercase | AudioSystem | audioSystem |
Variable | mixed case, starting in lowercase | availableWidth | AvailableWidth, available_width | Non-public, non-static field | mixed case, starting with "m" | mLongVariable | longVariable, LongVariable | Static field | mixed case, starting with "s" | sSingleton | singleton, staticVariable |
Constant | uppercase, using underscore to separate words | SOME_CONSTANT | some_constant |
Method | verbs, mixed case, starting with lowercase | getName() | get_name() | String key | lowercase, using underscore to separate words | good_example_key | badExampleKey | XML element identifier | lowercase, using underscore to separate words | good_id_example | badIdExample |
Line length | 120 characters |
Indentation |
Normal: 4 spaces with no tabs Wrapping lines: 8 spaces with no tabs |
Braces style | 1TBS braces style: class declarations, method declarations, block statements |
White spaces |
Before and after: operators Before: opening brace After: Java reserved words, commas, semicolons in for statements, any comment identifier |
Blank lines |
3 blank lines: Between sections of a source file Between class and interface definitions 2 blank lines: Between methods 1 blank line: Between local variables in a method and its first statement Before a block or single-line comment Between logical sections inside a method |
File organization | Copyright/ID comment package declaration import statements |
Class organization |
Class/Interface documentation class or interface statement Class (static) variables in the order public, protected, package (no access modifier), private Instance variables in the order public, protected, package (no access modifier), private Constructors Methods Inner classes |
Android components organization |
Component documentation class statement Class (static) variables in the order public, protected, package (no access modifier), private Instance variables in the order public, protected, package (no access modifier), private Constructors Lifecycle methods (ordered following the natural lifecycle, from creation to destruction) Other methods Inner classes |
Order of imports | Android imports, third parties imports (alphabetically), Java imports (java and javax) |
Order of method modifiers | public protected private abstract static final transient volatile synchronized native strictfp |
[1] Code Complete, Steve McConnel - Microsoft Press
[2] Clean Code, Robert C. Martin - Prentice Hall
[3] Java Coding Style Guide, Achut Reddy - Sun Microsystems, Inc.
http://cs.bilgi.edu.tr/pages/standards%5Fproject/java%5FCodingStyle.pdf
[4] Java Code Conventions
http://java.sun.com/docs/codeconv/html/CodeConvTOC.doc.html
[5] Android Code Style Guidelines for Contributors
http://source.android.com/source/code-style.html
[6] Coding Standards for Java from Geosoft
http://geosoft.no/development/javastyle.html
This page is maintained by ankidroid@gmail.com |