Android source code learning-factory method mode application and advantages

Source: Internet
Author: User

Factory method mode definition:
Define an interface for creating an object, but let subclasses decide which class to instantiate. Factory Method lets a class defer instantiation to subclasses.
Defines an interface used to create objects, so that the subclass determines which class to instantiate. The factory method delays the instantiation of a class to its subclass.

Common factory method mode structure:

As shown in (from Head First Design Patterns), it consists of four parts:
Abstract Product is responsible for defining Product commonalities and implementing the definition of abstract things. Creator is an abstract creation class, that is, an abstract factory, the specific creation of product classes is completed by the specific implementation factory ConcreteCreator. In Head First Design Patterns, the factory method mode is described in detail. The original Article is as follows:
As in the official definition, you'll often hear developers say that the Factory Method lets subclasses decide which class to instantiate. they say "decides" not because the pattern allows subclasses themselves to decide at runtime, but because the creator class is written without knowledge of the actual products that will be created, which is decided purely by the choice of the subclass that is used.

What are the advantages of the factory method model?:
Good encapsulation and clear code structure. An object is created with constraints. If a caller needs a specific product object, you only need to know the class name of the product. You do not need to know the process of creating the object, reduces coupling between modules.

Good scalability. When a product category is added, you only need to modify the specific factory category or expand a factory category.
Block product categories. The caller does not need to care about how the product class is implemented. The caller only needs to care about the product interfaces. As long as the interfaces remain unchanged, the upper-layer modules in the system do not need to be changed. Because the instantiation of a product class is the responsibility of the factory class, the specific product generation of a product object is determined by the factory class. In addition, the factory method mode is a typical loosely coupled structure. The high-level module only needs to know the abstract class of the product, and other implementation classes do not need to be related. They comply with the dimit rule, the dependency inversion principle, and the Rys replacement principle.

In the Android source code, ListActivity inherits from Activity and uses Activity as the factory method to generate Activity with ListView characteristics. The following describes ListActivity:
An activity that displays a list of items by binding to a data source such as an array or Cursor, and exposes event handlers when the user selects an item.
ListActivity hosts a ListView object that can be bound to different data sources, typically either an array or a Cursor holding query results. Binding, screen layout, and row layout are discussed in the following sections.

Screen Layout
ListActivity has a default layout that consists of a single, full-screen list in the center of the screen. however, if you desire, you can customize the screen layout by setting your own view layout with setContentView () in onCreate (). to do this, your own view MUST contain a ListView object with the id "@ android: id/list" (or listif it's in code)

There is such a function in the Activity class.:Copy codeThe Code is as follows :/**
* This method is called after {@ link # onStart} when the activity is
* Being re-initialized from a previusly saved state, given here in
* <Var> savedInstanceState </var>. Most implementations will simply use {@ link # onCreate}
* To restore their state, but it is sometimes convenient to do it here
* After all of the initialization has been done or to allow subclasses
* Decide whether to use your default implementation. The default
* Implementation of this method performs a restore of any view state that
* Had previusly been frozen by {@ link # onSaveInstanceState }.
*
* <P> This method is called between {@ link # onStart} and
* {@ Link # onPostCreate }.
*
* @ Param savedInstanceState the data most recently supplied in {@ link # onSaveInstanceState }.
*
* @ See # onCreate
* @ See # onPostCreate
* @ See # onResume
* @ See # onSaveInstanceState
*/
Protected void onRestoreInstanceState (Bundle savedInstanceState ){
If (mWindow! = Null ){
Bundle windowState = savedInstanceState. getBundle (WINDOW_HIERARCHY_TAG );
If (windowState! = Null ){
MWindow. restoreHierarchyState (windowState );
}
}
}

In the comment, "but it is sometimes convenient to do it here after all of the initialization has been done or to allow subclasses to decide whether to use your default implementation. ", English is not good, but it generally means that the Activity subclass can reload this function to determine whether to use the default implementation.

Check the ListActivity subclass.:Copy codeThe Code is as follows: public class ListActivity extends Activity {
/**
* This field shoshould be made private, so it is den from the SDK.
* {@ Hide}
*/
Protected ListAdapter mAdapter;
/**
* This field shoshould be made private, so it is den from the SDK.
* {@ Hide}
*/
Protected ListView mList;
Private Handler mHandler = new Handler ();
Private boolean mFinishedStart = false;
Private Runnable mRequestFocus = new Runnable (){
Public void run (){
MList. focusableViewAvailable (mList );
}
};
/**
* This method will be called when an item in the list is selected.
* Subclasses shocould override. Subclasses can call
* GetListView (). getItemAtPosition (position) if they need to access
* Data associated with the selected item.
*
* @ Param l The ListView where the click happened
* @ Param v The view that was clicked within the ListView
* @ Param position The position of the view in the list
* @ Param id The row id of the item that was clicked
*/
Protected void onListItemClick (ListView l, View v, int position, long id ){
}
/**
* Ensures the list view has been created before Activity restores all
* Of the view states.
*
* @ See Activity # onRestoreInstanceState (Bundle)
*/
@ Override
Protected void onRestoreInstanceState (Bundle state ){
EnsureList ();
Super. onRestoreInstanceState (state );
}
/**
* @ See Activity # onDestroy ()
*/
@ Override
Protected void onDestroy (){
MHandler. removeCallbacks (mRequestFocus );
Super. onDestroy ();
}
/**
* Updates the screen state (current list and other views) when
* Content changes.
*
* @ See Activity # onContentChanged ()
*/
@ Override
Public void onContentChanged (){
Super. onContentChanged ();
View emptyView = findViewById (com. android. internal. R. id. empty );
MList = (ListView) findViewById (com. android. internal. R. id. list );
If (mList = null ){
Throw new RuntimeException (
"Your content must have a ListView whose id attribute is" +
"'Android. R. id. list '");
}
If (emptyView! = Null ){
MList. setEmptyView (emptyView );
}
MList. setOnItemClickListener (mOnClickListener );
If (mFinishedStart ){
SetListAdapter (mAdapter );
}
MHandler. post (mRequestFocus );
MFinishedStart = true;
}
/**
* Provide the cursor for the list view.
*/
Public void setListAdapter (ListAdapter adapter ){
Synchronized (this ){
EnsureList ();
MAdapter = adapter;
MList. setAdapter (adapter );
}
}
/**
* Set the currently selected list item to the specified
* Position with the adapter's data
*
* @ Param position
*/
Public void setSelection (int position ){
MList. setSelection (position );
}
/**
* Get the position of the currently selected list item.
*/
Public int getSelectedItemPosition (){
Return mList. getSelectedItemPosition ();
}
/**
* Get the cursor row ID of the currently selected list item.
*/
Public long getSelectedItemId (){
Return mList. getSelectedItemId ();
}
/**
* Get the activity's list view widget.
*/
Public ListView getListView (){
EnsureList ();
Return mList;
}
/**
* Get the ListAdapter associated with this activity's ListView.
*/
Public ListAdapter getListAdapter (){
Return mAdapter;
}
Private void ensureList (){
If (mList! = Null ){
Return;
}
SetContentView (com. android. internal. R. layout. list_content_simple );
}
Private AdapterView. OnItemClickListener mOnClickListener = new AdapterView. OnItemClickListener (){
Public void onItemClick (AdapterView <?> Parent, View v, int position, long id)
{
OnListItemClick (ListView) parent, v, position, id );
}
};
}

