安卓筆記-視頻版(還沒學完)

/Users/yangyangzi/Desktop/YangZi2/android/Android12/2019/視頻學習.rtfd (公司電腦)

視頻

一、控件:TextView:標籤,用於顯示內容,內容不可編輯;Plain Text:內容可編輯;Button; imageView;imageButton:帶有點擊功能的圖片;checkBox複選框;RadioButton單選按鈕;radioGroup只能選一個

layout_width 

一查看註釋方法:選中-》View-》Quick Documentation 快捷鍵F1

格式化代碼:Option + cmd +L 

刪除整行:cmd + delete

光標到行首:cmd + <—

查找類:cmd+o

查看文件結構:cmd + F12

textStyle

textColor:安卓是十六進制顏色,需以#開頭 

#RGB #F00(純紅)

#ARGB  #FF00(純紅)

#RRGGBB #FF0000 

#AARRGGBB  #FFFF0000 

二、Button繼承自TextView

響應點擊事件:在代碼裏註冊View.OnClickListener監聽器

註冊View.OnClickLister方法分以下三種:

內部類

匿名類

XML設置android:onClick

在activity中實現???

外部類的方式來實現???

三、EditText 繼承自TextView

inputType 輸入類型,小數點等

hint placeholder,輸入提示

android:singleLine="true"  單行輸入

android:background="@color/colorAlpha" 設爲透明,下劃線幾小時

 

四、imageView及ImageButton(ImageButton是ImageView的子類)

設置圖片:

1、在xml文件中設置是android:src 

2、在代碼中設置是testIMV.setImageResource(R.mipmap.teacher_dev);

圖片與button小demo練習

android:scaleType="fitXY" 圖片的mode

 

 

五、選項控件

單選框:

RadioButton繼承自CompoundButton

   isChecked();確定是否被選中

   setChecked();強制選中或取消選中複選框

   setOnCheckedChangeListener事件監聽

   OnCheckedChangeListener事件回調

 

六、複選框

 CheckBox

 

StringBuilder  可變字符串

 

七、資源的使用

1、字符串資源 工程ResourceString

  字符串本地化或國際化

支持中文本地化:

  在res/文件夾下創建名爲values-zh的文件夾,將res/values文件夾下的string.xml文件複製到新建的values-zh文件夾下。注意在values與values-zh文件夾下的string.xml文件裏的鍵必須是共同存在的,即前者有哪個鍵值對,後者也必須有相應的鍵值對,否則會報錯;注意:鍵不能重複,值能重複;注意鍵值對要放在reasource下

xml中取string.xml中字符串值:android:text="@string/yh_world"

代碼中取string.xml中的字符串值:buttonYh.setText(R.string.yh_world);

獲取resource資源:

Resources res = getResources();

通過resource資源獲取具體資源:

String fdd = res.getString(R.string.yh_world);

鍵值對放在string下:<string name="yh_world">YH_WORLD</string>

在string.xml中添加鍵值對;也可以在調用的地方添加,例如按鈕在Attributes的text屬性右側有三個點,點擊此三個點即可選擇已有鍵值對或添加新的鍵值對

name要小寫

2、顏色資源 工程ResourceString

鍵值對放在color下:<color name="yhred">#FF0000</color>

 

3、圖片資源 工程ResourceString

drawable文件夾下:buttonYh.setBackgroundResource(R.drawable.tefreshing01);

mipmap文件夾下:imageBtns.setImageResource(R.mipmap.tefreshing02);

在xml中引用圖片:android:roundIcon="@mipmap/ic_launcher_round"

圖片放在相應資源下

 

4、尺寸資源 工程ResourceString

一般用dp或sp做長度單位,與屏幕的物理長度無關

Xml中引用:android:layout_marginBottom="@dimen/yh_width"

 

鍵值對放在dimen下:<dimen name="yh_height">50</dimen>

 

八、觸屏事件:

工程TouchScreen

重寫方法的快捷鍵 ctrl + o

on開頭的方法一般都是回調方法:

1、觸摸屏幕

    重寫onTouchEvent方法

 

2、觸摸屏幕上的某個控件

安卓事件分發機制詳解:Android事件分發機制詳解:史上最全面、最易懂太長了

 

九、線性與相對佈局

《一》線性佈局

LinearLayout:在一個方向上佈局

1、orientation:方向:orientation 水平or豎直

2layout_gravity對齊方式:layout_gravity 左 右 中間 上 下對齊 默認左上對齊

3layout_weight權重:佔父控件的百分比;eg:兩個按鈕,各佔屏幕的50%,則兩個按鈕設置如下屬性值爲:layout_width=“0dp” layout_weight=”1“;

方式:gravity 文字對齊android:gravity="left"

當有layout_weight用法

orientation vertical時,則豎直方向的layout_height取值不起作用

orientation horizontal時,則水平方向的layout_width取值不起作用

java將int轉變爲string方法:

1、buttonView.getId() + "" 

2、String.valueOf(buttonView.getId())

LinearLayoutTest工程有問題???,待解決

java中的 a |= b 即 a = a || b

CheckBox的setChecked的方法中調用了onCheckedChanged方法

 

2019.2.15

《二》相對佈局RelativeLayout:

1、相對於容器; 工程RelativeLayout

layout_alignParentTop = "true"

layout_alignParentBottom = "true"

layout_alignParentLeft = "true"

layout_alignParentRight = "true”

layout_centerInParent = "true"

 

2、相對於控件; 工程RelativeLayout

根據id做控件對齊依據

layout_above="@id/button1"  其下邊與button1的上邊挨着

layout_below="@id/button1"  其上邊與button1的下邊挨着

 

layout_alignLeft="@id/button1" 其與button1的左邊對齊

layout_alignTop="@id/button1"  其與button1的上邊對齊

 

layout_toLeftOf="@id/button1"  其右邊與button1的左邊挨着

layout_toRightOf="@id/button1" 其左邊與button1的右邊挨着

 

3、基線對齊 工程RelativeLayout2

layout_alignBaseline="@id/rightET" rightET的底部基線對齊

 

2019.2.18

佈局公有屬性

Padding:控件的內容與控件邊緣的距離;

Margin:控件與控件的相對距離;包括子控件與父控件邊緣距離

 

線性與相對佈局的嵌套使用:工程LinearAndRelative

字體大小:textSize

子視圖在俯視圖的佈局:margin

LayOut文件出問題,不報錯,卻運行不了,太坑了,寫錯了也不知道,太坑

嵌套原則:層數越少約好,越簡單約好

 

《三》表格佈局:TableLayout

1》、在行中添加單元格TableRow:

android:layout_column="2" 指明列數

android:layout_span="2" 橫向合併列

沒有添加tableRow的情況,則一個控件佔一行

注意:一個TableviewLayout有幾行是根據TableRow的個數決定的

而有每個TableRow有幾列不是其本身的TableRow上控件個數決定的,而是由其上下文決定的,即看此TableLayout中哪個TableRow的控件個數最多,按這個最多的TbaleRow的控件個數決定

2》、擴展、收縮和摺疊

擴展:android:stretchColumns="1" 第一列可以擴張,佔tableRow剩下的所有寬度

收縮:android:shrinkColumns="1"  內容長時第一列可以收縮自動換行

摺疊:android:collapseColumns="1" 隱藏第一列

只能合併列,不能合併行

 

《四》網格佈局:GridLayout

可以設置

組件的排列方式:android:orientation="vertical”默認是horizontal

行數:android:rowCount="6"

列數:android:columnCount="4"

合併兩行:android:layout_rowSpan="2"

合併三列:android:layout_columnSpan=“3”

填充合併的行或列:android:layout_gravity="fill”(layout_gravity還可以取值center/left/right/buttom及相應的_horizontal_vertical)

 

《五》幀佈局:FrameLayout 三星

顯示的控件都會放在屏幕左上角,不能指定位置

當有多個顯示對象,後一個將會遮蓋住前一個

 

《六》佈局:DrawerLayout 一星

能實現DrawerLayout效果的關鍵是:android:layout_gravity = "start"

android:gravity是對view控件本身來說的,是用來設置view本身的內容應該顯示在view的什麼位置,默認值是左側。也可以用來設置佈局中的控件位置;

表示當前View,即控件,內部的東西的,對齊方式

.android:layout_gravity是相對於包含該元素的父元素來說的,設置該元素在父元素的什麼位置;

表示當前View,即控件本身在父一級內的對齊方式

gravity與layout_gravity的區別:https://www.cnblogs.com/fuck1/p/5461952.html

 

《七》佈局:ScrollVIew 一星 extens FrameLayout

ScrollView和HorizontalScrollView只能有一個子控件,一般會放個LinearLayout

ScrollView用於設置垂直滾動條;HorizontalScrollView用於設置水平滾動條

隨意

 

2019.2.19

消息處理機制

主線程超過5秒爲響應,則系統會彈ANR框報錯 Sorry 。。。is not 

responding

一、消息隊列 

消息循環產生消息隊列

Activity用消息隊列(Message Queue)機制保證線程間通信

消息隊列用來存放Handler發佈的消息

安卓在程序第一次啓動時會默認爲UI線程(主線程)創建一個關聯消息隊列,用來管理程序的組件,如Activity,Service,Broatcast Receiver等

不同線程用Handler來使子線程和主線程通信

可以在子線程(工作線程中)創建Handler與主線程通信

 

主線程創建looper,looper裏存放消息隊列,消息隊列裏存message

 

二、Handler的消息傳遞機制 工程MessageRules

1、子線程通過Handler與主線程通訊

2、Handler對象的所有工作將在主線程中執行

3、Handler需要實現handleMessage()方法,來處理消息隊列中去除的Message對象

4、handleMessage()方法由主線程調用,可以在需要的時候更新UI界面。但是,必須確保此方法快速完成,因爲其他UI操作會等待它完成才能執行

5、可以在Message中附加不同參數 water標示;avg1,avg2傳遞int類型數據;obj傳遞對象類型的數據

 

三、Handler的編程接口

方法

void handleMessage(Message message) 在主線程處理消息

boolean sendEmptyMessage(int what)  發送空消息,此參數是一個消息標示

boolean sendMessage(Message message) 發送消息到Handler中,在handleMessage中處理

boolean hasMessage(int what) 判斷是否有what消息

boolean post(Runnable r) 將一個Runnable添加到消息隊列

 

XML的解析:

