Android實(shí)現(xiàn)過(guò)渡動(dòng)畫(huà)、引導(dǎo)頁(yè) Android判斷是否第一次啟動(dòng)App
目前的App在安裝后,第一次打開(kāi),都會(huì)顯示兩秒左右的logo,然后進(jìn)入引導(dǎo)頁(yè)。如果關(guān)閉App,再重新打開(kāi),則只會(huì)顯示logo,然后直接進(jìn)入主頁(yè)。
最近寫(xiě)了這個(gè),記錄一下。
首先是過(guò)渡動(dòng)畫(huà),因?yàn)樗徽揂pp是否第一次啟動(dòng)都會(huì)顯示。
這里我使用了Handler的postDelayed()方法。把過(guò)渡動(dòng)畫(huà)的Activity設(shè)為默認(rèn)啟動(dòng)的Activity。在當(dāng)前Activity中,執(zhí)行postDelayed()方法,把延時(shí)的時(shí)長(zhǎng)設(shè)為兩秒即可。
過(guò)渡頁(yè)面如下:transition_view.xml
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" android:orientation="vertical" android:background="#fff" > <ImageView android:src="@drawable/profile" android:layout_marginTop="80dp" android:layout_gravity="center" android:layout_width="100dp" android:layout_height="100dp" /> </LinearLayout>
這里因?yàn)槲业膱D片背景是白色的,就沒(méi)有設(shè)置LinearLayout的背景色了,如果Logo的背景色不一樣,則可以進(jìn)行設(shè)置。也可以直接用ImageView解決。
過(guò)渡Activity如下:TransitionActivity.java
package com.ikok.transitionandguidingpage; import android.app.Activity; import android.content.Intent; import android.content.SharedPreferences; import android.os.Bundle; import android.os.Handler; import android.view.Window; /** * Created by Anonymous on 2016/3/25. */ public class TransitionActivity extends Activity { boolean isFirstIn = false; private Intent intent; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); requestWindowFeature(Window.FEATURE_NO_TITLE); setContentView(R.layout.transition_view); final SharedPreferences sharedPreferences = getSharedPreferences("is_first_in_data",MODE_PRIVATE); isFirstIn = sharedPreferences.getBoolean("isFirstIn",true); new Handler().postDelayed(new Runnable() { @Override public void run() { if (isFirstIn) { // Toast.makeText(TransitionActivity.this, "First log", Toast.LENGTH_SHORT).show(); intent = new Intent(TransitionActivity.this, GuideActivity.class); TransitionActivity.this.startActivity(intent); TransitionActivity.this.finish(); } else { intent = new Intent(TransitionActivity.this, MainActivity.class); TransitionActivity.this.startActivity(intent); TransitionActivity.this.finish(); } } }, 2000); } }
顯示了過(guò)渡動(dòng)畫(huà)后,則需要判斷是否是第一次啟動(dòng)App了。因?yàn)楦鶕?jù)是否是第一次啟動(dòng)App會(huì)判斷進(jìn)入引導(dǎo)頁(yè)還是主頁(yè)。
因?yàn)檫@個(gè)判斷并不是一次執(zhí)行就不需再執(zhí)行了,而是每次啟動(dòng)App的時(shí)候都需要進(jìn)行判斷。所以這個(gè)判斷的數(shù)據(jù)需要持久化。
且為了判斷的時(shí)間很短,就不需要進(jìn)行訪問(wèn)數(shù)據(jù)庫(kù),或者網(wǎng)絡(luò)訪問(wèn)等耗時(shí)操作了。直接使用 SharedPreferences 進(jìn)行處理。
首先去指定 SharedPreferences 文件的名稱(chēng),如果不存在則會(huì)創(chuàng)建一個(gè)。創(chuàng)建的文件存放在 /data/data/<package name>/shared_prefs/ 目錄下。
第二個(gè)參數(shù)是指定對(duì)該文件的操作模式。默認(rèn)是 MODE_PRIVATE ,和直接傳入0是一樣的,表示只有當(dāng)前程序才能對(duì)這個(gè)文件進(jìn)行讀寫(xiě)操作。
MODE_MULTI_PROCESS 是用于多個(gè)程序?qū)ν粋€(gè) SharedPreferences 文件進(jìn)行讀寫(xiě)操作。
創(chuàng)建好了文件,接下來(lái)我們讀取標(biāo)志,看程序是否是第一次啟動(dòng)App。
getBoolean("isFirstIn",true); 這個(gè)是用來(lái)獲取標(biāo)志的,它是用來(lái)取出文件中對(duì)應(yīng)的鍵值對(duì)。第一個(gè)參數(shù)是鍵,第二個(gè)參數(shù)是默認(rèn)值。
它會(huì)取出對(duì)應(yīng)鍵的值,如果沒(méi)有這個(gè)鍵,或者沒(méi)有值,則直接使用默認(rèn)值,即第二個(gè)參數(shù)。因?yàn)槲覄?chuàng)建SharedPreferences 文件的時(shí)候并沒(méi)有創(chuàng)建這個(gè)鍵值對(duì)。
所以,它是讀不出對(duì)應(yīng)的鍵的值的,則會(huì)直接獲取到 true 值。則App判斷為第一次啟動(dòng)。接下來(lái)使用Intent,根據(jù)值,則開(kāi)啟了引導(dǎo)頁(yè)即 GuideActivity 。
引導(dǎo)頁(yè) 頁(yè)面如下:guide_view.xml
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent"> <android.support.v4.view.ViewPager android:id="@+id/viewpager" android:layout_width="match_parent" android:layout_height="match_parent"> </android.support.v4.view.ViewPager> </LinearLayout>
這里是v4包下的ViewPager。引導(dǎo)頁(yè)我決定使用ViewPager+FragmentPagerAdapter來(lái)實(shí)現(xiàn)。
如果我直接通過(guò)判斷VIewPager是否是最后一頁(yè),再左滑進(jìn)入App主頁(yè),ViewPager切換到主頁(yè)時(shí)候會(huì)有一點(diǎn)問(wèn)題??赡茏蠡艘稽c(diǎn),但是還想看前兩張引導(dǎo)頁(yè),再右滑,
結(jié)果是直接進(jìn)入了App主頁(yè),而不是上一張。體驗(yàn)感很不好,所以考慮到最后一頁(yè)上有一個(gè)按鈕,來(lái)進(jìn)行點(diǎn)擊進(jìn)入App主頁(yè)。這樣體驗(yàn)感會(huì)好一點(diǎn)。
引導(dǎo)頁(yè)Activity如下:GuideAcitivity.java
package com.ikok.transitionandguidingpage; import android.os.Bundle; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentActivity; import android.support.v4.app.FragmentPagerAdapter; import android.support.v4.view.ViewPager; import android.view.Window; import java.util.ArrayList; import java.util.List; /** * Created by Anonymous on 2016/3/26. */ public class GuideActivity extends FragmentActivity { private ViewPager mViewPager; private FragmentPagerAdapter mAdapter; private List<Fragment> mFragment = new ArrayList<Fragment>(); @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); requestWindowFeature(Window.FEATURE_NO_TITLE); setContentView(R.layout.guide_view); mViewPager = (ViewPager) findViewById(R.id.viewpager); Fragment guide1 = new Guide1(); Fragment guide2 = new Guide2(); Fragment guide3 = new Guide3(); mFragment.add(guide1); mFragment.add(guide2); mFragment.add(guide3); mAdapter = new FragmentPagerAdapter(getSupportFragmentManager()) { @Override public Fragment getItem(int position) { return mFragment.get(position); } @Override public int getCount() { return mFragment.size(); } }; // 為ViewPager添加動(dòng)畫(huà)效果,3.0以上可用 mViewPager.setPageTransformer(true,new DepthPageTransformer()); // mViewPager.setPageTransformer(true,new ZoomOutPageTransformer()); mViewPager.setAdapter(mAdapter); } }
中間創(chuàng)建了三個(gè)Fragment,去加載布局,布局就是在xml的根節(jié)點(diǎn)上添加了 background 屬性。
這里我為ViewPager的切換添加了切換動(dòng)畫(huà)。使用的 Google 官方文檔上列出的兩種動(dòng)畫(huà)效果。
當(dāng)然可以進(jìn)行自定義切換動(dòng)畫(huà),我本來(lái)自定義了一個(gè)切換20度角的切換動(dòng)畫(huà),但覺(jué)得不是很好看就沒(méi)放上來(lái)了。
切換動(dòng)畫(huà),低版本不支持。又添加了 nineoldandroid ,來(lái)使動(dòng)畫(huà)兼容到低版本。
最后一個(gè)頁(yè)面如下:guide_view3.xml
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:background="@drawable/guide3" android:layout_height="match_parent"> <Button android:id="@+id/into_app_btn" android:layout_width="wrap_content" android:layout_height="wrap_content" android:text="進(jìn)入App" android:textColor="#fefefe" android:background="@drawable/button_shape" android:layout_alignParentBottom="true" android:layout_centerInParent="true" android:layout_marginBottom="50dp" /> </RelativeLayout>
第三頁(yè)的代碼如下: Guide3.java
package com.ikok.transitionandguidingpage; import android.content.Intent; import android.content.SharedPreferences; import android.os.Bundle; import android.support.v4.app.Fragment; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.widget.Button; /** * Created by Anonymous on 2016/3/27. */ public class Guide3 extends Fragment { private Button mIntoAppBtn; private View view; @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { view = inflater.inflate(R.layout.guide_view3,container,false); return view; } @Override public void onActivityCreated(Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); mIntoAppBtn = (Button) view.findViewById(R.id.into_app_btn); mIntoAppBtn.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { Intent intent = new Intent(getActivity(), MainActivity.class); startActivity(intent); SharedPreferences sharedPreferences = getActivity().getSharedPreferences("is_first_in_data", 0x0000); SharedPreferences.Editor editor = sharedPreferences.edit(); editor.putBoolean("isFirstIn", false); editor.commit(); getActivity().finish(); } }); } }
這里我就對(duì)頁(yè)面上的Button綁定了一個(gè)點(diǎn)擊事件監(jiān)聽(tīng)器。點(diǎn)擊進(jìn)入主頁(yè),并且修改判斷是否第一次進(jìn)入App的標(biāo)志值。
通過(guò) SharedPreferences.Editor 對(duì)象去修改標(biāo)志值。然后 commit ,沒(méi)有 commit 是沒(méi)有進(jìn)行更新保存的。
這里getSharedPreferences() 的第二個(gè)參數(shù),我直接使用了 0x0000,十六進(jìn)制的0。
因?yàn)楫?dāng)時(shí)我使用 MODE_PRIVATE 的時(shí)候報(bào)錯(cuò),然后我就通過(guò)查源碼,發(fā)現(xiàn) MODE_PRIVATE 的值就是 0x0000,所以我直接使用了這個(gè) 0x0000。
為什么報(bào)錯(cuò)呢?因?yàn)?MODE_PRIVATE 是Context 里的變量,在 Fragment 里無(wú)法識(shí)別。如果一定要用,則使用 Context.MODE_PRIVATE。
為什么 Activity 能用呢?因?yàn)?Activity 繼承了 Context, 而 Fragment 沒(méi)有繼承 Context。
本來(lái)我做的是在主頁(yè)的Activity中去修改這個(gè)標(biāo)志值。但是后面考慮到,如果不是第一次啟動(dòng),每次進(jìn)入到主頁(yè),都需要修改一次標(biāo)志值,即使它沒(méi)有變化,還是多做了很多無(wú)用功。所以在最后一頁(yè)的點(diǎn)擊事件里進(jìn)行修改。標(biāo)志值只需要修改一次,引導(dǎo)頁(yè)也只出現(xiàn)一次,正好。
主頁(yè)就是創(chuàng)建工程默認(rèn)的主頁(yè)了。
其他事項(xiàng):
給Button加了樣式屬性。
button_shape.xml
<?xml version="1.0" encoding="utf-8"?> <shape xmlns:android="http://schemas.android.com/apk/res/android" android:shape="rectangle"> <!-- 填充的顏色 --> <solid android:color="#00FFFFFF" /> <stroke android:color="#fefefe" android:width="1dp" /> <!-- 設(shè)置按鈕的四個(gè)角為弧形 --> <!-- android:radius 弧形的半徑 --> <corners android:radius="5dip" /> <!-- padding:Button里面的文字與Button邊界的間隔 --> <padding android:left="10dp" android:top="10dp" android:right="10dp" android:bottom="10dp" /> </shape>
進(jìn)入程序會(huì)出現(xiàn)一瞬間的空白,然后顯示正常。這是因?yàn)锳ppTheme。這里我新建了一個(gè)空的樣式。然后讓默認(rèn)啟動(dòng)的Activity去應(yīng)用空的樣式。
style.xml
<pre name="code" class="html"><resources> <!-- Base application theme. --> <style name="AppTheme" parent="Theme.AppCompat.Light.DarkActionBar"> <!-- Customize your theme here. --> <item name="colorPrimary">@color/colorPrimary</item> <item name="colorPrimaryDark">@color/colorPrimaryDark</item> <item name="colorAccent">@color/colorAccent</item> </style> <!--空程序樣式--> <style name="EmptyTheme"> </style> </resources>
AndroidManifest.xml
<?xml version="1.0" encoding="utf-8"?> <manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.ikok.transitionandguidingpage"> <application android:allowBackup="true" android:icon="@drawable/profile" android:label="@string/app_name" android:supportsRtl="true" android:theme="@style/AppTheme"> <activity android:name=".MainActivity"> </activity> <!--應(yīng)用空樣式--> <activity android:name=".TransitionActivity" android:theme="@style/EmptyTheme"> <intent-filter> <action android:name="android.intent.action.MAIN" /> <category android:name="android.intent.category.LAUNCHER" /> </intent-filter> </activity> <activity android:name=".GuideActivity"> </activity> </application> </manifest>
以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
- Android使用ViewPager實(shí)現(xiàn)啟動(dòng)引導(dǎo)頁(yè)效果
- Android實(shí)現(xiàn)漸變啟動(dòng)頁(yè)和帶有指示器的引導(dǎo)頁(yè)
- android引導(dǎo)用戶開(kāi)啟自啟動(dòng)權(quán)限的方法
- Android客戶端首次啟動(dòng)引導(dǎo)界面
- Android UI設(shè)計(jì)與開(kāi)發(fā)之實(shí)現(xiàn)應(yīng)用程序只啟動(dòng)一次引導(dǎo)界面
- Android使用ViewPager實(shí)現(xiàn)啟動(dòng)引導(dǎo)頁(yè)
- Android實(shí)現(xiàn)啟動(dòng)引導(dǎo)圖
相關(guān)文章
Android編程實(shí)現(xiàn)將時(shí)間轉(zhuǎn)化成幾分鐘前、幾天前等形式的工具類(lèi)
這篇文章主要介紹了Android編程實(shí)現(xiàn)將時(shí)間轉(zhuǎn)化成幾分鐘前、幾天前等形式的工具類(lèi),涉及Android針對(duì)日期時(shí)間的相關(guān)運(yùn)算與判斷簡(jiǎn)單操作技巧,需要的朋友可以參考下2018-02-02Android使用Dialog風(fēng)格彈出框的Activity
這篇文章主要為大家詳細(xì)介紹了Android使用Dialog風(fēng)格彈出框的Activity,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2016-09-09Android 使用Vibrator服務(wù)實(shí)現(xiàn)點(diǎn)擊按鈕帶有震動(dòng)效果
這篇文章主要介紹了Android 使用Vibrator服務(wù)實(shí)現(xiàn)點(diǎn)擊按鈕帶有震動(dòng)效果,,本文通過(guò)實(shí)例圖文相結(jié)合給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)火鍋工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-06-06Android?Camera開(kāi)發(fā)實(shí)現(xiàn)可復(fù)用的相機(jī)組件
這篇文章主要為大家詳細(xì)介紹了Android?Camera開(kāi)發(fā)實(shí)現(xiàn)可復(fù)用的相機(jī)組件,文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2022-05-05Android Handler之消息循環(huán)的深入解析
本篇文章是對(duì)Handler消息循環(huán)進(jìn)行了詳細(xì)的分析介紹,需要的朋友參考下2013-05-05Android 實(shí)現(xiàn)自動(dòng)打電話與發(fā)短信的實(shí)例
這篇文章主要介紹了Android 實(shí)現(xiàn)自動(dòng)打電話與發(fā)短信的實(shí)例的相關(guān)資料,需要的朋友可以參考下2017-05-05Android手勢(shì)密碼view學(xué)習(xí)筆記(一)
這篇文章主要為大家詳細(xì)介紹了Android手勢(shì)密碼view的學(xué)習(xí)筆記,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-03-03