zoukankan      html  css  js  c++  java
  • 建立、配置和使用Activity——Activity

            Activity是Android应用中最重要、最常见的应用组件(此处的组件是粗粒度的系统组成部分,并非指界面控件:widget)。Android应用的一个重要组成部分就是开发Activity,下 面将会详细介绍Activity开发、配置的相关知识。

           Activity

           与开发Web应用时建立Servlet类相似,建立自己的Activity也需要继承Activity基类,当然,在不同应用场景下,有时也要求继承Activity的子类。例如如果应用程序界面只包括列表,则可以让应用程序继承ListActivity;如果应用程序界面需要实现标签页效果,则可以让应用程序继承TabActivity。

          图4.1显示了Android提供的Activity类。

     

           如图4.1所示,Activity类间接或直接地继承了Context、ContextWrapper、ContextThemeWrapper等基类,因此Activity可以直接调用它们的方法。

           与Servlet类似,当一个Activity定义出来之后,这个Activity类何时被实例化、它所包含的方法何时被调用,这些都不是由开发者决定的,都应该由安卓系统来决定。

          为了让Servlet能响应用户请求,开发者需要重写HttpServlet的doRequest(...)、doResponse(...)方法,或重写service(...)方法。Activity与此类相似,创建一个Activity也需要实现一个或多个方法,其中最常见的就是实现onCreate(Bundle status)方法,该方法将会在Activity创建时被回调,该方法调用Activity的setContentView(View view)方法来显示要展示的View。为了管理应用程序中的各种组件,调用Activity的findViewById(int id)方法来获取程序界面中的组价,接下来去修改格组件的属性和方法即可。

          实例:用LauncherActivity开发启动Activity的列表。

         通过前几章的实例介绍了Activity、ListActiviy、TabActivity等基类的用法,接下来开发一个继承LauncherActivity的应用。

          LauncherActivity继承了ListActivty,因此它本质上也是一个开发列表界面的Activity,但它开发出来的列表界面与普通列表界面有所不同。它开发出来的列表界面中的每个列表项都对应一个Intent,因此当用户单击不同的列表项时,应用程序会自动启动对应的Activity。

          使用LauncherActivity的方法并不难,由于依然是一个ListActivity,因此同样需要为它设置Adapter——既可使用简单的ArrayAdapter,也可使用SimpleAdapter,当然也可以扩展BaseAdapter来实现自己的Adapter。与使用普通ListActivity不同的是,继承LauncherActivity时通常应该重写Intent intentForPosition(int position)方法,该方法根据不同列表项返回不同的Intent(用于启动不同的Activity)。

          下面的程序中是一个LauncherActivity的子类。

    package com.example.studyactivity;
    
    import android.os.Bundle;
    import android.app.Activity;
    import android.app.LauncherActivity;
    import android.content.Intent;
    import android.view.Menu;
    import android.widget.ArrayAdapter;
    
    public class OtherActivity extends LauncherActivity {
    
        //定义两个Activity的名称
        String[] names={"设置程序参数","查看星际兵种"};
        //定义两个Activity对应的实现类
        Class<?>[] clazzs={PreferenceActivityTest.class,ExpandableListActivityTest.class};
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            ArrayAdapter<String> adapter=new ArrayAdapter<String>(this,
                    android.R.layout.simple_list_item_1,names);
            //设置该窗口显示列表所需的Adapter
            setListAdapter(adapter);
        }
        @Override
        protected Intent intentForPosition(int position) {
            // TODO Auto-generated method stub
            return new Intent(OtherActivity.this,clazzs[position]);
        }
        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            // Inflate the menu; this adds items to the action bar if it is present.
            getMenuInflater().inflate(R.menu.other, menu);
            return true;
        }
        
    }

    上面的程序中第一行粗体字代码为该ListActivity设置了所需的内容Adapter,第二段粗体字代码则根据用户单击的列表项去启动对一个的Activity。

        上面的程序还用到了如下两个Activity。

    •  ExpandableListActivityTest:它是ExpandableListActivityTest的子类,用于显示一个可展开的列表窗口。
    •  PreferenceActiviyTest:它是PreferenceActivity的子类,用于显示一个显示设置选项参数并进行保存的窗口。

        实例:使用ExpandableListActivity实现可展开的Activity  

        ExpandableListActivityTest,它继承了ExpandableListActivty的基类,ExpandableListActivity的用法与前面介绍的ExpandableListView的用法基本相似,只要为该Activity传入一个ExpandableListAdapter对象即可,接下来ExpandableListActivity将会生成一个显示可展开列表的窗口。

        下面是ExpandableListActivityTest的代码。

    package com.example.studyactivity;
    
    import android.os.Bundle;
    import android.app.Activity;
    import android.app.ExpandableListActivity;
    import android.database.DataSetObserver;
    import android.view.Gravity;
    import android.view.Menu;
    import android.view.View;
    import android.view.ViewGroup;
    import android.widget.AbsListView;
    import android.widget.ExpandableListAdapter;
    import android.widget.ImageView;
    import android.widget.LinearLayout;
    import android.widget.TextView;
    
    public class ExpandableListActivityTest extends ExpandableListActivity {
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            ExpandableListAdapter adapter=new ExpandableListAdapter(){
                int[] logos=new int[]{R.drawable.p,R.drawable.z,R.drawable.t};
                private String[] armTypes=new String[]{"神族兵种","虫族兵种","人族兵种"};
                private String[][] arms=new String[][]{
                        {"狂战士","龙骑士","黑暗圣堂","电兵"},
                        {"小狗","刺蛇","飞龙","自爆飞机"},
                        {"机枪手","护士MM","幽灵"}
                };
                @Override
                public boolean areAllItemsEnabled() {
                    // TODO Auto-generated method stub
                    return false;
                }
    
                @Override
                public Object getChild(int groupPosition, int childPosition) {
                    // TODO Auto-generated method stub
                    return arms[groupPosition][childPosition];
                }
    
                @Override
                public long getChildId(int groupPosition, int childPosition) {
                    // TODO Auto-generated method stub
                    return childPosition;
                }
                //该方法决定每个子选项的外观   
                @Override
                public View getChildView(int groupPosition, int childPosition, boolean isLastChild,
                        View convertView, ViewGroup parent) {
                    // TODO Auto-generated method stub
                    TextView textView=getTextView();
                    textView.setText(getChild(groupPosition,childPosition).toString());
                    return textView;
                }
    
                @Override
                public int getChildrenCount(int groupPosition) {
                    // TODO Auto-generated method stub
                    return arms[groupPosition].length;
                }
                
                private TextView getTextView()
                {
                    AbsListView.LayoutParams lp=new AbsListView.LayoutParams(ViewGroup.LayoutParams.FILL_PARENT,64);
                    TextView textView=new TextView(ExpandableListActivityTest.this);
                    textView.setLayoutParams(lp);
                    textView.setGravity(Gravity.CENTER_VERTICAL|Gravity.LEFT);
                    textView.setPadding(36, 0, 0, 9);
                    textView.setTextSize(20);
                    return textView;
                }
                @Override
                public long getCombinedChildId(long arg0, long arg1) {
                    // TODO Auto-generated method stub
                    return 0;
                }
    
                @Override
                public long getCombinedGroupId(long groupId) {
                    // TODO Auto-generated method stub
                    return 0;
                }
    
                @Override
                public Object getGroup(int groupPosition) {
                    // TODO Auto-generated method stub
                    return armTypes[groupPosition];
                }
    
                @Override
                public int getGroupCount() {
                    // TODO Auto-generated method stub
                    return armTypes.length;
                }
    
                @Override
                public long getGroupId(int groupPosition) {
                    // TODO Auto-generated method stub
                    return groupPosition;
                }
    
                 //该选项决定每个组选项的外观
                @Override
                public View getGroupView(int groupPosition, boolean isExpanded,
                        View convertView, ViewGroup parent) {
                    // TODO Auto-generated method stub
                    LinearLayout ll=new LinearLayout(ExpandableListActivityTest.this);
                    ll.setOrientation(0);
                    ImageView logo=new ImageView(ExpandableListActivityTest.this);
                    logo.setImageResource(logos[groupPosition]);
                    ll.addView(logo);
                    TextView textView=getTextView();
                    textView.setText(getGroup(groupPosition).toString());
                    ll.addView(textView);
                    
                    return ll;
                }
    
                @Override
                public boolean hasStableIds() {
                    // TODO Auto-generated method stub
                    return true;
                }
    
                @Override
                public boolean isChildSelectable(int groupPosition,
                        int childPosition) {
                    // TODO Auto-generated method stub
                    return true;
                }
    
                @Override
                public boolean isEmpty() {
                    // TODO Auto-generated method stub
                    return false;
                }
    
                @Override
                public void onGroupCollapsed(int groupPosition) {
                    // TODO Auto-generated method stub
                    
                }
    
                @Override
                public void onGroupExpanded(int groupPosition) {
                    // TODO Auto-generated method stub
                    
                }
    
                @Override
                public void registerDataSetObserver(DataSetObserver observer) {
                    // TODO Auto-generated method stub
                    
                }
    
                @Override
                public void unregisterDataSetObserver(DataSetObserver observer) {
                    // TODO Auto-generated method stub
                    
                }};
            //设置该窗口的显示列表
                setListAdapter(adapter);
        }
    
        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            // Inflate the menu; this adds items to the action bar if it is present.
            getMenuInflater().inflate(R.menu.expandable_list_activity_test, menu);
            return true;
    
        }
    
    }

    上面的程序中粗体字代码为ExpandableListActivity设置了一个ExpandableListAdpter对象,即可使得该Activity实现可展开列表的窗口。

        实例:PreferenceActivity结合PreferenceFragment实现参数设置界面

        PreferenceActivity是一个非常有用的基类,当我们开发一个Android应用程序时,不可避免地需要进行选项设置,这些选项设置会以参数的形式保存,习惯上我们会用Preferences进行保存。

        需要指出的是,如果Android应用程序中包含的某个Activity专门用于设置选项参数,那么Android为这种Activity提供了便捷的基类:PreferenceActivity。

        一旦Activity继承了PreferenceActivity,那么该Activity完全不需自己控制Preferences的读写,PreferenceActivity会为我们处理一切。

       PreferenceActivity与普通Activity不同,它不再使用普通的界面布局文件,而是使用选型设置的布局文件。选项设置的布局文件以PreferenceScreen作为根元素——它表明定义一个参数设置的界面布局。

        为了创建一个PreferenceActivity,需要先创建一个对应的界面布局文件。从Android3.0开始,Android不再推荐直接让PreferenceActivity加载选项设置的布局文件。而建议将PreferenceActivity与FreferenceFragment结合使用,其中PreferenceActivity只负责加载选项设置列表的布局文件,PreferenceFragment才负责加载选项设置的布局文件。

       本实例中PreferenceActivity加载的选项设置列表布局文件如下:

       

    <?xml version="1.0" encoding="utf-8"?>
    <preference-headers xmlns:android="http://schemas.android.com/apk/res/android" >
        <!-- 指定启动指定PreferenceFragment 的列表项 -->
       <header android:fragment="com.example.studyactivity.PreferenceActivityTest$Prefs1Fragment"
           android:icon="@drawable/ic_settings_applications"
           android:title="程序选项设置"
           android:summary="设置应用的相关选项"
           />
        <!-- 指定启动指定PreferenceFragment的列表项 -->
        <header android:fragment="com.example.studyactivity.PreferenceActivityTest$Prefs2Fragment"
            android:icon="@drawable/ic_settings_display"
            android:title="界面选项设置"
            android:summary="设置显示界面的相关选项">
            <!-- 使用extra可向Activity传入额外的数据 -->
            <extra android:name="website"
                android:value="www.crazyit.org"/>
        </header>
        <!-- 使用Intent启动指定Activity的列表项 -->
        <header android:icon="@drawable/ic_settings_display"
            android:title="使用Intent"
            android:summary="使用Intent启动某个Activity">
            <intent android:action="android.intent.action.VIEW"
                android:data="http://www.crazyit.org"/>
        </header>
    </preference-headers>

        上面的布局文件中指定使用Prefs1Fragment、Prefs2Fragment两个内部类,为此我们将会在PreferenceActivityTest类中定义这两个内部类。下面是PreferenceActivityTest的代码。

    package com.example.studyactivity;
    
    import java.util.List;
    
    import android.os.Bundle;
    import android.preference.PreferenceActivity;
    import android.preference.PreferenceActivity.Header;
    import android.preference.PreferenceFragment;
    import android.app.Activity;
    import android.view.Menu;
    import android.widget.Button;
    import android.widget.Toast;
    
    public class PreferenceActivityTest extends PreferenceActivity {
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            //该方法用于为该界面设置一个标题按钮
            if(hasHeaders())
            {
                Button button=new Button(this);
                button.setText("设置操作");
                //将该按钮添加到该界面上
                setListFooter(button);
            }
        }
        //重写该方法负责加载页面布局文件
        @Override
        public void onBuildHeaders(List<Header> target) {
            // TODO Auto-generated method stub
            
            //加载选项设置列表的布局文件
            loadHeadersFromResource(R.xml.preference_headers,target);
        }
        public static class Prefs1Fragment extends PreferenceFragment
        {
    
            @Override
            public void onCreate(Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                super.onCreate(savedInstanceState);
                addPreferencesFromResource(R.xml.preferences);
            }
        }
        
        public static class Prefs2Fragment extends PreferenceFragment
        {
    
            @Override
            public void onCreate(Bundle savedInstanceState) {
                // TODO Auto-generated method stub
                super.onCreate(savedInstanceState);
                addPreferencesFromResource(R.xml.display_prefs);
                //获取传入该Fragment的参数
                String website=getArguments().getString("website");
                Toast.makeText(getActivity(), "网站域名:"+website, Toast.LENGTH_LONG).show();
            }
            
            
        }
    
        @Override
        public boolean onCreateOptionsMenu(Menu menu) {
            // Inflate the menu; this adds items to the action bar if it is present.
            getMenuInflater().inflate(R.menu.preference_activity_test, menu);
            return true;
        }
    
    }

         上面的Activity重写了PreferenceActivity的public void onBuildHeaders(List<Header> target)方法,重写该方法指定加载前面定义preference_headers.xml布局文件。

         上面的Activity中定义了两个PreferenceFragment,它们需要分别加载preferences.xml、display_prefs.xml两个选项设置的布局文件。
          建立选项设置的布局文件需要创建根元素为PreferenceScreen的xml布局文件,它默认保存在/res/xml路径下。

         preferences.xml布局文件如下:

    <?xml version="1.0" encoding="utf-8"?>
    <PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android" >
        <!-- 设置系统铃声 -->
        <RingtonePreference 
            android:ringtoneType="all"
            android:title="设置铃声"
            android:summary="选择铃声(测试RingtionePreference)"
            android:showDefault="true"
            android:key="ring_key"
            android:showSilent="true"
            ></RingtonePreference>
        <PreferenceCategory android:title="个人信息设置组">
            <!-- 通过输入框填写用户名 -->
            <EditTextPreference
              android:key="name"
              android:title="填写用户名"
              android:summary="填写您的用户名(测试EditTextPreference)"
              android:dialogTitle="您所使用的用户名为:"  ></EditTextPreference>
            <!-- 通过列表框选择性别 -->
            <ListPreference 
                android:key="gender"
                android:title="性别"
                android:summary="选择您的性别(测试ListPreference)"
                android:dialogTitle="ListPreference"
                android:entries="@array/gender_name_list"
                android:entryValues="@array/gender_value_list"
                > </ListPreference >
        </PreferenceCategory>
        <PreferenceCategory  android:title="系统功能设置组">
            <CheckBoxPreference
                android:key="autoSave"
                android:title="自动保存进度"
                android:summaryOn="自动保存:开启"
                android:summaryOff="自动保存:关闭"
                android:defaultValue="true"> </CheckBoxPreference >
        </PreferenceCategory>
        
    
    </PreferenceScreen>

         上面的界面布局文件定义了一个参数设置界面,该参数设置界面中包括两个参数设置组,而且该惨呼设置界面全面应用了各种元素,这样方便读者以后查询。
         一旦定义了参数设置的界面布局文件之后,接下来在PreferenceFragment程序中使用该界面布局文件进行参数设置、保存十分简单,只要如下两步即可。

    1. 让Fragment继承PreferenceFragment
    2. 在onCreate(Bundle saveInstanceState)方法中调用addPreferencesFromRsource(...)方法加载指定的界面布局文件。

           上面的实例中还用到了一个display_prefs.xml选项设置布局文件,该布局文件的创建步骤与preferences.xml文件的创建步骤相同。该文件的代码如下:

    <?xml version="1.0" encoding="utf-8"?>
    <PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android" >
        <PreferenceCategory>
            <!-- 通过列表项选择灯光强度 -->
            <ListPreference android:key="light"
                android:title="灯光强度"
                android:summary="请选择灯光强度(测试ListPreference)"
                android:dialogTitle="请选择灯光强度"
                android:entries="@array/light_strength_list"
                android:entryValues="@array/light_value_list"/>
        </PreferenceCategory>
        <PreferenceCategory>
            <!-- 通过SwitchPreference设置是否自动滚屏 -->
            <SwitchPreference 
                android:key="autoScroll"
                android:title="自动滚屏"
                android:summaryOn="自动滚屏:开启"
                android:summaryOff="自动滚屏:关闭"
                android:defaultValue="true" />
        </PreferenceCategory>
        
    
    </PreferenceScreen>

    至此,我们为该应用程序开发了三个Activity类,但这三个Activity还不能使用,还必须在AndroidManifest.xml清单文件中配置Activity才行。

      配置Activity

      Android应用要求所有应用程序组件(Activty、Services、ContentProvider、BroadcastReceiver)都必须显示进行配置。

      只要为<application.../>元素添加<activity...>子元素即可配置Activity。例如下面的配置片段:

    <activity
                android:name="com.example.studyactivity.PreferenceActivityTest"
                android:icon="@drawable/ic_settings_applications"
                android:label="@string/title_activity_preference_activity_test" 
                android:exported="true"
                android:launchMode="singleInstance">
           ...                 
    </activity>

       从上面的配置片段可以看出,配置Activity时通常指定如下几个属性。

    1. name:指定该Activity的实现类的类名。
    2. icon:指定该Activity对应的图标。
    3. label:指定该Activity的标签。
    4. exported:指定该Activity是否允许被其他应用调用。如果将该属性设为true,那么该Activity将可以被其他应用调用。
    5. launchMode:指定该Activity的加载模式,该属性支持standard、singleTop、singleTask和singleInstance这4种加载模式。

          除此之外,配置Activity时通常还需要指定一个或多个<intent-filter.../>元素,该元素用于指定该Activity可响应的Intent。

     为了在AndroidManifest.xml布局文件中配置、管理上面的三个Activity,可以在清单文件的<application.../>元素中增加如下三个<activity.../>子元素

      <activity
                android:name="com.example.studyactivity.OtherActivity"
                android:label="@string/app_name" >
    <!--指定该Activity是程序的入口-->
                <intent-filter>
    
                    <action android:name="android.intent.action.MAIN" />
    
    
                  <category android:name="android.intent.category.LAUNCHER" /> 
                </intent-filter>
            </activity>
            <activity
                android:name="com.example.studyactivity.ExpandableListActivityTest"
                android:label="查看星际兵种" >
                
            </activity>
            <activity
                android:name="com.example.studyactivity.PreferenceActivityTest"
                android:icon="@drawable/ic_settings_applications"
                android:label="设置程序参数" 
               >
            </activity>

    上面的配置片段配置了三个Activity,其中第一个Activity还配置了一个<intent-filter.../>元素,该元素指定该Activity作为应用程序的入口。

         运行上面的应用程序,将看到如图4.6所示的界面。

     

      在图4.6所示的程序界面中,用户单击任意列表项即可启动对应额Activity,例如单击“设置程序参数”将会启动PreferenceActivityTest。单击“查看星际兵种”将会启动ExpandableListAcivityTest。单击4.6所示列表的第一个列表项将看到如图4.7所示的界面。

     图4.7就是利用PreferenceActivity生成的选项设置列表界面。这个界面只是包含三个列表项,其中前两个列表项用于启动PreferenceFragment,最后一个列表项将会根据Intent启动其他Activity。

      单击图4.7所示界面的第一个列表项,将可以看到如图4.8所示界面。

    图4.8所示界面就是利用PreferencesFragment生成的选项设置界面,这个界面非常漂亮,而且系统会自动将设置的参数永久地保存到系统中——这都得益于PreferenceActivity。例如我们单击图4.8所示界面中的“填写用户名”列表项,系统将会显示如图4.9所示的输入框。

    如果单击图4.6所示列表框中第二个列表项,将看到如图4.11所示的界面。

  • 相关阅读:
    [一步一步MVC]第二回:还是ActionFilter,实现对业务逻辑的统一Authorize处理 OnActionExecuting内如何获取参数
    携程SQL面试题忘大牛解答解决思路
    一些.Net面试题 (BS 方向)
    关于SQL SERVER高并发解决方案
    锁sql server锁
    MSSQL WITH (NOLOCK) 脏读
    python dict的函数
    conda常用命令
    sess.run() 中的fetches和feed_dict
    Tensorflow检验GPU是否安装成功 及 使用GPU训练注意事项
  • 原文地址:https://www.cnblogs.com/wolipengbo/p/3418364.html
Copyright © 2011-2022 走看看