1、xml文件放在res/xml目錄下,注意res下默認沒有xml文件夾,需要手動創建該文件夾,若果單純放在res文件夾下回報錯

2、xml文件在部署時將被編譯爲有效的二進制文件

3、根據需要可以自定義xml結構

4、安卓使用pull方式解析xml,本事是SAX解析(事件驅動,需要知道事件)

XMLPullPaser

寫示例

Java的拋異常機制???

效率好低啊

 

JSON解析

在res文件夾下新建raw文件

期初加入到raw文件夾下的文件名爲parJson.json,後報錯,把文件名的大寫J改爲小寫j即可

 

線程使用場景:解析xml並展示在listView上

工程:SimpleAdapterTest

1、onCreate方法中,創建子線程,並在子線程中添加要執行的異步操作(在run方法中),解析完文件,通過sendmessage回到主線程:

 new Thread(){

            @Override

            public void run() {

                try {

                    parseXml();

                    handler.sendEmptyMessage(what);

                } catch (XmlPullParserException e) {

                    handler.sendEmptyMessage(lala);

//                    e.printStackTrace();

                } catch (IOException e) {

                    handler.sendEmptyMessage(lala);

//                    e.printStackTrace();

                }

 

            };

        }.start();

2、回到主線程在,handler的handleMessage方法將得到的數據複製到主線程的listview

注意:不能再子線程處理控件,否則報錯,需要回歸到主線程再操作主線程

 

 

2.21 StringBuilder的.append(name)方法,傳參不能爲空

控件

 

消息提示Toast:

彈出Toast:短暫彈框,不用用戶響應

靜態方法:makeText()

構造函數:new ;setView();setDuration()

自定義Toast:通過LayoutInflater.from加載自定義view

View tview = LayoutInflater.from(this).inflate(R.layout.toast_self_defined_view, null);

 

AlertDialog:通過Builder創建,鏈式語法.set設置:

1》提醒框: AlertDialog

以下對話框都是AlertDialog,只是參數不同:

列表對話框:

2》單選列表對話框:AlertDialog

.setSingleChoiceItems(ddArray, 1, new DialogInterface.OnClickListener() {

    @Override

    public void onClick(DialogInterface dialog, int which) {

        Log.d("TEST", "" + which + "");

    }

})

 

3》多項選擇列表對話框;AlertDialog

.setMultiChoiceItems(sdff, new boolean[]{false, true, true}, new DialogInterface.OnMultiChoiceClickListener() {

    @Override

    public void onClick(DialogInterface dialog, int which, boolean isChecked) {

        Log.d("TEST", which + "," + isChecked);

    }

})

 

4》普通列表對話框 AlertDialog

無.setxxChoiceItems()方法

 

進度條對話框:ProcessDialog(圓圈或長條)

 

自定義對話框:工程SelfDefinedDialog

方式一:產生一個Dialog類實例:setContentView(View view)設置自定義的視圖:

twoDialog = new Dialog(this);

twoDialog.dismiss();

 

方式二:使用AlertDialog.Builder創建AlertDialog實例:setView(View view)設置自定義視圖;.create()創建對象  工程 SelfDefinedDialog

內部類要用到外部類的局部變量,需要用final修飾此局部變量

 

2019.2.25

適配器:Adapter

   負責爲選擇部件提供數據源,也負責將單獨的數據元素轉換爲顯示在選擇部件中的特定視圖

ArrayAdapter的三個參數:(安卓系統寫好的適配器)

      參一:上下文,通常是當前activity的實例

      參二:使用的視圖資源的ID

      參三:要實際顯示的選項數組或列表

 

列表:ListView

示例工程:AdapterAndListview

ArrayAdapter arrayAdapter = new ArrayAdapter(

        this,

        android.R.layout.simple_list_item_1,

        android.R.id.text1,

        data

);

listView.setAdapter(arrayAdapter);

 

 

 

SimpleAdapter:將xml解析並賦值給listview

    listView = findViewById(R.id.listview);

    SimpleAdapter simpleAdapter = new SimpleAdapter(

        this,//上下文

        data,//數據源

        R.layout.list_item,//項佈局

        new String[]{"name","age"},//顯示數據在數據源中的key

        new  int[] {R.id.leftTV, R.id.rightTV }//顯示數據的控件id

     );

    listView.setAdapter(simpleAdapter);

 

 

private static  final int what = 1001; 修飾詞這麼多

 

BaseAdapter:

工程:BaseAdapterTest

BaseAdapter 只是一個父類,在使用時需要創建繼承自BaseAdapter的子類

  ListView提高效率(相當於ios的cell重用機制);

工程:BaseAdapterAndEfficientTest  2.26

public View getView(int position, View convertView, ViewGroup parent) {}方法的covertView參數相關的重用機制,

獲得自定義xml的解析方法是dom解析,此種解析方法每次解析都會將文件放入內存,如果沒有使用重用機制就太浪費空間了,故我們在這創建了一個ViewHolder持有者,對自定義xml的子控件進行緩存持有。

此例用count值查看是否重用了;

ListView提高效率:使用ConterView+使用持有者模式

 

GridView:網格控件與上邊的ListView相似(ios的collectionview)

    與listview一樣都是選項控件,用適配器:

    verticalSpacing:垂直間距

