Android five-day music (third day) ListFragment and ViewPager, androidviewpager
1 ListFragment
Today, I first learned a very common display scenario: list display.
Yesterday I learned how to use Fragmet instead of activity for design. Today, I managed a single fragment and managed a layout list. First look at the effect:
Because the Fragment list needs to be saved using ArrayList, and in order to make the Fragment object affected by the lifecycle such as acrivity, create an example class, for example:
public class CrimeLab { private ArrayList<Crime> mCrimes; private static CrimeLab sCrimeLab; private Context mAppContext; private CrimeLab(Context context){ mAppContext=context; mCrimes=new ArrayList<Crime>(); for(int i=0;i<100;i++){ Crime c =new Crime(); c.setTitle("Crime #"+i); c.setSolved(i%2==0); mCrimes.add(c); } } public static CrimeLab get(Context c){ if(sCrimeLab==null){ sCrimeLab=new CrimeLab(c.getApplicationContext()); } return sCrimeLab; } public ArrayList<Crime> getmCrimes(){ return mCrimes; } public Crime getCrime(UUID id){ for (Crime c: mCrimes){ if(c.getId().equals(id)){ return c; } } return null; }}
At the same time, a corresponding fragment layout file and class file must be created. In fact, there is a class dedicated to list fragment: ListFragment. This class can be inherited, and then its built-in listadapter can be used.
Why is adapter used? Because we have created 100 new fragment objects in our fragmentlab, we cannot display them all on a page, but create objects only when they are displayed. The adapter obtains data from the model layer and provides it to the bridge shown in ListView.
private class CrimeAdapter extends ArrayAdapter<Crime>{ public CrimeAdapter(ArrayList<Crime> crimes){ super(getActivity(),0,crimes); } @Override public View getView(int position,View convertView,ViewGroup parent){ if(convertView==null){ convertView=getActivity().getLayoutInflater().inflate(R.layout.list_item_crime,null); } Crime c=getItem(position); TextView titleTextView=(TextView)convertView.findViewById(R.id.crime_list_item_titleTextView); titleTextView.setText(c.getTitle()); TextView dateTextView=(TextView)convertView.findViewById(R.id.crime_list_item_dateTextView); dateTextView.setText(c.getDate().toString()); CheckBox solvedCheckBox=(CheckBox)convertView.findViewById(R.id.crime_list_item_solvedCheckBox); solvedCheckBox.setChecked(c.isSolved()); return convertView; } }
To implement self-customized Adapater code, we need to implement our own adapter because we have customized our own layout for each entry in the list. For example, list_item_crime in the code.
In this way, the fragment displayed in the list is obtained.
2 ViewPager
ViewPager allows you to switch between the left and right screens to view different list items.
ViewPager can provide a view only by using the Adapter. Use the Child class of PagerAdapter: FragmentStatePagerAdapter to solve the coordination problem between the two.
Here we need to implement two methods: getCount () and getItem (). The sample code is as follows:
mViewPager.setAdapter(new FragmentStatePagerAdapter(fm) { @Override public int getCount(){ return mCrimes.size(); } @Override public Fragment getItem(int pos) { Crime crime=mCrimes.get(pos); return CrimeFragment.newInstance(crime.getId()); } });
3 fragment data transmission
Similar to activity, fragment can also transmit data. Moreover, fragment-level data transmission makes programming more flexible.
Imagine the following scenario: In CrimeFragment, You need to press the button to call up DatePickerFragment. The latter needs the data provided by the former for initialization. In addition, the returned value of DatePickerFragment also applies to CrimeFragment.
The following steps are required:
1) When initializing DatePickerFragment from CrimeFragment, pass the data as a construction parameter
2) When constructing a DatePickerFragment, save the passed value to argument.
3) When DatePickerFragment is rendered, the value of arguments is used.
4) DatePickerFragment returns the value to CrimeFragment
To implement the preceding process, you must first compile the newInstance method in DatePickerFragment. The newInstance method can be called and accepted when DatePickerFragment is instantiated, and data is prepared before fragment create.
public static DatePickerFragment newInstance(Date date){ Bundle args=new Bundle(); args.putSerializable(EXTRA_DATE,date); DatePickerFragment fragment=new DatePickerFragment(); fragment.setArguments(args); return fragment; }
When data is returned, the onActivityResult method is overwritten.
The interaction process is as follows: