Your SlideShare is downloading. ×
TheEdge 2010: Android Advanced Techniques
Upcoming SlideShare
Loading in...5
×

Thanks for flagging this SlideShare!

Oops! An error has occurred.

×
Saving this for later? Get the SlideShare app to save on your phone or tablet. Read anywhere, anytime – even offline.
Text the download link to your phone
Standard text messaging rates apply

TheEdge 2010: Android Advanced Techniques

3,563
views

Published on

TheEdge 2010: …

TheEdge 2010:

The Android platform has matured rapidly during the last two years.
We're going to bring you up to speed in the latest cutting edge Android development techniques including: New UI Patterns, supporting multiple screen resolutions, REST clients, Push applications and optimizing your applications.

Published in: Technology

0 Comments
3 Likes
Statistics
Notes
  • Be the first to comment

No Downloads
Views
Total Views
3,563
On Slideshare
0
From Embeds
0
Number of Embeds
5
Actions
Shares
0
Downloads
203
Comments
0
Likes
3
Embeds 0
No embeds

Report content
Flagged as inappropriate Flag as inappropriate
Flag as inappropriate

Select your reason for flagging this presentation as inappropriate.

Cancel
No notes for slide
  • Present as a story:Designing smart and cool UIThe work behind to UI – I/OAnd how to make it all work fast
  • What is an activity: each screen is an activityA screen is defined by a layout, a layout could be an XML or Code. Explain why XML is better than code, and some Layout types.Intent is a way of describing of you want the android OS to do.
  • When mentioninggoogle IO mention what is it
  • Your application Home Screen
  • The first screen the user sees
  • Explain in short what’s a LinearLayout
  • Voice search, suggestion, global search
  • (Don’t believe the emulator!)
  • Why rawQuery? Query method has too many parameters, they should use a builder…
  • Transcript

    • 1. Advanced Android Techniques
      By: GiladGaron
    • 2. This presentation is based onTheEdge 2010 Android Application:
      Download it from the Market
      Download the source code: http://code.google.com/p/theedge2010/for all the examples in this presentation
      Before we begin!
      TheEdge 2010 Android App
    • 3. UI Design Patterns
      I/O Access
      Optimizations
      Agenda
    • 4. UI Design Patterns
    • 5. Activity
      Layouts
      Intent
      A little reminder about:
      UI Design Patterns
    • 6. Dashboard
      Action Bar
      Search Bar
      Quick Actions
      Flingable List Item
      “Applications are ahead of the framework”
      UI Design Patterns
    • 7. Dashboard
      You know what they say about First Impressions...
      UI Design Patterns
      Dashboard
    • 8. Introduce your application
      Reveal its functionality
      Update the user
      Just a layout, nothing fancy
      Dashboard
      UI Design Patterns
    • 9. Dashboard Components
      UI Design Patterns
      Action Bar
      Updates Panel
      Functionality Panel
    • 10. Implementation
      UI Design Patterns
      <?xmlversion="1.0"encoding="utf-8"?>
      <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
      android:orientation="vertical"
      android:layout_width="fill_parent"
      android:layout_height="fill_parent"
      android:background="@color/background">
      <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
      android:orientation="horizontal"
      android:layout_width="fill_parent"
      android:layout_height="45dip"
      android:background="@color/action_bar_background">
      <!-- Action Bar Code -->
      </LinearLayout>
       
      <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
      android:orientation="horizontal"
      android:layout_width="fill_parent"
      android:layout_height="wrap_content"
      android:layout_weight="1">
      <!-- Functionality Panel -->
      </LinearLayout>
       
      <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
      android:id="@+id/now_playing"
      android:layout_width="fill_parent"
      android:layout_height="90dip"
      android:orientation="horizontal">
      <!-- Update Panel -->
      </LinearLayout>
      </LinearLayout>
    • 11. Action Bar
      UI Design Patterns
      Action Bar
    • 12. Improved Title Bar
      Persistent across the application
      Includes common actions
      Navigation Control
      Action Bar
      UI Design Patterns
    • 13. Implementation
      UI Design Patterns
      <LinearLayoutxmlns:android="http://schemas.android.com/apk/res/android"
      android:orientation="horizontal"
      android:layout_width="fill_parent"
      android:layout_height="45dip"
      android:background="@color/action_bar_background">
      <ImageButtonstyle="@style/action_bar_button"
      android:src="@drawable/home_btn_default"
      android:onClick="onHomeClick"/>
       
      <ImageViewstyle="@style/action_bar_separator"/>
      <TextViewstyle="@style/action_bar_text"
      android:text="Sessions"/>
       
      <ImageViewstyle="@style/action_bar_separator"/>
      <ImageButtonandroid:id="@+id/search_button"
      style="@style/action_bar_button"
      android:src="@drawable/search_button"
      android:onClick="onSearchClick"/>
      </LinearLayout>
    • 14. Search Bar
      UI Design Patterns
      Search Bar
    • 15. Implement search in your app
      Persistent across the application
      Can be used with the Action Bar
      Multiple search modes
      A clearer way to filter results
      Search Bar
      UI Design Patterns
    • 16. Declare your application as searchable
      Declare an activity that handles the search
      Handle the search itself
      Implementation
      UI Design Patterns
    • 17. Declare in /res/xml/searchable.xml
      Searchable Configuration
      UI Design Patterns
      <?xmlversion="1.0"encoding="utf-8"?>
      <searchablexmlns:android="http://schemas.android.com/apk/res/android"
      android:label="@string/app_name"
      android:hint="Hint" >
      </searchable>
    • 18. Searchable Activity
      Declare as Searchable in the AndroidManifest.xml:
      UI Design Patterns
      <manifestxmlns:android="http://schemas.android.com/apk/res/android"
      package="com.alphacsp.theedge"
      android:versionCode="4"
      android:versionName="1.03"
      android:installLocation="preferExternal">
       
      <applicationandroid:label="TheEdge 2010"android:icon="@drawable/ic_launcher">
       
      <activityandroid:name=".ui.activities.SearchActivity"android:label="Search"android:theme="@style/Theme.TheEdge">
      <intent-filter>
      <actionandroid:name="android.intent.action.SEARCH"/>
      </intent-filter>
      <meta-dataandroid:name="android.app.searchable"android:resource="@xml/searchable"/>
      </activity>
      <activityandroid:name=".ui.activities.AboutActivity"android:label="About“ android:theme="@style/Theme.TheEdge"/>
       
      <meta-dataandroid:name="android.app.default_searchable"android:value=".ui.activities.SearchActivity"/> 
      </manifest>
    • 19. Searchable Activity
      Handle the Query:
      UI Design Patterns
      publicclassSearchActivityextendsTabActivity {
      @Override
      publicvoidonCreate(BundlesavedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.search_activity);
       
      Intentintent = getIntent();
      String query = intent.getStringExtra(SearchManager.QUERY);
       
      finalTabHost host = getTabHost();
       
      IntentspeakersIntent = new Intent(SearchActivity.this, SpeakersActivity.class);
      speakersIntent.putExtra(SearchManager.QUERY, query);
      host.addTab(host.newTabSpec("Speakers").setIndicator(buildIndicator("Speakers")).setContent(speakersIntent));
       
      IntentsessionsIntent = new Intent(SearchActivity.this, SessionsActivity.class);
      sessionsIntent.putExtra(SearchManager.QUERY, query);
      host.addTab(host.newTabSpec("Sessions").setIndicator(buildIndicator("Sessions")).setContent(sessionsIntent));
      }
    • 20. Quick Actions
      Quick context menu
      UI Design Patterns
    • 21. Contextual actions driven popup menu
      Natural flow to the screen context
      Simple and effective
      Wow effect
      Quick Actions
      UI Design Patterns
    • 22. Not in the SDK
      Custom Views
      Implementation taken from: Lorenz’s Bloghttp://www.londatiga.net/it/how-to-create-quickaction-dialog-in-android/
      Implementation
      UI Design Patterns
    • 23. Flingable List Item
      Flingable context menu
      UI Design Patterns
    • 24. Contextual actions driven flinged menu
      Natural flow to the screen context
      Wow effect
      Flingable List Item
      UI Design Patterns
    • 25. Major players:
      ViewFlipper Layout
      GestureDetector
      ListAdaptor
      ListActivity
      Implementation
      UI Design Patterns
    • 26. Vertical scrollable view that allows multiple rows views (List Item)
      Uses ListAdapter to populate each List Item
      Recycles Views (So don’t cache them!)
      Supports different view types
      A few words about ListView
      UI Design Patterns
    • 27. ListView should not hold N Views.
      Use ConvertView in getView method:
      ListView Recycler
      UI Design Patterns
      @Override
      publicViewgetView(int position, ViewconvertView, ViewGroup parent) {
      if (convertView == null) {
      convertView = inflater.inflate(R.layout.speakers_list, parent, false);
      }
      //Get your components from the view
      finalTextViewspeakerName = (TextView) convertView.findViewById(R.id.speaker_name);
       
      //Get your item
      Speakerspeaker = getItem(position);
      returnconvertView;
      }
    • 28. ListView Recycler in action
      UI Design Patterns
    • 29. ViewFlipper
      UI Design Patterns
      Allows transition between layouts
      Supports animations
      <ViewFlipperxmlns:android="http://schemas.android.com/apk/res/android"
      android:id="@+id/flipper"
      android:layout_width="fill_parent"
      android:layout_height="fill_parent">
      <includeandroid:id="@+id/first"layout="@layout/sessions_list"/>
      <includeandroid:id="@+id/second"layout="@layout/sessions_list_flinged"/>
      </ViewFlipper>
    • 30. GestureDetector
      UI Design Patterns
      Detects various gestures and events using the supplied MotionEvents
      GestureDetectorgestureDetector= newGestureDetector(newGestureDetector.SimpleOnGestureListener() {
      @Override
      publicbooleanonFling(MotionEvent e1, MotionEvent e2, floatvelocityX, floatvelocityY) {
      }
       
      @Override
      publicbooleanonDown(MotionEvent e) {
      }
       
      @Override
      publicbooleanonSingleTapUp(MotionEvent e) {
      }
      });
    • 31. Implementation
      UI Design Patterns
      Read the Source Code…
    • 32. I/O Access
    • 33. File System
      Database
      Network
      Types of I/O:
      I/O Access
    • 34. Reading is fast
      Writing is slow
      Disk space affects performance
      Make sure you support External Storage (Both in installation and in caches/data)
      Flash I/O
      I/O Access
    • 35. Virtual Table that allows Full Text Search
      Produces results significantly faster than LIKE
      Comprehensive syntax
      SQLite FTS
      I/O Access
    • 36. Creating FTS table
      Similar to creating a regular table:
      I/O Access
      publicclassDatabaseHelperextendsSQLiteOpenHelper { 
      privatestaticfinalStringDATABASE_NAME = "TheEdge";
      publicstaticfinalStringSPEAKERS_TABLE = "speakers";
       
      @Language("SQLite")
      privatestaticfinalStringCREATE_SPEAKERS_TABLE = "CREATE VIRTUAL TABLE " + SPEAKERS_TABLE + " USING fts3 (speaker_name TEXT , bio TEXT, company TEXT, image_uri TEXT)";
       
      publicDatabaseHelper(Contextcontext, String name, SQLiteDatabase.CursorFactory factory, int version) {
      super(context, name, factory, version);
      }
       
      @Override
      publicvoidonCreate(SQLiteDatabasesqLiteDatabase) {
      Log.i(this.getClass().getSimpleName(), "Creating DB");
      sqLiteDatabase.execSQL(CREATE_SPEAKERS_TABLE);
      }
       
    • 37. Using:
      Use the MATCH keyword:
      I/O Access
      publicList<Session> searchSessions(String query) {
      finalList<Session> sessionList = newArrayList<Session>();
      finalSQLiteDatabasereadableDatabase = getReadableDatabase();
      finalCursorcursor = readableDatabase.rawQuery("select * from " + SESSIONS_TABLE + " where " + SESSIONS_TABLE + " match '" + query + "'", null);
      if (cursor.moveToFirst()) {
      do {
      finalSessionsession = newSession();
      session.setTopic(cursor.getString(cursor.getColumnIndex("topic")));
      session.setPresenter(cursor.getString(cursor.getColumnIndex("presenter")));
      session.setSessionAbstract(cursor.getString(cursor.getColumnIndex("abstract")));
      sessionList.add(session);
      } while (cursor.moveToNext());
      }
      if (!cursor.isClosed()) {
      cursor.close();
      }
      returnsessionList;
      }
       
    • 38. Use a Service
      Use Apache HTTPClient not URLConnection
      Don’t do it on the UI thread
      Parsing can be costly, design your data structure carefully
      Network
      I/O Access
    • 39. When using network, remember the following:
      Availability:Always check connectivity with ConnectivityManager.
      Performance:Don’t run on the UI Thread, use AsyncTask or Service.
      Bandwidth:Use as little as you can.
      Battery drain:Only use the network when you have to.
      I/O Access
    • 40. I/O Access
      Activity with separate thread for Network
    • 41. Optimization
    • 42. Allows you to execute a task without having to manage thread pools.
      Defined by three generic types: Parameters, Progress and Result.
      Has a lifecycle:
      onPreExecute – Called before running the task.
      doInBackground – Actual work
      onProgressUpdate – Callback to update the UI on task progress
      onPostExecute – Called after task has ended, receives the response object
      Very smart and easy.
      AsyncTask
      Optimization
    • 43. In order to implment lazy loading, we’ll need to do the following:
      Load the ListView an you would normally do.
      Create a task to fetch the data, use AsyncTask or a Service.
      Change the data on the UI thread.
      Use notifyDataSetChanged() to let ListView to update itself.
      Lazy Loading your ListView
      Optimization
    • 44. Example
      Optimization
      publicclassSpeakersActivityextendsListActivityimplementsServiceListener {
       
      privatevoidfetchImages() {
      for (Speakerspeaker : speakers) {
      SpeakerImageFetcherspeakerImageFetcher = newSpeakerImageFetcher();
      speakerImageFetcher.execute(speaker);
      }
      }
       
      privateclassSpeakerImageFetcherextendsAsyncTask<Speaker, Void, Void> {
       
      @Override
      protectedVoiddoInBackground(Speaker... speakers) {
      finalSpeakerspeaker = speakers[0];
      finalBitmapbitmap = dataAccessor.fetchImage(speaker.getImageUrl());
      speaker.setSpeakerImage(bitmap);
      returnnull;
      }
       
      @Override
      protectedvoidonPostExecute(VoidaVoid) {
      speakersAdapter.notifyDataSetChanged();
      }
      }
      }
    • 45. Runs in the background
      Is not killed when the application ends
      Running a service is easy
      Getting callbacks is a bit awkward
      Declare it in your AndroidManifest.xml
      Services
      Optimization
    • 46. Services oriented application:
      Optimization
      SQLite
      HttpClient
      Data Accessor
      Service
      Service Helper
      Activity
    • 47. Service Example:
      Optimization
      publicclassNetworkServiceextendsIntentService {
       
      @Override
      protectedvoidonHandleIntent(Intent intent) {
      finalDataAccessordataAccessor = DataAccessor.getSingleton(this);
       
      finalResultReceiver receiver = intent.getParcelableExtra(STATUS_LISTENER);
      finalintrequestAction = intent.getIntExtra(REFRESH_ACTION, -1);
      boolean result = false;
       
      if (requestAction == REFRESH_SPEAKERS) {
      result = dataAccessor.syncAllSpeakers();
      } elseif (requestAction == REFRESH_SESSIONS) {
      result = dataAccessor.syncAllSessions();
      } elseif (requestAction == REFRESH_SCHEDULE) {
      result = dataAccessor.syncAllEvents();
      } elseif (requestAction == REFRESH_ALL) {
      dataAccessor.syncAllSpeakers();
      dataAccessor.syncAllSessions();
      dataAccessor.syncAllEvents();
      }
      if (result) {
      receiver.send(STATUS_REFRESHED, Bundle.EMPTY);
      }
      receiver.send(STATUS_NOT_REFRESHED, Bundle.EMPTY);
      }
      }
       
    • 48. ResultReceiver:
      Implements Parcelable, so can be passed in the Intent object
      Good for “Here and now” results per intent
      Getting a Callback from a Service:
      Optimization
    • 49. ResultReceiver Example
      Accepts the Activity as the Listener using a custom interface
      Optimization
      publicclassNetworkServiceHelperextendsResultReceiver {
        privatefinalServiceListenerlistener;
        publicNetworkServiceHelper(ServiceListener listener) {
      super(new Handler()); this.listener = listener;
      }
        @Override
      protectedvoidonReceiveResult(intresultCode, BundleresultData) {
      if (listener != null) {
      listener.onReceiveResult(resultCode, resultData);
      }
      }
      }
    • 50. Optimization
      Using the service:
      publicclassScheduleActivityextendsActivityimplementsServiceListener {
        privateNetworkServiceHelpernetworkServiceHelper;
        @Override
      publicvoidonCreate(BundlesavedInstanceState) {
      super.onCreate(savedInstanceState);
      setContentView(R.layout.schedule_activity);
      dataAccessor = DataAccessor.getSingleton(this);
      initCalendar();
      networkServiceHelper = newNetworkServiceHelper(this);
      finalIntentserviceIntent = new Intent(Intent.ACTION_SYNC, null, this, NetworkService.class);
      serviceIntent.putExtra(NetworkService.STATUS_LISTENER, networkServiceHelper);
      serviceIntent.putExtra(NetworkService.REFRESH_ACTION, NetworkService.REFRESH_SCHEDULE);
      startService(serviceIntent);
      }
      @Override
      publicvoidonReceiveResult(intresultCode, BundleresultData) {
      if (resultCode == NetworkService.STATUS_REFRESHED) {
      calendarLayout.removeAllViews();
      initCalendar();
      }
      }
      }
    • 51. Reference
    • 52. Reference
      http://developer.android.com/guide/index.html
      http://www.londatiga.net/it/how-to-create-quickaction-dialog-in-android/
      http://code.google.com/p/theedge2010/
      http://android-developers.blogspot.com/?hl=en
      http://www.google.com/events/io/2010/sessions.html#Android
      http://www.sqlite.org/fts3.html
      http://www.sqlite.org/cvstrac/wiki/wiki?p=FtsUsage
    • 53. Thank You!
      We appreciate your feedback

    ×