GridView隨着數據的刷新而更新:工程AdapterRefresh (數據更新reload;按鈕的點擊事件寫法3:視頻裏extends Activity;而現在AS是extends AppCompatActivity,故這種事件點擊方式不適用AS

public class AdapterRefresh extends AppCompatActivity implements OnClickListener{

@Override

protected void onCreate(Bundle savedInstanceState) {

    super.onCreate(savedInstanceState);

    addBtn.setOnClickListener(this);

}})

   

String name = editText.getText().toString().trim();

方法trim()的作用:去掉字符串收尾的空格

通知數據修改Adapter的notifyDataSetChanged()方法

 

Spinner:顯示下拉式內容,顯示多項內容的選擇控件

工程:SpinnerTest

1》通過Adapter添加數據 topSpinner.setAdapter()

2》在xml文件中通過屬性entries添加字符串資源數組添加數據 android:entries="@array/name_string_array"

進階:聯動spinner(班級:學生級聯菜單)工程SpinnerTest(自己寫的有問題) + 工程SpinnerLianDongTest(視頻的)

注:開始自己寫的工程SpinnerTest來演示聯動spinner,總是編譯不過,經過各種嘗試,發現是泛型使用不規範引起的,看來java對泛型的要求很高啊,以後凡是數組一定要加上泛型(ios在泛型這塊就沒那麼苛刻了)

java數組:

private List <String>leftArray new ArrayList<String>();

leftArray.add("安卓");

leftArray.add("蘋果");

private String[] leftArray = {"安卓", "蘋果"};

有啥區別?

前者是集合,後者纔是數組待java書到之後細研究

 

Activity配置:

四大組件之一;組件必須在AndroidManifest.xml中說明才能使用

AndroidManifest.xml文件中的

1、package="com.example.yangyangzi.spinnertest”是包名

<activity android:name=".SpinnerTest"> 此處是類名

2、<activity android:name=".SecondActivity"

          android:label="第二個Activity"></activity>

   此處的android:label默認是

   <application

    android:allowBackup="true"

    android:label="@string/app_name”>處的label

 

Activity之間的跳轉:

通過intent跳轉:

顯式跳轉:通過目標Activity名稱跳轉

Intent intentt = new Intent(this,SecondActivity.class);

startActivity(intentt);

{

//        Intent intent = new Intent();

//        intent.setClass(this,SecondActivity.class);

//        startActivity(intent);

}

 

隱式跳轉:通過activity的邏輯動作名跳轉,可以不暴露目標Activity的名稱

AndroidManifest.xml:

<activity android:name=".ThirdActivity"

    android:label="第三個Activity">

    <intent-filter>

        <!--自定義邏輯動作名-->

      <action android:name="yhaction"/>

      <category android:name="android.intent.category.DEFAULT"/>

    </intent-filter>

</activity>

 

Intent intent = new Intent();

intent.setAction("yhaction");

startActivity(intent);

 

 

Activity間通訊:

啓動Activity:startActivity;startActivityForResult:啓動過程有返回

通過:intent.putExtras(Bundle); intent.putExtra(key,value);傳值到另一個組件

接收:目標組件通過getIntent()得到intent,通過getExtras方法得到所傳的對象

工程:ActivityPassSomething

 

Activity返回值:

開始Activity:

       startActivityForResult() 啓動Activity

       onActivityResult() 接收目的Activity返回的數據

目標Activity:

       setResult(code,intent); 目標Activity設置返回的內容

 

Activity生命週期:示例工程:LifeOfActivity

onCreate創建,在整個生命週期只調用一次

onStart加載到內存,Activity不可見,啓動

onResume顯示,Activity可見

onPause失焦點,Activity可見,但是不能操作

onStop被其他Activity蓋掉,Activity不可見,未銷燬

onDestory 在整個生命週期只調用一次,

點back則onDestory了

線程Thread中,返回到主線程的另一方法:

線程的終止居然用boolean屬性值和死循環實現

 

new Thread(){

    @Override

    public void run() {

       count++;

            handler.post(new Runnable() {

                @Override

                public void run() {

                    //運行在主線程中

                    textView.setText("" + count);

                }

            });

    }

}.start();

 

Activity的啓動模式:4種launchMode

在AndroidManifest.xml中設置模式launchMode

<activity android:name=".SingleInstanceActivity"

    android:label="SingleInstanceActivity"

    android:launchMode="singleInstance"

    ></activity>

 

1、standard(默認):每次激活Activity都會重新創建,並放入任務棧中

2、singleTop:如果在任務的棧頂正好存在該Activity的實例,就會重用該實例,而不會重新創建新的Activity對象,不過它會調用onNewIntent()方法;如果棧頂不存在就會創建新的實例並放入棧頂(即使棧中已經存在該Activity實例,只要不在棧頂,都會創建實例)。不會調用onNewIntent()方法

注:Activity中this.toString()結果 一般都是包名+@+16進制字符串

3、singleTask:如果在棧中有改Activity實例,就重用該實例(會調用實例的onNewIntent()方法);

重用時,會讓該實例回到棧頂,因此在它上面的實例將會被移除棧。

如果棧中不存在該實例,將會創建新的實例放到棧中

在棧中只有一個

 

4、singleInstance:與singleTask模式的區別是存放singleInstance模式窗口對象的回退棧不能有其他任何窗口對象。因此如果該窗口不存在,則要新建任務來存放該singleInstance窗口???

