Android Android Pitfalls and Anti-patterns Jigar Brahmbhatt I do not read..I’ll just ask someone what’s new on Android I read your blog…it’s fantastic…can you share your source code so I can copy paste ? I don’t know enough Java, but I would love to do Android development Is this already available in Support Library ? Since When? Just making this Context static to get work done! Will remove it later What is AsyncLayoutInflater ? velopment move it later Oh yeah! I know what is abstraction in OOPS! Got full marks in college exam What do you mean by “context is leaking” ? Oh it’s an easy fix! Let me just put a NULL check before it Hey dude, don’t worry about Android lint! bunch of warnings huah! Dead code ! Dead code! Dead code! How to freaking know when my user is online and offline ? PM requirement! android:screenOrientation=“portrait" Yay! doSomething(null, null, true, null, false) Javadoc ? Who’s gonna read? public static String MY_GLOBAL_STRING = “”; ne ? PM requirement! I don’t know enough Java, but I would love to do Android development Is this already available in Support Library ? Since When? Just making this Context static to get work done! Will remove it later Oh yeah! I know what is abstraction in OOPS! Got full marks in college exam What do you mean by “context is leaking” ? Oh it’s an easy fix! Let me just put a NULL check before it Dead code ! Dead code! Dead code! Javadoc ? Who’s gonna read? public static String MY_GLOBAL_STRING = “”; ine ? PM requirement! BOOT_COMPLETED Code reviews ? YAGNI “Don’t Repeat Yourself” What is AsyncLayoutInflater ? d development @jabbar_jigariyo
not language ‣ Excitement for Android without understanding Java (recent grads) ‣ Knowledge of OOPS, but don’t utilize ‣ Poor or lack of understanding related to design patterns
int count, int after) { } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // process the text, and do something } @Override public void afterTextChanged(Editable s) { } }); public abstract class MyBaseTextWatcher implements TextWatcher { @Override public void beforeTextChanged(CharSequence s, int start, int count, int after) { // Do nothing } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // Do nothing } @Override public void afterTextChanged(Editable s) { // Do nothing } } Example: Utilizing OOPS concepts
beforeTextChanged(CharSequence s, int start, int count, int after) { // Do nothing } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // Do nothing } @Override public void afterTextChanged(Editable s) { // Do nothing } } editText.addTextChangedListener(new MyBaseTextWatcher() { @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // process the text, and do something } });
beforeTextChanged(CharSequence s, int start, int count, int after) { // Do nothing } @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // Do nothing } @Override public void afterTextChanged(Editable s) { // Do nothing } } editText.addTextChangedListener(new MyBaseTextWatcher() { @Override public void onTextChanged(CharSequence s, int start, int before, int count) { // process the text, and do something } });
} public class PaytmStrategy implements PaymentStrategy { final String phone; public PaytmStrategy(String phone) { this.phone = phone; } @Override public void pay(int amount) { // make payment using phone } }
} public class PaytmStrategy implements PaymentStrategy { final String phone; public PaytmStrategy(String phone) { this.phone = phone; } @Override public void pay(int amount) { // make payment using phone } }
final String email; public FreechargeStrategy(String phone, String email) { this.phone = phone; this.email = email; } @Override public void pay(int amount) { // make payment using phone and email } } // Calling methods new PaytmStrategy("9090909090").pay(125); new FreechargeStrategy("9090909090", "[email protected]").pay(123);
final String email; public FreechargeStrategy(String phone, String email) { this.phone = phone; this.email = email; } @Override public void pay(int amount) { // make payment using phone and email } } // Calling methods new PaytmStrategy("9090909090").pay(125); new FreechargeStrategy("9090909090", "[email protected]").pay(123);
final String email; public FreechargeStrategy(String phone, String email) { this.phone = phone; this.email = email; } @Override public void pay(int amount) { // make payment using phone and email } } // Calling methods new PaytmStrategy("9090909090").pay(125); new FreechargeStrategy("9090909090", "[email protected]").pay(123);
be lost if the activity needs to later be restored from its state, so this should only be used for cases where it is okay for the UI state to change unexpectedly on the user.
‣ Can’t provide useful input if not up-to-date ‣ Writing unnecessary code because you don’t know what is already available IF YOU’RE NOT READING..WE’RE NOT HIRING YOU!!!!!! @Haptik
‣ Can’t provide useful input if not up-to-date ‣ Writing unnecessary code because you don’t know what is already available if(phone != null && !phone.isEmpty()) { // Do something } IF YOU’RE NOT READING..WE’RE NOT HIRING YOU!!!!!! @Haptik
‣ Can’t provide useful input if not up-to-date ‣ Writing unnecessary code because you don’t know what is already available if(phone != null && !phone.isEmpty()) {} // instead of “android.text.TextUtils" if(!TextUtils.isEmpty(phone)) { // phone is ready to use } IF YOU’RE NOT READING..WE’RE NOT HIRING YOU!!!!!! @Haptik
// public void thisMethodIsNotWorking(String phone) { // this.phone = phone; // // if(phone != null && !phone.isEmpty()) { // Something is not working // } // // // instead of // if(!TextUtils.isEmpty(phone)) { // probably this is not right // } // } ‣ If you’re sole developer or early stage startup then, you are suffering from spaghetti code everywhere
progressDialog.dismiss(); } } @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); progressDialog = new ProgressDialog(this); } Fatal Exception: java.lang.IllegalArgumentException: View=com.android.internal.policy.PhoneWindow$DecorView{9c3d915 V.E...... R......D 0,0-1026,348} not attached to window manager at android.view.WindowManagerGlobal.findViewLocked(WindowManagerGlobal.jav a:424) at android.view.WindowManagerGlobal.removeView(WindowManagerGlobal.java: 350) at android.view.WindowManagerImpl.removeViewImmediate(WindowManagerImpl.ja va:116) at android.app.Dialog.dismissDialog(Dialog.java:362) at android.app.Dialog.dismiss(Dialog.java:345)
vs direct JSON public class UserCreationResponse { String userId; String username; boolean error; public String getUserId() { return userId; } public String getUsername() { return username; } public boolean isError() { return error; } }