A股上市公司传智教育(股票代码 003032)旗下技术交流社区北京昌平校区

 找回密码
 加入黑马

QQ登录

只需一步,快速开始

1黑马币
本帖最后由 Jim-剣◆﹏ 于 2016-1-31 11:01 编辑


通常我们会在宿主activity的初始化fragment,FragmenTwo与FragmentOne叠加在一起,这就是因为你的Activity重新启动,在原来的FragmenTwo上又绘制了一个FragmentOne。
好了,下面看一段代码:
  1. package com.zhy.zhy_fragments;

  2. import android.app.Activity;
  3. import android.app.FragmentManager;
  4. import android.app.FragmentTransaction;
  5. import android.os.Bundle;
  6. import android.view.Window;

  7. public class MainActivity extends Activity

  8. {
  9.         private FragmentOne mFOne;

  10.         @Override
  11.         protected void onCreate(Bundle savedInstanceState)
  12.         {
  13.                 super.onCreate(savedInstanceState);
  14.                 requestWindowFeature(Window.FEATURE_NO_TITLE);
  15.                 setContentView(R.layout.activity_main);

  16.                 mFOne = new FragmentOne();
  17.                 FragmentManager fm = getFragmentManager();
  18.                 FragmentTransaction tx = fm.beginTransaction();
  19.                 tx.add(R.id.id_content, mFOne, "ONE");
  20.                 tx.commit();

  21.         }

  22. }
复制代码


Fragment:
  1. package com.zhy.zhy_fragments;

  2. import android.app.Fragment;
  3. import android.os.Bundle;
  4. import android.util.Log;
  5. import android.view.LayoutInflater;
  6. import android.view.View;
  7. import android.view.ViewGroup;

  8. public class FragmentOne extends Fragment
  9. {
  10.         private static final String TAG = "FragmentOne";

  11.         @Override
  12.         public View onCreateView(LayoutInflater inflater, ViewGroup container,
  13.                         Bundle savedInstanceState)
  14.         {
  15.                 Log.e(TAG, "onCreateView");
  16.                 View view = inflater.inflate(R.layout.fragment_one, container, false);
  17.                 return view;
  18.         }

  19.         @Override
  20.         public void onCreate(Bundle savedInstanceState)
  21.         {
  22.                 // TODO Auto-generated method stub
  23.                 super.onCreate(savedInstanceState);

  24.                 Log.e(TAG, "onCreate");
  25.         }

  26.         @Override
  27.         public void onDestroyView()
  28.         {
  29.                 // TODO Auto-generated method stub
  30.                 super.onDestroyView();
  31.                 Log.e(TAG, "onDestroyView");
  32.         }

  33.         @Override
  34.         public void onDestroy()
  35.         {
  36.                 // TODO Auto-generated method stub
  37.                 super.onDestroy();
  38.                 Log.e(TAG, "onDestroy");
  39.         }

  40. }
复制代码
很简单的代码,当你运行之后,不断的旋转屏幕,你会发现每旋转一次屏幕,屏幕上就多了一个FragmentOne的实例,并且后台log会打印出许多套生命周期的回调。

类似:
  1. 07-20 08:18:46.651: E/FragmentOne(1633): onCreate
  2. 07-20 08:18:46.651: E/FragmentOne(1633): onCreate
  3. 07-20 08:18:46.651: E/FragmentOne(1633): onCreate
  4. 07-20 08:18:46.681: E/FragmentOne(1633): onCreateView
  5. 07-20 08:18:46.831: E/FragmentOne(1633): onCreateView
  6. 07-20 08:18:46.891: E/FragmentOne(1633): onCreateView
复制代码
这是为什么呢,因为当屏幕发生旋转,Activity发生重新启动,默认的Activity中的Fragment也会跟着Activity重新创建;这样造成当旋转的时候,本身存在的Fragment会重新启动,然后当执行Activity的onCreate时,又会再次实例化一个新的Fragment,这就是出现的原因。

那么如何解决呢:
其实通过检查onCreate的参数Bundle savedInstanceState就可以判断,当前是否发生Activity的重新创建:
默认的savedInstanceState会存储一些数据,包括Fragment的实例:通过打印可以看出:
  1. 07-20 08:23:12.952: E/FragmentOne(1782): Bundle[{android:fragments=android.app.FragmentManagerState@40d0b7b8, android:viewHierarchyState=Bundle[{android:focusedViewId=2131230721, android:views=android.util.SparseArray@40d0af68}]}]
复制代码

所以,我们简单改一下代码,只有在savedInstanceState==null时,才进行创建Fragment实例:
  1. package com.zhy.zhy_fragments;

  2. import android.app.Activity;
  3. import android.app.FragmentManager;
  4. import android.app.FragmentTransaction;
  5. import android.os.Bundle;
  6. import android.util.Log;
  7. import android.view.Window;

  8. public class MainActivity extends Activity

  9. {
  10.         private static final String TAG = "FragmentOne";
  11.         private FragmentOne mFOne;

  12.         @Override
  13.         protected void onCreate(Bundle savedInstanceState)
  14.         {
  15.                 super.onCreate(savedInstanceState);
  16.                 requestWindowFeature(Window.FEATURE_NO_TITLE);
  17.                 setContentView(R.layout.activity_main);

  18.                 Log.e(TAG, savedInstanceState+"");
  19.                
  20.                 if(savedInstanceState == null)
  21.                 {
  22.                         mFOne = new FragmentOne();
  23.                         FragmentManager fm = getFragmentManager();
  24.                         FragmentTransaction tx = fm.beginTransaction();
  25.                         tx.add(R.id.id_content, mFOne, "ONE");
  26.                         tx.commit();
  27.                 }
  28.                
  29.                

  30.         }

  31. }
复制代码
现在无论进行多次旋转都只会有一个Fragment实例在Activity中。



0 个回复

您需要登录后才可以回帖 登录 | 加入黑马