即創建了一個新的棧,可以理解爲單例模式

單例的理解如下圖:

 

對上圖的解釋(也是singleInstance模式的精髓)

現在有兩個Activity,即MainActivity(除SingleInsatnce模式以外的其他模式)和SingleInstanceActivity(SingleInstance模式):

由MainActivity跳到SingleInstanceActivity(創建新的SingleInstanceActivity),

再由SingleInstance跳到MainActivity(創建新的MainActivity),

再由MainActivity跳到SingleInstanceActivity(用舊的SingleInstanceActivity),

再由SingleInstance跳到MainActivity(創建新的MainActivity),三

再由MainActivity跳到SingleInstanceActivity(用舊的SingleInstanceActivity) 四

注意以上跳轉是互相調用而非返回

MainActivity無論屬於哪種模式在這種情況,按正常走都得新建;SingleInstanceActivity因爲是SingleInstance模式的只用新建一次(跟單例差不多)

接下來,在上邊操作步驟基礎上,

做回退操作(當前在SingleInstanceActivity裏即從四開始回退):

在SingleInstanceActivity時點擊返回按鈕,退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,退到桌面

SingleInstance回退一次,在回退則進入正常的任務棧,將此棧的所有Activity銷燬後,之後再點一次返回則退到home

 

做回退操作(當前在MainActivity裏即從三開始回退):

在MainActivity頁面點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到MainActivity,

再點返回按鈕,還是退到SingleInstanceActivity,

再點返回按鈕,退到桌面

說明先是把正常的任務棧的所有Activity銷燬後再點返回纔會跳到SingleInstance模式的Activity,之後再點一次返回則退到home

 

 

注:finish()與點返回按鈕當前Activity都被從任務棧中移除

棧id:棧的唯一標識符

靈活使用四種Activity模式可以節約系統資源

 

Fragment的生命週期和使用:

  Fragment是在Android3.0(API level 11)開始引入新的API技術。

  爲提高代碼重用性和改善用戶體驗,我們將Activity中的UI組件進行分組和模塊化管理。這些分組後的UI組件就是Fragment。

  一個Activity可以包含多個Fragment模塊,而同一個Fragment模塊也可以被多個Activity使用。

  每個Fragment有自己的佈局,有自己是生命週期。

 我們可以設計Fragment的佈局

 Fragments必須放在一個Activity中,

 Fragments有自己的生命週期,而且受到它所在宿主Activity是聲明週期的影響

Fragmens可以接收它自己是事件

一個Fragment可以放在多個Activity中,一個Activity也可以放置多個Fragments

Fragment的生命週期:

     創建一個Fragment需要實現是回調函數:

     onCreate():創建Fragment時系統會調用此函數

     onPause():當用戶離開當前Fragment時調用此方法。通常用來保存持久化數據

     OnCreateView():當Fragment第一次繪製它的UI時調用。這個方法必須返回一個View,表示這個Fragment的根佈局

 

創建Fragment,如果用到早期的Android系統如2.2,2.3則需要繼承自android.support.v4.app.Fragment()即minSdkVersion<11時繼承自v4 jar包;其他直接繼承自系統的Fragment的jar包,安卓3.0以上

 

Fragment的生命週期:

 [Fragment is added]->onAttach()->onCreate()->onCreateView()->onActivityCreated()->onStart()->onResume()->[Fragment is active]->1、/2、->onPause()->onStop()->onDestoryView()->onDestory()->onDetach()->[Fragment is destoryed]

 

 

Fragment的生命週期和Activity做比較:

 

(一)運行-》界面出現 (MyFragmentMyFragment是Fragment;ActivityMyFragment是Activity)

MyFragmentMyFragment: onCreate

MyFragmentMyFragment: onCreateView

ActivityMyFragment: onCreate

ActivityMyFragment: onStart

MyFragmentMyFragment: onStart

ActivityMyFragment: onResume

MyFragmentMyFragment: onResume

Fragment的onCreate->Activity的onCreate->Activity的onStart->Fragment的onStart->Actvity的onResume->Fragment的onResume

 

工程界面-》home鍵(Activity不銷燬)-》桌面

MyFragmentMyFragment: onPause

ActivityMyFragment: onPause

MyFragmentMyFragment: onStop

ActivityMyFragment: onStop

Fragment的onPause->Activity的onPause->Fragment的onStop->Activtiy的onStop

 

桌面-》工程界面

ActivityMyFragment: onStart

MyFragmentMyFragment: onStart

ActivityMyFragment: onResume

MyFragmentMyFragment: onResume

Activity的onStart->Fragment的onStart->Activty的onResume->Fragment的onResume

 

工程界面-》返回鍵(Activity銷燬)-》桌面

MyFragmentMyFragment: onPause

ActivityMyFragment: onPause

MyFragmentMyFragment: onStop

ActivityMyFragment: onStop

MyFragmentMyFragment: onDestroy

ActivityMyFragment: onDestroy

Fragment的onPause->Activty的onPause->Fragment的onStop->Activity的onStop->Fragment的onDestory->Activity的onDestory

返回後桌面-》工程界面

MyFragmentMyFragment: onPause

ActivityMyFragment: onPause

MyFragmentMyFragment: onStop

