SlideShare ist ein Scribd-Unternehmen logo
1 von 54
Downloaden Sie, um offline zu lesen
Who I am
Born in the past millenium and still
  an happy software developer

             Mobile addicted
           Android enthusiastic
            Free software fan
               Proud rider

          … and Tiramisu' lover

                         rainbowbreeze

   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)    Slide 1
Overview

                        Online learnig resources
                 Paintless rotation with threads
                          Easy IoC/DI framework
               Testing, from unit to automation
        Honeycomb and backward compatibility
                       Libraries and frameworks
                                    Q&A session

Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)      Slide 2
Chocolate Interaction model




Don't be scare: interact, collaborate, share your fun!
   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 3
Useful online material – Patterns


       Designing and Implementing Android UIs
http://www.google.com/events/io/2011/sessions/designing-and-implementing-android-uis-
                            for-phones-and-tablets.html
                         http://code.google.com/p/iosched/


  Advanced Topics for Expert Android App Devs
http://www.google.com/events/io/2011/sessions/android-protips-advanced-topics-for-expert-
                             android-app-developers.html


   Developing Android REST client applications
http://www.google.com/events/io/2010/sessions/developing-RESTful-android-apps.html




    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)                               Slide 4
Useful online material - ListView



                           The world of ListView
   http://www.google.com/events/io/2010/sessions/world-of-listview-android.html


            Lazy-loading of remote thumbnails
http://android-developers.blogspot.com/2010/07/multithreading-for-performance.html


               Drag and Drop capable ListView
                      https://github.com/commonsguy/cwac-touchlist




   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)                           Slide 5
Background thread, progress bar and rotation


 Your application have to be smooth, don't use UI
       thread for long operation (> 200ms)

Yuo cannot update UI Thread from external threads

     Use Activity.runOnUiThread(Runnable),
View.post(Runnable), View.postDelayed(Runnable,
      long), Handler to bypass the problem


   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 6
Background thread, progress bar and rotation

 public void onClick(View v) {
   //background thread
   new Thread(new Runnable() {
    public void run() {
      final Bitmap b = loadImageFromNetwork();
      //update ui thread
      mImageView.post(new Runnable() {
       public void run() {
          mImageView.setImageBitmap(b);
       }
      });
    }
   }).start();
 }

  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 7
Background thread, progress bar and rotation




                               The simplest way

                                       AsyncTask
            Can access to UI Thread from separate thread
      http://android-developers.blogspot.com/2009/05/painless-threading.html




  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 8
Background thread, progress bar and rotation

 protected void onCreate(Bundle savedInstanceState) {
   ...
   mLblResult = (TextView) findViewById(R.id.lblResult);
   LongTask longTask = new LongTask();
   longTask.execute();
   …
 }

 private class LongTask extends AsyncTask<Void, Void, String>
  ...
  protected void onPostExecute(String result) {
    mLblResult.setText(result);
  }


  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)            Slide 9
Background thread, progress bar and rotation



 But if the screen is rotated while the backgroud
             thread is still in execution?

          UI not updated, dialogs disappear,
         NullPointerException, memory leaks...

                                             OMG!



  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)     Slide 10
Background thread, progress bar and rotation
                                       The clean way

  - Define an Handler inside the Activity that process thread
                      tasks (update/result)
        - Create background thread passing the handler
 - Call the handler from the thread when a progress must be
                 published or the thread finish
   - Update activity reference inside thread using OnPause()
                        and OnResume()
- Pay attention to OnStart and other Activity lifecycle events
http://code.google.com/p/rainbowlibs/source/browse/android/trunk/rainbowlibs/src/it/rainb
                 owbreeze/libs/logic/RainbowBaseBackgroundThread.java