The onRestoreInstanceState (Bundle state) function is rewritten, and the default setContentView (com. android. internal. R. layout. list_content_simple) is set in the View );Copy codeThe Code is as follows :/**
* Ensures the list view has been created before Activity restores all
* Of the view states.
*
* @ See Activity # onRestoreInstanceState (Bundle)
*/
@ Override
Protected void onRestoreInstanceState (Bundle state ){
EnsureList ();
Super. onRestoreInstanceState (state );
}
...
Private void ensureList (){
If (mList! = Null ){
Return;
}
SetContentView (com. android. internal. R. layout. list_content_simple );
}

SetContentView () function in Activity:Copy codeThe Code is as follows :/**
* Set the activity content from a layout resource. The resource will be
* Inflated, adding all top-level views to the activity.
*
* @ Param layoutResID Resource ID to be inflated.
*
* @ See # setContentView (android. view. View)
* @ See # setContentView (android. view. View, android. view. ViewGroup. LayoutParams)
*/
Public void setContentView (int layoutResID ){
GetWindow (). setContentView (layoutResID );
InitActionBar ();
}
/**
* Set the activity content to an explicit view. This view is placed
* Directly into the activity's view hierarchy. It can itself be a complex
* View hierarchy. When calling this method, the layout parameters of
* Specified view are ignored. Both the width and the height of the view are
* Set by default to {@ link ViewGroup. LayoutParams # MATCH_PARENT}. To use
* Your own layout parameters, invoke
* {@ Link # setContentView (android. view. View, android. view. ViewGroup. LayoutParams )}
* Instead.
*
* @ Param view The desired content to display.
*
* @ See # setContentView (int)
* @ See # setContentView (android. view. View, android. view. ViewGroup. LayoutParams)
*/
Public void setContentView (View view ){
GetWindow (). setContentView (view );
InitActionBar ();
}
/**
* Set the activity content to an explicit view. This view is placed
* Directly into the activity's view hierarchy. It can itself be a complex
* View hierarchy.
*
* @ Param view The desired content to display.
* @ Param params Layout parameters for the view.
*
* @ See # setContentView (android. view. View)
* @ See # setContentView (int)
*/
Public void setContentView (View view, ViewGroup. LayoutParams params ){
GetWindow (). setContentView (view, params );
InitActionBar ();
}

Summary: Activity is used as the "Factory method". The default setting or subclass is used to display the content in the specific View. The ListActivity is used as the actual implementation, and the ListView is used to display the content in the View; the View here is the default display in the Activity, that is, "Product", while the ListView is "ConcreteProduct", which is determined by the ListActivity.

In addition to ListActivity, ExpandableListActivity also uses Activity as the factory class to create its own display effect.
My skills and time are limited (I will add content in the future due to lack of "mode usage"). I am very rough in writing. I am waiting for your criticism. Thank you ~~~

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.