ActivityMyFragment: onStop

ActivityMyFragment: onStart

MyFragmentMyFragment: onStart

ActivityMyFragment: onResume

MyFragmentMyFragment: onResume

 

Fragment的生命週期和Activity非常相似,一個Fragment可以處於3種狀態:

運行:Fragment在當前運行的前臺,Activity中可見

暫停:另一個Activity在前臺,具有焦點,但是Fragment所在的Activity依然可見

停止:Fragment不可見。宿主Activity處於停止狀態或Fragment已經從Activity刪除並添加到後臺棧中。

 

Framment的宿主Activity的生命週期直接影響Fragment的生命週期。因此,Activity的每個生命週期回調函數都會調用Fragment的回調函數。例如,當宿主Activity的onPause()方法被調用時,Fragment的onPause()方法也被調用。

 

(二)Fragment還有一些其他的回調函數與宿主Activity交互,處理UI的創建與銷燬。

onAttach()當Fragment與Activity建立關聯時調用,Activity作爲參數傳入;

onCreateView()創建Framgment的UI;

onActivityCreated()當Activity的onCreate()方法返回時調用;

onDestoryView()當Fragment的UI被刪除時調用;

onDetach()當Frament與Activty取消關聯調用;

 

 

加入以上四個Fragment的方法後的運行順序爲:

 

運行-》工程界面:

MyFragmentMyFragment: onAttach

MyFragmentMyFragment: onCreate

MyFragmentMyFragment: onCreateView

ActivityMyFragment: onCreate

MyFragmentMyFragment: onActivityCreated

ActivityMyFragment: onStart

MyFragmentMyFragment: onStart

ActivityMyFragment: onResume

MyFragmentMyFragment: onResume

 

工程界面-》back-》桌面:

MyFragmentMyFragment: onPause

ActivityMyFragment: onPause

MyFragmentMyFragment: onStop

ActivityMyFragment: onStop

MyFragmentMyFragment: onDestroyView

MyFragmentMyFragment: onDestroy

MyFragmentMyFragment: onDetach

ActivityMyFragment: onDestroy

 

無論是home還是back後的桌面-》工程界面都和(一)相同

 

Fragment的生命週期:

當宿主Activity處於運行狀態時,可以自由添加和刪除Fragment。只有Activity處於運行狀態時,Fragment的聲明週期才能獨立變化。否則,直接受宿主Activity聲明週期的影響

 

3.4Frament交互及管理

1》FragmentManager API:工程FragmentManagerTest

APP:import android.app.FragmentManager;

獲取FragmentManager:manager = getFragmentManager();

獲取Fragment:fragmentDemo = (FragmentDemo) manager.findFragmentById(R.id.myfragment);

            fragmentDemoOne = (FragmentDemo)manager.findFragmentByTag("YHLL");

 

V4import android.support.v4.app.FragmentManager;

獲取FragmentManager:manager = getSupportFragmentManager();

獲取Fragment:v4FragmentDemo = (V4FragmentDemo)fragmentManager.findFragmentById(R.id.v4fragment);

            manager.findFragmentByTag("YHLL");

            v4FragmentDemoTwo = (V4FragmentDemo)fragmentManager.findFragmentByTag("v4fragmentTwo");

 

 

2》FragmentTranscation API(動態添加Fragment,以前的都是靜態添加的):工程FragmentTranscationTest

add():向容器中添加一個Fragment

remove():刪除Fragment

replace():將容器中的Fragment替換成新的Fragment

hide():隱藏已存在的Fragment

show():顯示此前隱藏的Fragment

addToBackStack():將事務添加到後臺棧

commit():提交事務,將改變應用到Activity

.replace()替換Fragment(注意:不能替換本Fragment只能是替換另一個不同類型的Fragment)

 

  添加Fragment:

    FragmentManager manager = getFragmentManager();//1、獲取FragmentManager

  FragmentTransaction transaction = manager.beginTransaction();//2、通過FragmentManager獲取FragmentTransaction事物

  MyFragment myFragment = new MyFragment();//3、創建Fragment

  transaction.add(R.id.frameLayout,myFragment,"he");//4、將上邊的Fragment添加到FragmentTransaction事物

  transaction.commit();//5、提交事物

 

替換Fragment:

//添加到返回棧中,點返回按鈕則依次返回,最後退到桌面,不添加返回棧的則直接退到桌面

getFragmentManager().beginTransaction().replace(R.id.frameLayout,numFragment).addToBackStack(null).commit();

 

靜態方法(類方法);靜態成員變量(類成員變量ios無);工程JavaTest

 

3》系統提供的Fragment類開發者可以繼承:實現了Fragment類的子類

DialogFragment:顯示一個懸浮對話框 工程:DialogFragmentTest

   好像和AlertDialog差不多啊,爲麼還要費事用DialogFragment???

   DialogFragmentTest.this.showToast();//成員方法調用showToast()實例方法

  ((DialogFragmentTest)getActivity()).showToast();//getActivity()調的是FragmentActivity

java:

非靜態方法可以訪問靜態方法;而靜態的不能訪問非靜態的   非靜態>靜態  對比ios的工程:testLei

靜態與非靜態之間的互相調用 DialogFragmentTest-TestStatic類