http://code.google.com/p/rainbowlibs/source/browse/android/trunk/rainbowlibs/src/it/rainb
                    owbreeze/libs/ui/RainbowSplashScreenActivity.java
      Android Survival Guide
      Alfredo Morresi (http://www.rainbowbreeze.it)                           Slide 11
Background thread, progress bar and rotation
 public class WebcamActivity extends Activity() {

  private Handler mActivityHandler = new Handler() {

  public void handleMessage(Message msg) {
   Log.debug("Message from external thread" + msg.what);
   switch (msg.what) {
    case RotationThread.OPERATION_STARTS:
     //create progress dialog + other UI operations
     break;
    case RotationThread.OPERATION_COMPLETED:
     //remove the dialog + additional logic
     break;
    case RotationThread.OPERATION_ERROR:
     //remove the dialog + additional error logic
  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)        Slide 12
Background thread, progress bar and rotation

 public class WebcamActivity extends Activity() {

  private RotatingThread mRotatingThread;

  private void showWebcam() {
   //show a progress dialog
   showDialog(DIALOG_PREPARE_FOR_FULLSCREEN);

      mRotatingThread = new RotatingThread(
       mActivityHandler,
       webcamToShowId);
      mRotatingThread.start();
  }

  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)     Slide 13
Background thread, progress bar and rotation
 public class RotatingThread() extends Thread {
  private WeakReference<Handler> mCallerHandler;

 public RotatingThread(Handler handler, int webcamId) {
   registerCallerHandler(handler);
   …
 }

 public void registerCallerHandler(Handler newHandler {
   mCallerHandler =
    new WeakReference<Handler>(newHandler);
 }

 public void unregisterCallerHandler()
 { mCallerHandler = null; }
  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)       Slide 14
Background thread, progress bar and rotation


 public class RotatingThread() extends Thread {
  ...

  public void run() {
   callHandlerAndRetry(OPERATION_STARTS);

      //your long operation here

      callHandlerAndRetry(OPERATION_COMPLETED);
  }




  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 15
Background thread, progress bar and rotation
 protected void callHandlerAndRetry(int messageCode) {
  for (int retries = 0; retries < TOTAL_RETRIES; retries++) {
     if (null != mCallerHandler && null != mCallerHandler.get()) {
         Message message =
           mCallerHandler.get().obtainMessage(messageCode);
         message.arg1 = arg1;
         mCallerHandler.get().sendMessage(message);
         break;
       }
         try { //what some times, maybe next time activity is ready
           Thread.sleep(INTERVAL_BETWEEN_RETRIES);
         } catch (InterruptedException ignoreExcepition) {}
     }
 }
     Android Survival Guide
     Alfredo Morresi (http://www.rainbowbreeze.it)             Slide 16
Background thread, progress bar and rotation
 public class WebcamActivity extends Activity() {

  @Override
  protected void onPause() {
    mRotatingThread.unregisterCallerHandler();
    super.onPause();
  }

  @Override
  protected void onResume() {
    mRotatingThread.registerCallerHandler(mActivityHandler);
    super.onResume();
  }



  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)        Slide 17
Background thread, progress bar and rotation
 public class WebcamActivity extends Activity() {

  @Override
  public Object onRetainNonConfigurationInstance() {
    return mRotatingThread;
  }

  @Override
  protected void onStart() {
    super.onStart();
    mRotatingThread =
      (RotatinThread)getLastNonConfigurationInstance();
    //nothing saved, first run of the activity
    if (null == mRotatingThread) showWebcam();
  }
  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)           Slide 18
Background thread, progress bar and rotation




         The short (but no totally complete) way

      Use a Fragment and setRetainInstance(true)
http://developer.android.com/resources/samples/ApiDemos/src/com/example/android/apis/
                            app/FragmentRetainInstance.html




     Android Survival Guide
     Alfredo Morresi (http://www.rainbowbreeze.it)                        Slide 19
Lazy loading singleton

                                 Singleton Pattern
Ensure that only one instance of a class is created and provide a
             global point of access to the object.

       Create your own singleton or extend
 android.app.Application and modify its onCreate()
                     method.
Base class for those who need to maintain global application state.
You can provide your own implementation by specifying its name in
  your AndroidManifest.xml’s <application> tag, which will cause
  that class to be instantiated for you when the process for your
                  application/package is created.

    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)         Slide 20
Lazy loading singleton
public class App extends Application {
 public static int myGlobalStaticValue;
 public int myGlobalValue;

 @Override
 public void onCreate() {
   super.onCreate();
   myGlobalStaticValue = 10;
   myGlobalValue = 20;
 }

<application android:name="it.rainbowbreeze.singleton.App">

int value = App.myGlobalStaticValue;
int value = ((App)context.getApplication()).myGlobalValue;
 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)         Slide 21
Lazy loading singleton

                         Drawbacks
         Singleton is a pattern or an anti-pattern?
http://stackoverflow.com/questions/3826905/singletons-vs-application-context-in-android


 OS may kill your application process, including the Application
  subclass instance. As a result the state is lost. When you later
  return to the application, then the OS will restore its activity
stack and Application subclass instance, but its fields will be null.

   If you really need singleton, at least use lazy-
 loading singleton and avoid static fields to store
              application lifecycle data
    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 22
Lazy loading singleton

public class MySingleton() {
 private MySingleton mInstance;

public synchronized MySingleton getInstance(Context c) {
  if (null == mInstance) {
    mInstance = new MySingleton(context);
  }
  return mInstance;
}

private MySingleton(Context appContext) {
  //initializes the object
  //reload SharedPreferences data
}

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)       Slide 23
Inversion of Control / Dependency Injection


                 Dependency Injection Pattern
The object does not need to know in advance about how the
  other part of the system works. Instead, the programmer
provides (injects) the relevant system component in advance
  along with a contract that it will behave in a certain way.
                   http://en.wikipedia.org/wiki/Dependency_injection


Reduce the coupling among software components:
 better code testability, useful in libraries, clean
                      code.


  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)                        Slide 24
Inversion of Control / Dependency Injection
public class ItemDao implements ItemDao {

    public ItemDao(Context appContext) {
      //performs initialization
    }
}

public DataManager implements IDataManager {
 INetManager mNetManager;
 IItemDao mItemDao;

    public DataManager(INetManager netMngr, IItemDao itemDao)
    {
      mNetManager = netMngr;
      mItemDao = itemDao;
    }
    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)    Slide 25
Inversion of Control / Dependency Injection



                        Drawbacks
               Complex and less readable code
                  Chain of dependencies
                    More code to write

                  Solutions
Ioc/DI frameworks manage all the boring things!



 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 26
Inversion of Control / Dependency Injection
public class AppEnv() {
 public static AppEnv i(Context appContext) {
   …
    mInstance = new AppEnv(appContext);
   return mInstance;
 }

 private AppEnv(Context appContext) {
   mItemDao = new ItemDao(appContext);
   mDataManager = new DataManager(mNetMngr, mItemDao);
 }

 ItemsDao mItemDao;
 public ItemsDao getItemDao(){
   return mItemDao;
 }

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)      Slide 27
Inversion of Control / Dependency Injection




                    Drawbacks
     Cannot inject mock for testiong purposes

                  Solutions
Separate the object factory from the singleton




 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)   Slide 28
Inversion of Control / Dependency Injection

public class ObjFactory {

    public ItemDao createDao(Context appContext) {
      return new ItemDao(appContext);
    }

    public DataManager createDataManager(
        INetManager netMngr, ItemDao itemDao) {
      return new DataManager(netManager, itemDao);
    }

}



    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)    Slide 29
Inversion of Control / Dependency Injection

public class AppEnv() {
 private static ObjFactory mObjFactory = new ObjFactory();

 public static AppEnv i(Context c) {
   …
    mInstance = new AppEnv(c, mObjFactory);
   return mInstance;
 }

 public static AppEnv i(Context c, ObjFactory customFactory) {
   …
    mInstance = new AppEnv(c, customFactory);
   return mInstance;
 }

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)          Slide 30
Inversion of Control / Dependency Injection

public class AppEnv() {
 …

 private AppEnv(Context appContext, ObjFactory objFactory) {
   mDao = objFactory.createDao(appContext);
   //... other initialization
   mDataManager = objFactory.createDataManager(
      mNetMngr, mDao);
 }

 private ItemsDao mDao;
 public ItemsDao getItemDao(){
   return mDao;
 }

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)       Slide 31
Inversion of Control / Dependency Injection

--- inside your activity / component ---
AppEnv appEnv = AppEnv.i(getContext());
ItemDao dao = appEnv.getItemDao();


--- inside your test class ---
MockObjFactory mockFactory = new MockObjFactory() {
  @Overrides
  public ItemDao createDao(Context appContext) {
    return new MockItemDao(appContext);
  }
};
AppEnv appEnv = AppEnv.i(getContext(), mockFactory);
ItemDao dao = appEnv.getItemDao();

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)         Slide 32
Inversion of Control / Dependency Injection



                                          RoboGuice
                         Like Google Guice, but for Android
                          http://code.google.com/p/roboguice/
      http://stackoverflow.com/questions/5067681/guice-performance-on-android




                                    Other solutions
http://stackoverflow.com/questions/1029696/the-hunt-for-the-j2me-friendly-ioc-container-is-on




     Android Survival Guide
     Alfredo Morresi (http://www.rainbowbreeze.it)                                Slide 33
Testing - basic




  Software testing = reduce risks of software
               implementation

                   Lot of support Android side
    http://developer.android.com/guide/topics/testing/testing_android.html




Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 34
Testing - first steps


             Create new “Android Test Project”
            Create a class that extends TestCase
                       Code first test

                             Red, Green, Refactor!

http://developer.android.com/resources/tutorials/testing/helloandroid_test.html




Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 35
Testing - first steps

public class MyFirstTest extends TextCase() {
 Private MyStringConverter mConverter;

    public void setUp() {
      mConverter = new MyStringConverter();
    }

    public testUpperCaseConversion() {
      String result = mConverter.toUppercase(“ota2011”);
      assertEquals(“Wrong value”, “OTA2011”, result);
    }
}



    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)          Slide 36
Testing with special Android Mock

                                AndroidTestCase
                                    access to a context
    http://developer.android.com/reference/android/test/AndroidTestCase.html


                            ApplicationTestCase
                    test app lifecycle, inject mock context
   http://developer.android.com/reference/android/test/ApplicationTestCase.html


                             Activity Testing API
test activity lifecycle, inject mocks, send key or touch events, etc
     http://developer.android.com/resources/tutorials/testing/activity_test.html
       http://developer.android.com/guide/topics/testing/activity_testing.html



   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)                             Slide 37
Testing with special Android Mock

public class SpinnerActivityTest extends
ActivityInstrumentationTestCase2<SpinnerActivity> {

protected void setUp() throws Exception {
  …
  mActivity = getActivity();
  mSpinner = (Spinner) mActivity.findViewById(R.id.Spinner01);
  …
}
public void testSpinnerUI() {
  this.sendKeys(KeyEvent.KEYCODE_DPAD_CENTER);
  mPos = mSpinner.getSelectedItemPosition();
  mSelection = (String)mSpinner.getItemAtPosition(mPos);
  assertEquals(resultText, mSelection);

 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)        Slide 38
Testing with special Android Mock


                           ProviderTestCase2
             test contentProvicer with isolated context
http://developer.android.com/guide/topics/testing/contentprovider_testing.html


                              ServiceTestCase
    test the service lifecycle, not the logic (detached)
    http://developer.android.com/guide/topics/testing/service_testing.html


                   ViewAsserts, MoreAsserts
                                  extended asserts


Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 39
Test automation with monkey



   adb shell monkey -p your.package.name -v 500
                        sends sequences of random events
           http://developer.android.com/guide/developing/tools/monkey.html


                                    monkeyrunner
A Python program that runs an application, sends keystrokes to it,
     takes screenshots of its user interface, and stores them
  http://developer.android.com/guide/developing/tools/monkeyrunner_concepts.html




    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)                            Slide 40
Testing with external tools


                                       Robotium
Automatic black-box test cases for Android applications, with
                   gesture and actions
                           http://code.google.com/p/robotium/


                                     Robolectric
 Fast and easy TDD, runs tests in normal JavaVM with mock
           Android classes, no need to deploy on
             devicehttp://pivotal.github.com/robolectric/



 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)                  Slide 41
Honeycomb and Backward Compatibility


Nowadays Android has two separate branches, but
     Ice Cream Sandwich will merge them

Avoid different versions of same app and prefer one adaptive
                  Use alternative resources
       AndroidManifest.xml filters for sdk, screen, hw
                   Put some dirty if in code
                             http://code.google.com/p/iosched/




  Android Survival Guide
  Alfredo Morresi (http://www.rainbowbreeze.it)                  Slide 42
Honeycomb and Backward Compatibility


                                           Resources

res/layout/main_activity.xml                           # For phones
res/layout-xlarge/main_activity.xml                    # Large screen
res/layout-sw600dp/main_activity.xml                   # For 7” tablets
res/layout-sw720dp/main_activity.xml                   # For 10” tablets
… and much more!


  http://android-developers.blogspot.com/2011/07/new-tools-for-managing-screen-
                                     sizes.html




 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)                         Slide 43
Honeycomb and Backward Compatibility
<!-- Tablet-only application -->
<manifest ... >
  <supports-screens android:smallScreens="false"
            android:normalScreens="false"
            android:largeScreens="false"
            android:xlargeScreens="true"
            android:requiresSmallestWidthDp="600" />
  <application ... >
     ...
  </application>
</manifest>
    http://android-developers.blogspot.com/2011/09/preparing-for-handsets.html
    http://android-developers.blogspot.com/2011/07/new-mode-for-apps-on-large-
                                    screens.html


 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)                         Slide 44
