我有Activity
(称为MonitorActivity),其中包含ViewPager
。 MonitorActivity
绑定到本地Service
并从服务接收Broadcasts
。
收到服务广播后,我希望通过调用update
方法在ViewPager中update
个片段。
一切都行,直到我离开活动一段时间。当我返回MonitorActivity
时,应用崩溃,因为片段中的某些观看次数为null
。
查看Activity
和Fragment
生命周期日志:
// First Run
Activity onCreate
Activity onStart
Activity onResume
Fragment onAttach
Fragment onCreate
Fragment onCreateView
Fragment onActivityCreated
Fragment onStart
Fragment onResume
Fragment update :tempView: Not null
Fragment update :tempView: Not null
Fragment update :tempView: Not null
...
// Leaving Activity
Fragment onPause
Activity onPause
Fragment onStop
Activity onStop
// Returning back to Activity
Activity onCreate
Fragment onAttach
Fragment onCreate
Fragment onCreateView
Fragment onActivityCreated
Fragment onStart
Activity onStart
Activity onResume
Fragment onResume
Fragment update :tempView: Null
Fragment update :tempView: Null
Fragment update :tempView: Null
...
我的问题是:重新创建活动会导致在片段内重新创建ViewPager,Adapter,Fragments和Views。 tempView
初始化了Fragment's onCreateView
。返回null
后,为什么此视图为MonitorActivity
?
MonitorActivity:
private ViewPager viewpager;
private PagerAdapter pagerAdapter;
private FragmentManager fragmentManager;
@Override
protected void onCreate(Bundle savedInstanceState) {
Log.d(TAG, "Activity onCreate");
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_monitor);
fragmentManager = getSupportFragmentManager();
pagerAdapter = new PagerAdapter(fragmentManager);
viewpager = (ViewPager) findViewById(R.id.viewpager);
viewpager.setAdapter(pagerAdapter);
// ...
Intent gattServiceIntent = new Intent(this, BluetoothLeService.class);
bindService(gattServiceIntent, mServiceConnection, BIND_AUTO_CREATE);
}
@Override
protected void onResume() {
super.onResume();
Log.d(TAG, "Activity onResume");
registerReceiver(updateReceiver, makeUpdateIntentFilter());
}
@Override
protected void onPause() {
super.onPause();
Log.d(TAG, "Activity onPause");
unregisterReceiver(mUpdateReceiver);
}
private final BroadcastReceiver mUpdateReceiver = new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
final Bundle extras = intent.getExtras();
String deviceAddress = extras.getString(Constants.KEY_EXTRAS_DEVICE_ADDRESS);
pagerAdapter.getFragment(deviceAddress).update(intent); // <== Calling this method of MonitorFragment instance throws NullPointerException
}
};
PagerAdapter内部课程:
class PagerAdapter extends FragmentPagerAdapter {
private HashMap<String, MonitorFragment> fragments;
private ArrayList<Item> items;
public PagerAdapter(FragmentManager fm) {
super(fm);
fragments = new HashMap<>();
items = ItemRepository.getInstance().getAll();
for (Item item : items) {
String deviceAddress = item.getDeviceAddress();
fragments.put(deviceAddress, MonitorFragment.newInstance(deviceAddress));
}
}
@Override
public Fragment getItem(int position) {
return fragments.get(items.get(position).getDeviceAddress());
}
@Override
public int getCount() {
return items == null ? 0 : items.size();
}
public MonitorFragment getFragment(String deviceAddress) {
return fragments.get(deviceAddress);
}
public HashMap<String, MonitorFragment> getFragments() {
return fragments;
}
}
MonitorFragment:
public static MonitorFragment newInstance(String deviceAddress) {
MonitorFragment fragment = new MonitorFragment();
Bundle args = new Bundle();
args.putString(ARG_DEVICE_ADDRESS, deviceAddress);
fragment.setArguments(args);
return fragment;
}
@Override
public void onAttach(Context context) {
super.onAttach(context);
// ...
}
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.d(TAG, "Fragment onCreate");
if (getArguments() != null) {
deviceAddress = getArguments().getString(ARG_DEVICE_ADDRESS);
item = ItemRepository.getInstance().getByDeviceAddress(deviceAddress);
}
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
Log.d(TAG, "Fragment onCreateView");
view = inflater.inflate(R.layout.fragment_monitor, container, false);
tempView = (TempView) view.findViewById(R.id.tempView);
// ...
return view;
}
public void update(Intent intent) {
// ...
temp.setValue(Something); // <== Throws NullPointerException
// ...
}