public statc class  MyDialogFragment extends DialogFragment{

   public  static MyDialogFragment newInstance (String tittle){//初始化帶參靜態方法

      MyDialogFragment myDialogFragment = new MyDialogFragment();

      Bundle bundle = new Bundle();

      bundle.putString("title",tittle);

      myDialogFragment.setArguments(bundle);

      return myDialogFragment;

  }

   public Dialog onCreateDialog(Bundle savedInstanceState) {//創建AlertDialog彈窗

    tittle = getArguments().getString("title");

    Dialog dlog = new AlertDialog.Builder(getActivity())

            .setTitle(tittle)

            .setIcon(R.mipmap.ic_launcher)

            .setPositiveButton("確定", new DialogInterface.OnClickListener(){

                @Override

                public void onClick(DialogInterface dialog, int which) {

                    ((DialogFragmentTest)getActivity()).showToast();

                }

 

            })

            .setNegativeButton("取消",null)

            .create();

    return dlog;

  }

}

 

 

 

ListFragment:顯示一個由adapter管理的項目列表

public  void showListFragmentAction(View view){

  String[]data = {"AAA","BBB","CCC"};

  MyListFragment myListFragment = MyListFragment.newInstance(data);

 

         getFragmentManager().beginTransaction()

         .add(R.id.fatherLayout,myListFragment)

         .commit();

 

 

}

 

public static class MyListFragment extends ListFragment {

    public static MyListFragment newInstance(String[] data){

        MyListFragment myListFragment = new MyListFragment();

        Bundle bundle = new Bundle();

        bundle.putStringArray("data",data);

        myListFragment.setArguments(bundle);

        return myListFragment;

    }

 

    @Override

    public void onAttach(Context context) {//設置適配器

        super.onAttach(context);

        String[] data = getArguments().getStringArray("data");

        setListAdapter(new ArrayAdapter<String>(

                getActivity(),

                android.R.layout.simple_list_item_1,

                android.R.id.text1,

                data

        ));

 

    }

     @Override

    public void onListItemClick(ListView l, View v, int position, long id){//重新onListItemClick方法,響應點擊事件

     Toast.makeText(getActivity(),data[position],Toast.LENGTH_LONG).show();

    super.onListItemClick(l, v, position, id);

   }

 

}

 

Fragment如果是動態添加到宿主Activity,則不一定和Acitivity聲明週期相關

 

 

3.11

Fragment總和應用(一)

支持平板和手機 工程名:FragmentAdaptePhoneAndPad  3月文件夾

v4包的Activity繼承自FragmentActivity

另一種Activity繼承自Activity

接口:

FragmentAdaptePhoneAndPad->MyJieKou

FragmentAdaptePhoneAndPad->SelectCityListener

FragmentAdaptePhoneAndPad->FatherJieKou

接口之間的繼承;類在實現多個接口

適配橫豎屏***   layout-land

爲了避免在一個Fragment中出現調用另外一個避免耦合嚴重,應該定義回調接口,需要宿主Activity實現這個接口。這樣在Fragment接收到事件的時候,調用這個接口中的方法讓Activity根據具體的配置做出響應

 

Fragment總和應用(二)

ViewPager 在supportv4中:一般和Fragment使用,也可以和view使用;在3.0以下版本只能用view,以上版本用Fragment配合使用,官方(谷歌)推薦使用Fragment

<android.support.v4.view.ViewPager

    android:layout_width=""

    android:layout_height=""></android.support.v4.view.ViewPager>

 

佈局解析器inflater:LayoutInflater inflater = LayoytInflater.from(this);

viewPager對象設置適配器:PagerAdapter(是一個抽象類)

以view爲子視圖工程:ViewPagerTest 抽象類是PageAdapter

//ViewPager對象設置適配器PageAdapter

viewPager.setAdapter(new MyPageAdapter());

public class MyPageAdapter extends PagerAdapter{

    @Override

    public int getCount() {

        return views.length;

    }

 

    @Override

    public boolean isViewFromObject(@NonNull View view, @NonNull Object o) {

        return view == o;

    }

 

    @Override

    public void destroyItem(@NonNull ViewGroup container, int position, @NonNull Object object) {

       container.removeView(views[position]);

    }

 

    @NonNull

    @Override

    public Object instantiateItem(@NonNull ViewGroup container, int position) {

        container.addView(views[position]);

        return views[position];

    }

 

}

 

以Fragment爲子視圖工程:ViewPagerTestAgain 抽象類是專門用於Frament的FragmentPagerAdapter

 

viewPager.setAdapter(new MyPageAdapater(getSupportFragmentManager()));

class MyPageAdapater extends FragmentPagerAdapter {

 

 

    public MyPageAdapater(FragmentManager fm) {

        super(fm);

    }

 

    @Override

    public Fragment getItem(int i) {

        return fragments[i];

    }

 

    @Override

    public int getCount() {

        return fragments.length;

    }

}

注意:

1》view和Fragment分別做子類時,其viewpager對象的適配器PageAdapter不同,但都是繼承自抽象類PageAdapter的自定義抽象類;

2》抽象類需要實現的方法不完全相同;

3》Viewpager設置適配器的構造方法的參數有差別

 

2019.3.12 

ViewPager的總和運用(三)FragmentThreeTest

使用ViewPager實現基本導航,即不隨ViewPager而滾動

Viewpager:

設置當前子控件:viewPager.setCurrentItem(item);

滑動及選中事件:viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {

    @Override

    public void onPageScrolled(int i, float v, int i1) {//正在滾動

 

    }

 

    @Override

    public void onPageSelected(int i) {//已經改變

        selectTittle(i);

 

    }

 

    @Override

    public void onPageScrollStateChanged(int i) {//滾動狀態發生改變

 

    }

});

 

ViewPager的總和運用(四)工程:FragmentFourTest(自己寫的)  工程:FragmentThreeTest的副本(視頻關鍵位置運用)

歡迎界面:

選擇器的創建和使用(FragmentThreeTest的副本):

在drawable文件夾下新建文件dot.xml(new -file -Drawble Resource File-dot.xml選擇selector) 

<?xml version="1.0" encoding="utf-8"?>

<selector xmlns:android="http://schemas.android.com/apk/res/android">

    <item android:state_enabled="true" android:drawable="@drawable/raidono"></item>//選中狀態是圖片raidono

    <item android:state_enabled="false" android:drawable="@drawable/raidoselec"></item>//非選中狀態是圖片raidoselec

 

</selector>

圖片在使用時,則src如下:(dot爲上邊創建的xml的文件名)

<ImageView

    style="@style/tab_style"

    android:src="@drawable/dot"

    />

爲何selector的圖片只能放在drawable文件夾下??不做圖片適配麼?

 

ActionBar:(Fragment綜合使用五)工程:ActionBarVSFragmentFiveTest

 

使用ActionBar來創建tab步驟,則滑動效果自然就有了

啓用NAVIGATION_MODE_TABS

創建幾個ActionBar.Tab的實例

對每個實例實現ActionBar.TabListener接口

 

2019.3.13

DrawerLayout :(抽屜式導航 Fragment綜合使用五)工程:DrawerLayoutVSFragmentTest

 

自定義控件:

按類型劃分,自定義View的實現方式可分爲三種:

自繪控件:工程 SelfDefinedControlDraw

  View上所展示的內容全部是繪製出來的;

  繪製代碼寫在onDraw()方法中的;

  自定義在View界面上顯示,只需要像普通控件一樣使用自定義view即可

  示例:圈;長方形;圖片

 <com.example.yangyangzi.selfdefinedcontroldraw.DrawView //包名+類名

    android:layout_width="match_parent"

    android:layout_height="match_parent" />

 

移動的自定義view 工程:SelfDefinedControlInvalidate

 view的刷新

  

組合控件:工程CollectionSelfDefinedControl

  XML組合控件;代碼組合控件

 

繼承控件:工程ExtendsSelfDefinedControl

   

3.14 Service

是一種Android的組件,可以在後臺長時間運行

不提供交互界面:

     即便用戶跳轉至另一個應用後,service仍在後臺運行

     任意應用組件都可以綁定服務,甚至可以用來完成進程間通訊的任務,例如 需要下載時;播放音樂;文件I/o

 

3.15 工程:ServiceTest

1>單獨的服務:

創建service file-》new service

啓動服務:

intent = new Intent(this,MyService.class);

startService(intent);

停止服務:

intent = new Intent(this,MyService.class);

stopService(intent);

重寫服務的方法:

   onCreate;onDestroy;onStartCommand;onBind

點擊start按鈕:

onCreate

onStartCommand

點擊stop按鈕:

onDestroy

再點擊start按鈕:

onCreate

onStartCommand

再點擊start按鈕:

onStartCommand

注意:如果啓動服務再次啓動服務,則會調用onStartCommand方法

 

2>和應用關聯的服務:

創建service file-》new service

啓動服務:

intent = new Intent(this,MyService.class);

bindService(intent, conn, BIND_AUTO_CREATE);//bindService必須要有個連接的存在,如果不存在BIND_AUTO_CREATE參數指示自動創建

停止服務:

intent = new Intent(this,MyService.class);

unbindService(conn);

重寫服務的方法:

   onCreate;onDestroy;onStartCommand;onBind

點擊bind按鈕:

onCreate

onBind

onServiceConnected(Activity中)

點擊unbind按鈕:

onDestroy

再點擊bind按鈕:

無反應

再點擊start按鈕:

無反應

注意:如果要Activity的ServiceConnection的回調方法響應,必須在onBind方法中創建並返回繼承自Binder的類

 

工程:BindServiceTest 用bind的service計算平均分,並顯示在界面上

內部類方法可以調用外部類方法,反之不可

工程:StartServiceTest 用startService的方法計算平均分,只能在sevice計算,不能單純返回到activity,以後可以用廣播的方式返回並展示

 

系統服務:

由於是Android原代碼,可以通過Android代碼來對服務進行交互

Android將Binder封裝成普通的Manager類,代碼調用時無法察覺是使用了Service

這些服務通過Context.getSystemService(String name)來獲得,name決定了獲得不同的Mananger類,不同的Manager類有各自的方法來調用系統功能或是訪問系統狀態

例如:

電源管理:POWER_SERVICE

NotificationManager通知的管理:NOTIFICATION_SERVICE

LocationManager定位的控制:LOCATION_SERVICE

ConnectionManager網絡連接的控制:CONNECTIVITY_SERVICE

示例:SystemServiceTest 音量和鬧鈴

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章