Testing with special Android Mock
                                                 Dirty if

private static boolean fragmentsSupported = false;

private static void checkFragmentsSupported()
throws NoClassDefFoundError {
  fragmentsSupported = android.app.Fragment.class != null;
}

static {
 try {
   checkFragmentsSupported();
 } catch (NoClassDefFoundError e) {
   fragmentsSupported = false;
 }
 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)              Slide 45
Testing with special Android Mock
@Override
public void onCreate(Bundle savedInstanceState) {
 super.onCreate(savedInstanceState);

    Intent intent = null;
    if (!fragmentsSupported)
      intent = new Intent(this, MainNonFragmentActivity.class);
    else
       intent = new Intent(this, MainFragmentActivity.class);

        startActivity(intent);
        finish();
    }
}
http://blog.radioactiveyak.com/2011/02/strategies-for-honeycomb-and-backwards.html
    Android Survival Guide
    Alfredo Morresi (http://www.rainbowbreeze.it)                       Slide 46
Honeycomb and Backward Compatibility



              Android Compatibility Package
                 Backport some 3.x APIs to 1.6 and 2.x
            http://developer.android.com/sdk/compatibility-library.html


  Support for Fragment, Loader, ViewPager

        Native code on 3.x, library code on 2.x



Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                             Slide 47
Honeycomb and Backward Compatibility

                                      Fragment




http://android-developers.blogspot.com/2011/03/fragments-for-all.html



Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                    Slide 48
Honeycomb and Backward Compatibility



                setRetainInstance(true)
activity is rotated but fragment is not destroyed and
         recreated, lifecycle events are called.
                         Finally!
        Bug: http://code.google.com/p/android/issues/detail?id=17423
  Bug: http://stackoverflow.com/questions/6250580/fragment-already-added-
                             illegalstateexception




   Android Survival Guide
   Alfredo Morresi (http://www.rainbowbreeze.it)                  Slide 49
Honeycomb Backward Compatibility




                             ActionBarSherlock
Library that uses native code for 3.x or its own code for 2.x
                               http://actionbarsherlock.com/




                                     GreenDroid
              Brand new actionbar implementation
                          http://android.cyrilmottier.com/?p=274




 Android Survival Guide
 Alfredo Morresi (http://www.rainbowbreeze.it)                     Slide 50
Useful libraries and resources
                    Android UI patterns blogs
                           http://www.androiduipatterns.com
                            http://www.androidpatterns.com


                               Android-ui-utils
            Asset Studio, Pencil stencils, icon templates
                       http://code.google.com/p/android-ui-utils/


      Additional Eclipse plugins for Android
                         sorce code, api level analysis
                         http://code.google.com/p/adt-addons/


                        Maven Android plugin
                   http://code.google.com/p/maven-android-plugin/

Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                       Slide 51
Useful libraries and resources

                                      Kernel source
                  to learn, to get inspired and to solve bugs!
http://grepcode.com/snapshot/repository.grepcode.com/java/ext/com.google.android/andro
                                      id/2.3.4_r1/

                             Clean code in Android
                              IoC, Binding, Annotation etc
             http://blog.springsource.com/2011/08/26/clean-code-with-android


                                        Crash report
   http://androidblogger.blogspot.com/2010/03/crash-reporter-for-android-slight.html




     Android Survival Guide
     Alfredo Morresi (http://www.rainbowbreeze.it)                             Slide 52
Useful libraries and resources



Use Apache HTTP library instead of Java.Net
                Https bugs, bufferization problems, etc
             http://code.google.com/p/android/issues/detail?id=3164
 http://groups.google.com/group/android-developers/msg/4ddd2e502f195e3a
                 http://stackoverflow.com/questions/2105364/


                      Be part of communities
                        mailing list, StackOveflow, ...
         http://developer.android.com/resources/community-groups.html




Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)                           Slide 53
Conclusion




                         Q&A
           (example: “Isn't it lunch time yet?”)



Android Survival Guide
Alfredo Morresi (http://www.rainbowbreeze.it)      Slide 54

Weitere ähnliche Inhalte

Ähnlich wie Android Survival Guide - Two years of software development

Android - Open Source Bridge 2011
Android - Open Source Bridge 2011Android - Open Source Bridge 2011
Android - Open Source Bridge 2011sullis
 
[Ultracode Munich #4] Short introduction to the new Android build system incl...
[Ultracode Munich #4] Short introduction to the new Android build system incl...[Ultracode Munich #4] Short introduction to the new Android build system incl...
[Ultracode Munich #4] Short introduction to the new Android build system incl...BeMyApp
 
HTML5 Who what where when why how
HTML5 Who what where when why howHTML5 Who what where when why how
HTML5 Who what where when why howbrucelawson
 
Android 3.0 Portland Java User Group 2011-03-15
Android 3.0 Portland Java User Group 2011-03-15Android 3.0 Portland Java User Group 2011-03-15
Android 3.0 Portland Java User Group 2011-03-15sullis
 
Making your site mobile-friendly - DevCSI Reading 21.07.2010
Making your site mobile-friendly - DevCSI Reading 21.07.2010Making your site mobile-friendly - DevCSI Reading 21.07.2010
Making your site mobile-friendly - DevCSI Reading 21.07.2010Patrick Lauke
 
Flutter Forward EXTENDED - Flutter로 앱 개발 입문하기
Flutter Forward EXTENDED -  Flutter로 앱 개발 입문하기Flutter Forward EXTENDED -  Flutter로 앱 개발 입문하기
Flutter Forward EXTENDED - Flutter로 앱 개발 입문하기SuJang Yang
 
Dori waldman android _course_2
Dori waldman android _course_2Dori waldman android _course_2
Dori waldman android _course_2Dori Waldman
 
[Droidcon Paris 2013]Multi-Versioning Android Tips
[Droidcon Paris 2013]Multi-Versioning Android Tips[Droidcon Paris 2013]Multi-Versioning Android Tips
[Droidcon Paris 2013]Multi-Versioning Android TipsKenichi Kambara
 
Dori waldman android _course
Dori waldman android _courseDori waldman android _course
Dori waldman android _courseDori Waldman
 
Developing Android Apps
Developing Android AppsDeveloping Android Apps
Developing Android AppsClaire Lee
 
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...olrandir
 
Lecture #3 activities and intents
Lecture #3  activities and intentsLecture #3  activities and intents
Lecture #3 activities and intentsVitali Pekelis
 
How to develop a Graphical User Interface (GUI) in Scilab
How to develop a Graphical User Interface (GUI) in ScilabHow to develop a Graphical User Interface (GUI) in Scilab
How to develop a Graphical User Interface (GUI) in ScilabScilab
 
Lhy tutorial gui(1)
Lhy tutorial gui(1)Lhy tutorial gui(1)
Lhy tutorial gui(1)Brijesh Naik
 
Android 3.1 - Portland Code Camp 2011
Android 3.1 - Portland Code Camp 2011Android 3.1 - Portland Code Camp 2011
Android 3.1 - Portland Code Camp 2011sullis
 
Asynchronous Programming in Android
Asynchronous Programming in AndroidAsynchronous Programming in Android
Asynchronous Programming in AndroidJohn Pendexter
 
Apache Cordova In Action
Apache Cordova In ActionApache Cordova In Action
Apache Cordova In ActionHazem Saleh
 

Ähnlich wie Android Survival Guide - Two years of software development (20)

Android - Open Source Bridge 2011
Android - Open Source Bridge 2011Android - Open Source Bridge 2011
Android - Open Source Bridge 2011
 
[Ultracode Munich #4] Short introduction to the new Android build system incl...
[Ultracode Munich #4] Short introduction to the new Android build system incl...[Ultracode Munich #4] Short introduction to the new Android build system incl...
[Ultracode Munich #4] Short introduction to the new Android build system incl...
 
HTML5 Who what where when why how
HTML5 Who what where when why howHTML5 Who what where when why how
HTML5 Who what where when why how
 
Android 3.0 Portland Java User Group 2011-03-15
Android 3.0 Portland Java User Group 2011-03-15Android 3.0 Portland Java User Group 2011-03-15
Android 3.0 Portland Java User Group 2011-03-15
 
Making your site mobile-friendly - DevCSI Reading 21.07.2010
Making your site mobile-friendly - DevCSI Reading 21.07.2010Making your site mobile-friendly - DevCSI Reading 21.07.2010
Making your site mobile-friendly - DevCSI Reading 21.07.2010
 
Flutter Forward EXTENDED - Flutter로 앱 개발 입문하기
Flutter Forward EXTENDED -  Flutter로 앱 개발 입문하기Flutter Forward EXTENDED -  Flutter로 앱 개발 입문하기
Flutter Forward EXTENDED - Flutter로 앱 개발 입문하기
 
Dori waldman android _course_2
Dori waldman android _course_2Dori waldman android _course_2
Dori waldman android _course_2
 
Lightning Talk - Xamarin
Lightning Talk - Xamarin Lightning Talk - Xamarin
Lightning Talk - Xamarin
 
[Droidcon Paris 2013]Multi-Versioning Android Tips
[Droidcon Paris 2013]Multi-Versioning Android Tips[Droidcon Paris 2013]Multi-Versioning Android Tips
[Droidcon Paris 2013]Multi-Versioning Android Tips
 
Dori waldman android _course
Dori waldman android _courseDori waldman android _course
Dori waldman android _course
 
Developing Android Apps
Developing Android AppsDeveloping Android Apps
Developing Android Apps
 
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...
Android: the Single Activity, Multiple Fragments pattern | One Activity to ru...
 
Android
AndroidAndroid
Android
 
Lecture #3 activities and intents
Lecture #3  activities and intentsLecture #3  activities and intents
Lecture #3 activities and intents
 
How to develop a Graphical User Interface (GUI) in Scilab
How to develop a Graphical User Interface (GUI) in ScilabHow to develop a Graphical User Interface (GUI) in Scilab
How to develop a Graphical User Interface (GUI) in Scilab
 
Lhy tutorial gui(1)
Lhy tutorial gui(1)Lhy tutorial gui(1)
Lhy tutorial gui(1)
 
Synapseindia android apps application
Synapseindia android apps applicationSynapseindia android apps application
Synapseindia android apps application
 
Android 3.1 - Portland Code Camp 2011
Android 3.1 - Portland Code Camp 2011Android 3.1 - Portland Code Camp 2011
Android 3.1 - Portland Code Camp 2011
 
Asynchronous Programming in Android
Asynchronous Programming in AndroidAsynchronous Programming in Android
Asynchronous Programming in Android
 
Apache Cordova In Action
Apache Cordova In ActionApache Cordova In Action
Apache Cordova In Action
 

Mehr von Alfredo Morresi

Slightly Advanced Android Wear ;)
Slightly Advanced Android Wear ;)Slightly Advanced Android Wear ;)
Slightly Advanced Android Wear ;)Alfredo Morresi
 
Testing in Android: automatici, di integrazione, TDD e scenari avanzati
Testing in Android: automatici, di integrazione, TDD e scenari avanzatiTesting in Android: automatici, di integrazione, TDD e scenari avanzati
Testing in Android: automatici, di integrazione, TDD e scenari avanzatiAlfredo Morresi
 
Mobile platforms development overview
Mobile platforms development overviewMobile platforms development overview
Mobile platforms development overviewAlfredo Morresi
 
Funambol Code Sniper - Avatargrabber
Funambol Code Sniper - AvatargrabberFunambol Code Sniper - Avatargrabber
Funambol Code Sniper - AvatargrabberAlfredo Morresi
 
Mobile security & privacy - Paranoia in movimento
Mobile security & privacy - Paranoia in movimentoMobile security & privacy - Paranoia in movimento
Mobile security & privacy - Paranoia in movimentoAlfredo Morresi
 
Tesi cartoni animati e modelli culturali
Tesi cartoni animati e modelli culturaliTesi cartoni animati e modelli culturali
Tesi cartoni animati e modelli culturaliAlfredo Morresi
 
BlueSecurity: quando il dente fa male!
BlueSecurity: quando il dente fa male!BlueSecurity: quando il dente fa male!
BlueSecurity: quando il dente fa male!Alfredo Morresi
 
QR code - Alfredo Morresi
QR code - Alfredo MorresiQR code - Alfredo Morresi
QR code - Alfredo MorresiAlfredo Morresi
 

Mehr von Alfredo Morresi (9)

Slightly Advanced Android Wear ;)
Slightly Advanced Android Wear ;)Slightly Advanced Android Wear ;)
Slightly Advanced Android Wear ;)
 
Testing in Android: automatici, di integrazione, TDD e scenari avanzati
Testing in Android: automatici, di integrazione, TDD e scenari avanzatiTesting in Android: automatici, di integrazione, TDD e scenari avanzati
Testing in Android: automatici, di integrazione, TDD e scenari avanzati
 
Mobile platforms development overview
Mobile platforms development overviewMobile platforms development overview
Mobile platforms development overview
 
Refactoring 2 The Max
Refactoring 2 The MaxRefactoring 2 The Max
Refactoring 2 The Max
 
Funambol Code Sniper - Avatargrabber
Funambol Code Sniper - AvatargrabberFunambol Code Sniper - Avatargrabber
Funambol Code Sniper - Avatargrabber
 
Mobile security & privacy - Paranoia in movimento
Mobile security & privacy - Paranoia in movimentoMobile security & privacy - Paranoia in movimento
Mobile security & privacy - Paranoia in movimento
 
Tesi cartoni animati e modelli culturali
Tesi cartoni animati e modelli culturaliTesi cartoni animati e modelli culturali
Tesi cartoni animati e modelli culturali
 
BlueSecurity: quando il dente fa male!
BlueSecurity: quando il dente fa male!BlueSecurity: quando il dente fa male!
BlueSecurity: quando il dente fa male!
 
QR code - Alfredo Morresi
QR code - Alfredo MorresiQR code - Alfredo Morresi
QR code - Alfredo Morresi
 

Kürzlich hochgeladen

Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...Jeffrey Haguewood
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)wesley chun
 
MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024MIND CTI
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businesspanagenda
 
presentation ICT roal in 21st century education
presentation ICT roal in 21st century educationpresentation ICT roal in 21st century education
presentation ICT roal in 21st century educationjfdjdjcjdnsjd
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...apidays
 
AWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAndrey Devyatkin
 
AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024The Digital Insurer
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...DianaGray10
 
ICT role in 21st century education and its challenges
ICT role in 21st century education and its challengesICT role in 21st century education and its challenges
ICT role in 21st century education and its challengesrafiqahmad00786416
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...apidays
 
Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024The Digital Insurer
 
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...apidays
 
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FMESafe Software
 
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Drew Madelung
 
Data Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt RobisonData Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt RobisonAnna Loughnan Colquhoun
 
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Miguel Araújo
 
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ..."I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...Zilliz
 
Strategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a FresherStrategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a FresherRemote DBA Services
 
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin WoodPolkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin WoodJuan lago vázquez
 

Kürzlich hochgeladen (20)

Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
Web Form Automation for Bonterra Impact Management (fka Social Solutions Apri...
 
Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)Powerful Google developer tools for immediate impact! (2023-24 C)
Powerful Google developer tools for immediate impact! (2023-24 C)
 
MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024MINDCTI Revenue Release Quarter One 2024
MINDCTI Revenue Release Quarter One 2024
 
Why Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire businessWhy Teams call analytics are critical to your entire business
Why Teams call analytics are critical to your entire business
 
presentation ICT roal in 21st century education
presentation ICT roal in 21st century educationpresentation ICT roal in 21st century education
presentation ICT roal in 21st century education
 
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
Apidays Singapore 2024 - Building Digital Trust in a Digital Economy by Veron...
 
AWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of TerraformAWS Community Day CPH - Three problems of Terraform
AWS Community Day CPH - Three problems of Terraform
 
AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024AXA XL - Insurer Innovation Award Americas 2024
AXA XL - Insurer Innovation Award Americas 2024
 
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
Connector Corner: Accelerate revenue generation using UiPath API-centric busi...
 
ICT role in 21st century education and its challenges
ICT role in 21st century education and its challengesICT role in 21st century education and its challenges
ICT role in 21st century education and its challenges
 
Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...Apidays New York 2024 - The value of a flexible API Management solution for O...
Apidays New York 2024 - The value of a flexible API Management solution for O...
 
Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024Manulife - Insurer Transformation Award 2024
Manulife - Insurer Transformation Award 2024
 
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
Apidays New York 2024 - Accelerating FinTech Innovation by Vasa Krishnan, Fin...
 
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers:  A Deep Dive into Serverless Spatial Data and FMECloud Frontiers:  A Deep Dive into Serverless Spatial Data and FME
Cloud Frontiers: A Deep Dive into Serverless Spatial Data and FME
 
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
Strategies for Unlocking Knowledge Management in Microsoft 365 in the Copilot...
 
Data Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt RobisonData Cloud, More than a CDP by Matt Robison
Data Cloud, More than a CDP by Matt Robison
 
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
Mastering MySQL Database Architecture: Deep Dive into MySQL Shell and MySQL R...
 
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ..."I see eyes in my soup": How Delivery Hero implemented the safety system for ...
"I see eyes in my soup": How Delivery Hero implemented the safety system for ...
 
Strategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a FresherStrategies for Landing an Oracle DBA Job as a Fresher
Strategies for Landing an Oracle DBA Job as a Fresher
 
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin WoodPolkadot JAM Slides - Token2049 - By Dr. Gavin Wood
Polkadot JAM Slides - Token2049 - By Dr. Gavin Wood
 

Android Survival Guide - Two years of software development

  • 1. Who I am Born in the past millenium and still an happy software developer Mobile addicted Android enthusiastic Free software fan Proud rider … and Tiramisu' lover rainbowbreeze Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 1
  • 2. Overview Online learnig resources Paintless rotation with threads Easy IoC/DI framework Testing, from unit to automation Honeycomb and backward compatibility Libraries and frameworks Q&A session Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 2
  • 3. Chocolate Interaction model Don't be scare: interact, collaborate, share your fun! Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 3
  • 4. Useful online material – Patterns Designing and Implementing Android UIs http://www.google.com/events/io/2011/sessions/designing-and-implementing-android-uis- for-phones-and-tablets.html http://code.google.com/p/iosched/ Advanced Topics for Expert Android App Devs http://www.google.com/events/io/2011/sessions/android-protips-advanced-topics-for-expert- android-app-developers.html Developing Android REST client applications http://www.google.com/events/io/2010/sessions/developing-RESTful-android-apps.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 4
  • 5. Useful online material - ListView The world of ListView http://www.google.com/events/io/2010/sessions/world-of-listview-android.html Lazy-loading of remote thumbnails http://android-developers.blogspot.com/2010/07/multithreading-for-performance.html Drag and Drop capable ListView https://github.com/commonsguy/cwac-touchlist Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 5
  • 6. Background thread, progress bar and rotation Your application have to be smooth, don't use UI thread for long operation (> 200ms) Yuo cannot update UI Thread from external threads Use Activity.runOnUiThread(Runnable), View.post(Runnable), View.postDelayed(Runnable, long), Handler to bypass the problem Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 6
  • 7. Background thread, progress bar and rotation public void onClick(View v) { //background thread new Thread(new Runnable() { public void run() { final Bitmap b = loadImageFromNetwork(); //update ui thread mImageView.post(new Runnable() { public void run() { mImageView.setImageBitmap(b); } }); } }).start(); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 7
  • 8. Background thread, progress bar and rotation The simplest way AsyncTask Can access to UI Thread from separate thread http://android-developers.blogspot.com/2009/05/painless-threading.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 8
  • 9. Background thread, progress bar and rotation protected void onCreate(Bundle savedInstanceState) { ... mLblResult = (TextView) findViewById(R.id.lblResult); LongTask longTask = new LongTask(); longTask.execute(); … } private class LongTask extends AsyncTask<Void, Void, String> ... protected void onPostExecute(String result) { mLblResult.setText(result); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 9
  • 10. Background thread, progress bar and rotation But if the screen is rotated while the backgroud thread is still in execution? UI not updated, dialogs disappear, NullPointerException, memory leaks... OMG! Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 10
  • 11. Background thread, progress bar and rotation The clean way - Define an Handler inside the Activity that process thread tasks (update/result) - Create background thread passing the handler - Call the handler from the thread when a progress must be published or the thread finish - Update activity reference inside thread using OnPause() and OnResume() - Pay attention to OnStart and other Activity lifecycle events http://code.google.com/p/rainbowlibs/source/browse/android/trunk/rainbowlibs/src/it/rainb owbreeze/libs/logic/RainbowBaseBackgroundThread.java http://code.google.com/p/rainbowlibs/source/browse/android/trunk/rainbowlibs/src/it/rainb owbreeze/libs/ui/RainbowSplashScreenActivity.java Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 11
  • 12. Background thread, progress bar and rotation public class WebcamActivity extends Activity() { private Handler mActivityHandler = new Handler() { public void handleMessage(Message msg) { Log.debug("Message from external thread" + msg.what); switch (msg.what) { case RotationThread.OPERATION_STARTS: //create progress dialog + other UI operations break; case RotationThread.OPERATION_COMPLETED: //remove the dialog + additional logic break; case RotationThread.OPERATION_ERROR: //remove the dialog + additional error logic Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 12
  • 13. Background thread, progress bar and rotation public class WebcamActivity extends Activity() { private RotatingThread mRotatingThread; private void showWebcam() { //show a progress dialog showDialog(DIALOG_PREPARE_FOR_FULLSCREEN); mRotatingThread = new RotatingThread( mActivityHandler, webcamToShowId); mRotatingThread.start(); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 13
  • 14. Background thread, progress bar and rotation public class RotatingThread() extends Thread { private WeakReference<Handler> mCallerHandler; public RotatingThread(Handler handler, int webcamId) { registerCallerHandler(handler); … } public void registerCallerHandler(Handler newHandler { mCallerHandler = new WeakReference<Handler>(newHandler); } public void unregisterCallerHandler() { mCallerHandler = null; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 14
  • 15. Background thread, progress bar and rotation public class RotatingThread() extends Thread { ... public void run() { callHandlerAndRetry(OPERATION_STARTS); //your long operation here callHandlerAndRetry(OPERATION_COMPLETED); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 15
  • 16. Background thread, progress bar and rotation protected void callHandlerAndRetry(int messageCode) { for (int retries = 0; retries < TOTAL_RETRIES; retries++) { if (null != mCallerHandler && null != mCallerHandler.get()) { Message message = mCallerHandler.get().obtainMessage(messageCode); message.arg1 = arg1; mCallerHandler.get().sendMessage(message); break; } try { //what some times, maybe next time activity is ready Thread.sleep(INTERVAL_BETWEEN_RETRIES); } catch (InterruptedException ignoreExcepition) {} } } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 16
  • 17. Background thread, progress bar and rotation public class WebcamActivity extends Activity() { @Override protected void onPause() { mRotatingThread.unregisterCallerHandler(); super.onPause(); } @Override protected void onResume() { mRotatingThread.registerCallerHandler(mActivityHandler); super.onResume(); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 17
  • 18. Background thread, progress bar and rotation public class WebcamActivity extends Activity() { @Override public Object onRetainNonConfigurationInstance() { return mRotatingThread; } @Override protected void onStart() { super.onStart(); mRotatingThread = (RotatinThread)getLastNonConfigurationInstance(); //nothing saved, first run of the activity if (null == mRotatingThread) showWebcam(); } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 18
  • 19. Background thread, progress bar and rotation The short (but no totally complete) way Use a Fragment and setRetainInstance(true) http://developer.android.com/resources/samples/ApiDemos/src/com/example/android/apis/ app/FragmentRetainInstance.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 19
  • 20. Lazy loading singleton Singleton Pattern Ensure that only one instance of a class is created and provide a global point of access to the object. Create your own singleton or extend android.app.Application and modify its onCreate() method. Base class for those who need to maintain global application state. You can provide your own implementation by specifying its name in your AndroidManifest.xml’s <application> tag, which will cause that class to be instantiated for you when the process for your application/package is created. Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 20
  • 21. Lazy loading singleton public class App extends Application { public static int myGlobalStaticValue; public int myGlobalValue; @Override public void onCreate() { super.onCreate(); myGlobalStaticValue = 10; myGlobalValue = 20; } <application android:name="it.rainbowbreeze.singleton.App"> int value = App.myGlobalStaticValue; int value = ((App)context.getApplication()).myGlobalValue; Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 21
  • 22. Lazy loading singleton Drawbacks Singleton is a pattern or an anti-pattern? http://stackoverflow.com/questions/3826905/singletons-vs-application-context-in-android OS may kill your application process, including the Application subclass instance. As a result the state is lost. When you later return to the application, then the OS will restore its activity stack and Application subclass instance, but its fields will be null. If you really need singleton, at least use lazy- loading singleton and avoid static fields to store application lifecycle data Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 22
  • 23. Lazy loading singleton public class MySingleton() { private MySingleton mInstance; public synchronized MySingleton getInstance(Context c) { if (null == mInstance) { mInstance = new MySingleton(context); } return mInstance; } private MySingleton(Context appContext) { //initializes the object //reload SharedPreferences data } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 23
  • 24. Inversion of Control / Dependency Injection Dependency Injection Pattern The object does not need to know in advance about how the other part of the system works. Instead, the programmer provides (injects) the relevant system component in advance along with a contract that it will behave in a certain way. http://en.wikipedia.org/wiki/Dependency_injection Reduce the coupling among software components: better code testability, useful in libraries, clean code. Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 24
  • 25. Inversion of Control / Dependency Injection public class ItemDao implements ItemDao { public ItemDao(Context appContext) { //performs initialization } } public DataManager implements IDataManager { INetManager mNetManager; IItemDao mItemDao; public DataManager(INetManager netMngr, IItemDao itemDao) { mNetManager = netMngr; mItemDao = itemDao; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 25
  • 26. Inversion of Control / Dependency Injection Drawbacks Complex and less readable code Chain of dependencies More code to write Solutions Ioc/DI frameworks manage all the boring things! Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 26
  • 27. Inversion of Control / Dependency Injection public class AppEnv() { public static AppEnv i(Context appContext) { … mInstance = new AppEnv(appContext); return mInstance; } private AppEnv(Context appContext) { mItemDao = new ItemDao(appContext); mDataManager = new DataManager(mNetMngr, mItemDao); } ItemsDao mItemDao; public ItemsDao getItemDao(){ return mItemDao; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 27
  • 28. Inversion of Control / Dependency Injection Drawbacks Cannot inject mock for testiong purposes Solutions Separate the object factory from the singleton Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 28
  • 29. Inversion of Control / Dependency Injection public class ObjFactory { public ItemDao createDao(Context appContext) { return new ItemDao(appContext); } public DataManager createDataManager( INetManager netMngr, ItemDao itemDao) { return new DataManager(netManager, itemDao); } } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 29
  • 30. Inversion of Control / Dependency Injection public class AppEnv() { private static ObjFactory mObjFactory = new ObjFactory(); public static AppEnv i(Context c) { … mInstance = new AppEnv(c, mObjFactory); return mInstance; } public static AppEnv i(Context c, ObjFactory customFactory) { … mInstance = new AppEnv(c, customFactory); return mInstance; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 30
  • 31. Inversion of Control / Dependency Injection public class AppEnv() { … private AppEnv(Context appContext, ObjFactory objFactory) { mDao = objFactory.createDao(appContext); //... other initialization mDataManager = objFactory.createDataManager( mNetMngr, mDao); } private ItemsDao mDao; public ItemsDao getItemDao(){ return mDao; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 31
  • 32. Inversion of Control / Dependency Injection --- inside your activity / component --- AppEnv appEnv = AppEnv.i(getContext()); ItemDao dao = appEnv.getItemDao(); --- inside your test class --- MockObjFactory mockFactory = new MockObjFactory() { @Overrides public ItemDao createDao(Context appContext) { return new MockItemDao(appContext); } }; AppEnv appEnv = AppEnv.i(getContext(), mockFactory); ItemDao dao = appEnv.getItemDao(); Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 32
  • 33. Inversion of Control / Dependency Injection RoboGuice Like Google Guice, but for Android http://code.google.com/p/roboguice/ http://stackoverflow.com/questions/5067681/guice-performance-on-android Other solutions http://stackoverflow.com/questions/1029696/the-hunt-for-the-j2me-friendly-ioc-container-is-on Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 33
  • 34. Testing - basic Software testing = reduce risks of software implementation Lot of support Android side http://developer.android.com/guide/topics/testing/testing_android.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 34
  • 35. Testing - first steps Create new “Android Test Project” Create a class that extends TestCase Code first test Red, Green, Refactor! http://developer.android.com/resources/tutorials/testing/helloandroid_test.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 35
  • 36. Testing - first steps public class MyFirstTest extends TextCase() { Private MyStringConverter mConverter; public void setUp() { mConverter = new MyStringConverter(); } public testUpperCaseConversion() { String result = mConverter.toUppercase(“ota2011”); assertEquals(“Wrong value”, “OTA2011”, result); } } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 36
  • 37. Testing with special Android Mock AndroidTestCase access to a context http://developer.android.com/reference/android/test/AndroidTestCase.html ApplicationTestCase test app lifecycle, inject mock context http://developer.android.com/reference/android/test/ApplicationTestCase.html Activity Testing API test activity lifecycle, inject mocks, send key or touch events, etc http://developer.android.com/resources/tutorials/testing/activity_test.html http://developer.android.com/guide/topics/testing/activity_testing.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 37
  • 38. Testing with special Android Mock public class SpinnerActivityTest extends ActivityInstrumentationTestCase2<SpinnerActivity> { protected void setUp() throws Exception { … mActivity = getActivity(); mSpinner = (Spinner) mActivity.findViewById(R.id.Spinner01); … } public void testSpinnerUI() { this.sendKeys(KeyEvent.KEYCODE_DPAD_CENTER); mPos = mSpinner.getSelectedItemPosition(); mSelection = (String)mSpinner.getItemAtPosition(mPos); assertEquals(resultText, mSelection); Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 38
  • 39. Testing with special Android Mock ProviderTestCase2 test contentProvicer with isolated context http://developer.android.com/guide/topics/testing/contentprovider_testing.html ServiceTestCase test the service lifecycle, not the logic (detached) http://developer.android.com/guide/topics/testing/service_testing.html ViewAsserts, MoreAsserts extended asserts Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 39
  • 40. Test automation with monkey adb shell monkey -p your.package.name -v 500 sends sequences of random events http://developer.android.com/guide/developing/tools/monkey.html monkeyrunner A Python program that runs an application, sends keystrokes to it, takes screenshots of its user interface, and stores them http://developer.android.com/guide/developing/tools/monkeyrunner_concepts.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 40
  • 41. Testing with external tools Robotium Automatic black-box test cases for Android applications, with gesture and actions http://code.google.com/p/robotium/ Robolectric Fast and easy TDD, runs tests in normal JavaVM with mock Android classes, no need to deploy on devicehttp://pivotal.github.com/robolectric/ Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 41
  • 42. Honeycomb and Backward Compatibility Nowadays Android has two separate branches, but Ice Cream Sandwich will merge them Avoid different versions of same app and prefer one adaptive Use alternative resources AndroidManifest.xml filters for sdk, screen, hw Put some dirty if in code http://code.google.com/p/iosched/ Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 42
  • 43. Honeycomb and Backward Compatibility Resources res/layout/main_activity.xml # For phones res/layout-xlarge/main_activity.xml # Large screen res/layout-sw600dp/main_activity.xml # For 7” tablets res/layout-sw720dp/main_activity.xml # For 10” tablets … and much more! http://android-developers.blogspot.com/2011/07/new-tools-for-managing-screen- sizes.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 43
  • 44. Honeycomb and Backward Compatibility <!-- Tablet-only application --> <manifest ... > <supports-screens android:smallScreens="false" android:normalScreens="false" android:largeScreens="false" android:xlargeScreens="true" android:requiresSmallestWidthDp="600" /> <application ... > ... </application> </manifest> http://android-developers.blogspot.com/2011/09/preparing-for-handsets.html http://android-developers.blogspot.com/2011/07/new-mode-for-apps-on-large- screens.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 44
  • 45. Testing with special Android Mock Dirty if private static boolean fragmentsSupported = false; private static void checkFragmentsSupported() throws NoClassDefFoundError { fragmentsSupported = android.app.Fragment.class != null; } static { try { checkFragmentsSupported(); } catch (NoClassDefFoundError e) { fragmentsSupported = false; } Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 45
  • 46. Testing with special Android Mock @Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); Intent intent = null; if (!fragmentsSupported) intent = new Intent(this, MainNonFragmentActivity.class); else intent = new Intent(this, MainFragmentActivity.class); startActivity(intent); finish(); } } http://blog.radioactiveyak.com/2011/02/strategies-for-honeycomb-and-backwards.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 46
  • 47. Honeycomb and Backward Compatibility Android Compatibility Package Backport some 3.x APIs to 1.6 and 2.x http://developer.android.com/sdk/compatibility-library.html Support for Fragment, Loader, ViewPager Native code on 3.x, library code on 2.x Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 47
  • 48. Honeycomb and Backward Compatibility Fragment http://android-developers.blogspot.com/2011/03/fragments-for-all.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 48
  • 49. Honeycomb and Backward Compatibility setRetainInstance(true) activity is rotated but fragment is not destroyed and recreated, lifecycle events are called. Finally! Bug: http://code.google.com/p/android/issues/detail?id=17423 Bug: http://stackoverflow.com/questions/6250580/fragment-already-added- illegalstateexception Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 49
  • 50. Honeycomb Backward Compatibility ActionBarSherlock Library that uses native code for 3.x or its own code for 2.x http://actionbarsherlock.com/ GreenDroid Brand new actionbar implementation http://android.cyrilmottier.com/?p=274 Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 50
  • 51. Useful libraries and resources Android UI patterns blogs http://www.androiduipatterns.com http://www.androidpatterns.com Android-ui-utils Asset Studio, Pencil stencils, icon templates http://code.google.com/p/android-ui-utils/ Additional Eclipse plugins for Android sorce code, api level analysis http://code.google.com/p/adt-addons/ Maven Android plugin http://code.google.com/p/maven-android-plugin/ Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 51
  • 52. Useful libraries and resources Kernel source to learn, to get inspired and to solve bugs! http://grepcode.com/snapshot/repository.grepcode.com/java/ext/com.google.android/andro id/2.3.4_r1/ Clean code in Android IoC, Binding, Annotation etc http://blog.springsource.com/2011/08/26/clean-code-with-android Crash report http://androidblogger.blogspot.com/2010/03/crash-reporter-for-android-slight.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 52
  • 53. Useful libraries and resources Use Apache HTTP library instead of Java.Net Https bugs, bufferization problems, etc http://code.google.com/p/android/issues/detail?id=3164 http://groups.google.com/group/android-developers/msg/4ddd2e502f195e3a http://stackoverflow.com/questions/2105364/ Be part of communities mailing list, StackOveflow, ... http://developer.android.com/resources/community-groups.html Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 53
  • 54. Conclusion Q&A (example: “Isn't it lunch time yet?”) Android Survival Guide Alfredo Morresi (http://www.rainbowbreeze.it) Slide 54