Android 4.0日历(calendar)源码分析之DayFragment
周视图
周视图和日视图都是由DayFragment管理的,因为两者有很相似的地方:
1.都是直接用自定义的view绘出来的
2.都是两个在viewswitcher中的dayview交替显示
3.整个视图基本上都只有一个dayview,没有多余的控件(actionbar除外,周视图上面的周几提示除外)
在相同的Fragment下能显示出不同view的原因是allinoneactivity他们各自的参数不一样.
case ViewType.DAY: //如果当前为日视图
….
frag = new DayFragment(timeMillis, 1);
case ViewType. WEEK: //如果当前为周视图
….
frag = new DayFragment(timeMillis, 7);
一周有7天,所以第二个参数为7 ,一日只有一天,所以第二个参数为1.
DayFragment中在通过将第二个参数传递给DayView,DayView根据不同的参数绘出不同的界面。
因此要分析这两个视图,重点还是集中在DayFragment和DayView两个文件中。
除此之外,你还应该了解ViewSwitcher的用法。
我们从DayFragment开始吧。
DayFragment
首先是DayFragment的构造函数:
public DayFragment(long timeMillis, int numOfDays) {
mNumDays = numOfDays;
if (timeMillis == 0) {
mSelectedDay.setToNow();
} else {
mSelectedDay.set(timeMillis);
}
}
mNumDays保存了刚刚提到参数。
然后在makeView()方法中这个值传递给了DayView
public View makeView() {
mTZUpdater.run();
DayView view = new DayView(getActivity(), CalendarController
.getInstance(getActivity()), mViewSwitcher, mEventLoader, mNumDays);
view.setId(VIEW_ID);
view.setLayoutParams(new ViewSwitcher.LayoutParams(
LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT));
view.setSelected(mSelectedDay, false, false);
return view;
}
makeView会在ViewSwitcher加载的时候自动调用,因为我们在DayFragment里面将ViewSwitcher的“工厂”设置成了当前DayFragment对象。这是在onCreateView()中完成的:
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.day_activity, null);
mViewSwitcher = (ViewSwitcher) v.findViewById(R.id.switcher);
mViewSwitcher.setFactory(this);
mViewSwitcher.getCurrentView().requestFocus();
((DayView) mViewSwitcher.getCurrentView()).updateTitle();
return v;
}
onCreateView获取到了Fragment的相对应的xml文件day_activity,里面有个ViewSwitcher控件,mViewSwitcher.setFactory(this)将给自己装入子元素的工厂设置成当前DayFragment对象,以便调用上面提到的makeView,然后下面两行
mViewSwitcher.getCurrentView().requestFocus();
((DayView) mViewSwitcher.getCurrentView()).updateTitle();
是对mViewSwitcher做一些初始化。
onCreate:
public void onCreate(Bundle icicle) {
super.onCreate(icicle);
Context context = getActivity();
mInAnimationForward = AnimationUtils.loadAnimation(context, R.anim.slide_left_in);
mOutAnimationForward = AnimationUtils.loadAnimation(context, R.anim.slide_left_out);
mInAnimationBackward = AnimationUtils.loadAnimation(context, R.anim.slide_right_in);
mOutAnimationBackward = AnimationUtils.loadAnimation(context, R.anim.slide_right_out);
mEventLoader = new EventLoader(context);
}