使用ViewPager实现左右“无限”滑动的万年历
有时候就是这样,研究一个问题,一开始想到了一个觉得可行的方案,然后去尝试;尝试了很久、很多次,已经要放弃了,关掉电脑心里
这次我遇到的是这样一个问题,由于系统的CalendarView不太美观,所以要自己实现一个日历的布局;所以想到了使用GridView,然后
用ViewPager做左右滑动切换日期的效果;
mCurrentPageNumber
来分别代表当前展示的日期和当前所示的ViewPager的页数;然后滑动的时候,根据传进来的pageNum和当前的mCurrentPageNumber的大小来判断创建的日历是下个月,还是上个月;
mCurrentPageNumber的值为501;问题就出在这里,刚开始的时候初始化500,比如500代表8月,那么499的时候就是七月,这没有问题,可是当七月的界面创建完成之后,当前的Calendar就是七月,而
mCurrentPageNumber是499,在创建501的时候七月加1就是八月,也就是本来501代表9月,可是显示的是8月;滑动之后还出现了各种不可预知的结果......然后我就开始无数次的微调,判断如果是初始化就怎么样,然后就怎么样;改变当前页的值等等;一直一直弄了很久之后我都要昏了可还是没有搞定;最后决定算了,解决不了......
package tk.sweetvvck.calender.adapter; import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date; import tk.sweetvvck.calender.R;
import android.app.Activity;
import android.content.res.Resources;
import android.view.Gravity;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.LinearLayout;
import android.widget.LinearLayout.LayoutParams;
import android.widget.TextView; public class CalendarGridViewAdapter extends BaseAdapter { private Calendar calStartDate = Calendar.getInstance();// 当前显示的日历
private Calendar calToday = Calendar.getInstance(); // 今日
private int iMonthViewCurrentMonth = 0; // 当前视图月
// 根据改变的日期更新日历
// 填充日历控件用
private void UpdateStartDateForMonth() {
calStartDate.set(Calendar.DATE, 1); // 设置成当月第一天
iMonthViewCurrentMonth = calStartDate.get(Calendar.MONTH);// 得到当前日历显示的月 // 星期一是2 星期天是1 填充剩余天数
int iDay = 0;
int iFirstDayOfWeek = Calendar.MONDAY;
int iStartDay = iFirstDayOfWeek;
if (iStartDay == Calendar.MONDAY) {
iDay = calStartDate.get(Calendar.DAY_OF_WEEK) - Calendar.MONDAY;
if (iDay < 0)
iDay = 6;
}
if (iStartDay == Calendar.SUNDAY) {
iDay = calStartDate.get(Calendar.DAY_OF_WEEK) - Calendar.SUNDAY;
if (iDay < 0)
iDay = 6;
}
calStartDate.add(Calendar.DAY_OF_WEEK, -iDay); calStartDate.add(Calendar.DAY_OF_MONTH, -1);// 周日第一位 }
ArrayList<java.util.Date> titles;
private ArrayList<java.util.Date> getDates() { UpdateStartDateForMonth(); ArrayList<java.util.Date> alArrayList = new ArrayList<java.util.Date>(); for (int i = 1; i <= 42; i++) {
alArrayList.add(calStartDate.getTime());
calStartDate.add(Calendar.DAY_OF_MONTH, 1);
} return alArrayList;
} private Activity activity;
Resources resources;
// construct
public CalendarGridViewAdapter(Activity a,Calendar cal) {
calStartDate=cal;
activity = a;
resources=activity.getResources();
titles = getDates();
} public CalendarGridViewAdapter(Activity a) {
activity = a;
resources=activity.getResources();
} @Override
public int getCount() {
return titles.size();
} @Override
public Object getItem(int position) {
return titles.get(position);
} @Override
public long getItemId(int position) {
return position;
} @SuppressWarnings("deprecation")
@Override
public View getView(int position, View convertView, ViewGroup parent) {
LinearLayout iv = new LinearLayout(activity);
iv.setGravity(Gravity.CENTER);
iv.setOrientation(LinearLayout.VERTICAL);
iv.setBackgroundColor(resources.getColor(R.color.white)); Date myDate = (Date) getItem(position);
Calendar calCalendar = Calendar.getInstance();
calCalendar.setTime(myDate); final int iMonth = calCalendar.get(Calendar.MONTH);
final int iDay = calCalendar.get(Calendar.DAY_OF_WEEK); // 判断周六周日
iv.setBackgroundColor(resources.getColor(R.color.white));
if (iDay == 7) {
// 周六
iv.setBackgroundColor(resources.getColor(R.color.text_6));
} else if (iDay == 1) {
// 周日
iv.setBackgroundColor(resources.getColor(R.color.text_7));
} else { }
// 判断周六周日结束 TextView txtToDay = new TextView(activity);
txtToDay.setGravity(Gravity.CENTER_HORIZONTAL);
txtToDay.setTextSize(9);
if (equalsDate(calToday.getTime(), myDate)) {
// 当前日期
iv.setBackgroundColor(resources.getColor(R.color.selection));
txtToDay.setText("TODAY!");
}
// 设置背景颜色结束 // 日期开始
TextView txtDay = new TextView(activity);// 日期
txtDay.setGravity(Gravity.CENTER_HORIZONTAL); // 判断是否是当前月
if (iMonth == iMonthViewCurrentMonth) {
txtToDay.setTextColor(resources.getColor(R.color.ToDayText));
txtDay.setTextColor(resources.getColor(R.color.Text));
} else {
txtDay.setTextColor(resources.getColor(R.color.noMonth));
txtToDay.setTextColor(resources.getColor(R.color.noMonth));
} int day = myDate.getDate(); // 日期
txtDay.setText(String.valueOf(day)); LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
iv.addView(txtDay, lp); LinearLayout.LayoutParams lp1 = new LinearLayout.LayoutParams(
LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
iv.addView(txtToDay, lp1); return iv;
} @SuppressWarnings("deprecation")
private Boolean equalsDate(Date date1, Date date2) {
if (date1.getYear() == date2.getYear()
&& date1.getMonth() == date2.getMonth()
&& date1.getDate() == date2.getDate()) {
return true;
} else {
return false;
}
}
}
/*
* Copyright 2012 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package tk.sweetvvck.calender.activity;
import java.util.Calendar;
import tk.sweetvvck.calender.R;
import tk.sweetvvck.calender.adapter.CalendarGridViewAdapter;
import tk.sweetvvck.calender.utils.Utils;
import android.app.Activity;
import android.app.Fragment;
import android.content.res.Resources;
import android.graphics.Color;
import android.os.Bundle;
import android.view.Display;
import android.view.Gravity;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.view.WindowManager;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
import android.widget.BaseAdapter;
import android.widget.GridView;
import android.widget.LinearLayout;
import android.widget.LinearLayout.LayoutParams;
import android.widget.TextView;
public class CalendarFragment extends Fragment {
public static final String ARG_PAGE = "page";
private int mPageNumber;
private Calendar mCalendar;
private CalendarGridViewAdapter calendarGridViewAdapter;
public static Fragment create(int pageNumber) {
CalendarFragment fragment = new CalendarFragment();
Bundle args = new Bundle();
args.putInt(ARG_PAGE, pageNumber);
fragment.setArguments(args);
return fragment;
}
public CalendarFragment() {
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mPageNumber = getArguments().getInt(ARG_PAGE);
mCalendar = Utils.getSelectCalendar(mPageNumber);
calendarGridViewAdapter = new CalendarGridViewAdapter(getActivity(),
mCalendar);
}
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
// Inflate the layout containing a title and body text.
ViewGroup rootView = (ViewGroup) inflater.inflate(
R.layout.calendar_view, container, false);
GridView titleGridView = (GridView) rootView
.findViewById(R.id.gridview);
TitleGridAdapter titleAdapter = new TitleGridAdapter(getActivity());
initGridView(titleGridView, titleAdapter);
GridView calendarView = (GridView) rootView
.findViewById(R.id.calendarView);
initGridView(calendarView, calendarGridViewAdapter);
calendarView.setOnItemClickListener(new OnItemClickListener() {
@Override
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
for (int i = 0; i < parent.getCount(); i++) {
if ((i % 7) == 6) {
parent.getChildAt(i).setBackgroundColor(
getActivity().getResources().getColor(
R.color.text_6));
} else if ((i % 7) == 0) {
parent.getChildAt(i).setBackgroundColor(
getActivity().getResources().getColor(
R.color.text_7));
} else {
parent.getChildAt(i).setBackgroundColor(
Color.TRANSPARENT);
}
}
view.setBackgroundColor(getActivity().getResources().getColor(
R.color.selection));
}
});
return rootView;
}
private void initGridView(GridView gridView, BaseAdapter adapter) {
gridView = setGirdView(gridView);
gridView.setAdapter(adapter);// 设置菜单Adapter
}
@SuppressWarnings("deprecation")
private GridView setGirdView(GridView gridView) {
gridView.setNumColumns(7);// 设置每行列数
gridView.setGravity(Gravity.CENTER_VERTICAL);// 位置居中
gridView.setVerticalSpacing(1);// 垂直间隔
gridView.setHorizontalSpacing(1);// 水平间隔
gridView.setBackgroundColor(getResources().getColor(
R.color.calendar_background));
WindowManager windowManager = getActivity().getWindowManager();
Display display = windowManager.getDefaultDisplay();
int i = display.getWidth() / 7;
int j = display.getWidth() - (i * 7);
int x = j / 2;
gridView.setPadding(x, 0, 0, 0);// 居中
return gridView;
}
public class TitleGridAdapter extends BaseAdapter {
int[] titles = new int[] { R.string.Sun, R.string.Mon, R.string.Tue,
R.string.Wed, R.string.Thu, R.string.Fri, R.string.Sat };
private Activity activity;
// construct
public TitleGridAdapter(Activity a) {
activity = a;
}
@Override
public int getCount() {
return titles.length;
}
@Override
public Object getItem(int position) {
return titles[position];
}
@Override
public long getItemId(int position) {
return position;
}
@Override
public View getView(int position, View convertView, ViewGroup parent) {
LinearLayout iv = new LinearLayout(activity);
TextView txtDay = new TextView(activity);
txtDay.setFocusable(false);
txtDay.setBackgroundColor(Color.TRANSPARENT);
iv.setOrientation(LinearLayout.VERTICAL);
txtDay.setGravity(Gravity.CENTER);
LinearLayout.LayoutParams lp = new LinearLayout.LayoutParams(
LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
int i = (Integer) getItem(position);
txtDay.setTextColor(Color.GRAY);
Resources res = getResources();
if (i == R.string.Sat) {
// 周六
txtDay.setBackgroundColor(res.getColor(R.color.title_text_6));
} else if (i == R.string.Sun) {
// 周日
txtDay.setBackgroundColor(res.getColor(R.color.title_text_7));
} else {
}
txtDay.setText((Integer) getItem(position));
iv.addView(txtDay, lp);
return iv;
}
}
}
package tk.sweetvvck.calender.activity; import java.util.Calendar;
import tk.sweetvvck.calender.R;
import tk.sweetvvck.calender.utils.Utils;
import android.app.Fragment;
import android.app.FragmentManager;
import android.os.Bundle;
import android.support.v13.app.FragmentStatePagerAdapter;
import android.support.v4.app.FragmentActivity;
import android.support.v4.view.ViewPager;
import android.widget.TextView;
/**
* 日历
* @author 程科
*/
public class MainActivity extends FragmentActivity {
private ViewPager viewPager;
private TextView tvMonth;
private String month;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
viewPager = (ViewPager) this.findViewById(R.id.viewpager);
final ScreenSlidePagerAdapter screenSlidePagerAdapter = new ScreenSlidePagerAdapter(
getFragmentManager());
viewPager.setAdapter(screenSlidePagerAdapter);
viewPager.setCurrentItem(500);
tvMonth = (TextView) this.findViewById(R.id.tv_month);
month = Calendar.getInstance().get(Calendar.YEAR)
+ "-"
+ Utils.LeftPad_Tow_Zero(Calendar.getInstance().get(
Calendar.MONTH) + 1);
tvMonth.setText(month);
viewPager.setOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageSelected(int position) {
Calendar calendar = Utils.getSelectCalendar(position);
month = calendar.get(Calendar.YEAR)
+ "-"
+ Utils.LeftPad_Tow_Zero(calendar.get(Calendar.MONTH) + 1);
tvMonth.setText(month);
}
@Override
public void onPageScrolled(int position, float positionOffset,
int positionOffsetPixels) {
}
@Override
public void onPageScrollStateChanged(int state) {
}
});
}
private class ScreenSlidePagerAdapter extends FragmentStatePagerAdapter {
public ScreenSlidePagerAdapter(FragmentManager fm) {
super(fm);
}
@Override
public Fragment getItem(int position) {
return CalendarFragment.create(position);
}
@Override
public int getCount() {
return 1000;
}
}
}
使用ViewPager实现左右“无限”滑动的万年历的更多相关文章
- ViewPager结合view无限滑动
使用viewPager进无限滑动,这里的实现是在适配器里面进行,当然在外头使用滑动监听也行. import android.support.v4.view.PagerAdapter; import a ...
- ViewPager无限滑动
2016-6-19 前言 View轮播效果在app中很常见,一想到左右滑动的效果就很容易想到使用ViewPager来实现.对于像我们常说的banner这样的效果,具备无限滑动的功能是可以用ViewPa ...
- Android使用ViewPager实现左右循环滑动及轮播效果
边界的时候会看到一个不能翻页的动画,可能影响用户体验.此外,某些区域性的ViewPager(例如展示广告或者公告之类的ViewPager),可能需要自动轮播的效果,即用户在不用滑动的情况下就能够看到其 ...
- android笔记:ViewPager实现界面的滑动
最近在学习ViewPager实现界面的滑动,拜读了郭神的博客文章,并抽取归纳了自己对ViewPager的理解. ViewPager实现界面滑动的步骤如下: 1.在xml布局内加入控件android.s ...
- Android 使用ViewPager实现左右循环滑动图片
ViewPager这个小demo实现的是可以左右循环滑动图片,下面带索引,滑到最后一页在往右滑动就要第一页,第一页往左滑动就到最后一页,先上效果图,用美女图片是我一贯的作风,呵呵 1. 首先看一 ...
- android 解决ViewPager双层嵌套的滑动问题
解决ViewPager双层嵌套的滑动问题 今天我分享一下ViewPager的双层嵌套时影响内部ViewPager的触摸滑动问题 之前在做自己的一个项目的时候,遇到广告栏图片动态切换,我第一时间想到的就 ...
- Android实战简易教程-第三十四枪(基于ViewPager和FragmentPagerAdapter实现滑动通用Tab)
上一段时间写过一篇文章<基于ViewPager实现微信页面切换效果> 里面实现了相似微信Tab的页面.可是这样的实现方法有个问题.就是以后全部的代码逻辑都必须在MainActivity中实 ...
- Android 仿美团网,探索使用ViewPager+GridView实现左右滑动查看更多分类的功能
看下效果图,自己考虑下自己会如何实现,然后再继续看看作者的实现~ 不记得什么时候,我留意到到美团网首页有使用ViewPager+GridView实现左右滑动查看更多分类的一个功能,感觉它很有趣,于是想 ...
- android 事件拦截 (Viewpager不可以左右滑动)
以前没有做过真正的需求,所以从来没有觉得事件拦截分发处理有什么好懂的. 现在做需求了,真的是什么需求都有,你作为开发都要去研究实现.比如说,只能点不能滑动的viewpager.其实这都可以不用view ...
随机推荐
- 【 Failed to create the Java Virtual Machine】的2种解决方式
初学Android,下载并安装好了eclipse,ADT和SDK之后,打开Eclipse时,出现: Failed to create the Java Virtual Machine 点击确定,ecl ...
- 揭开枚举类的面纱(Unlocking the Enumeration/enum Mystery)
枚举给用户定义固定数据组提供了方便.枚举类就是一系列常量整型值,这也就意味着枚举类型不能被修改. 这里我们将要讨论C语言中枚举类型的用法和限制. 枚举通过枚举关键值定义,类似结构体定义 语法(Synt ...
- jsp中iframe所包含的页面调用父页面的function方法
a.jsp中写了注册的Ext窗体loginWindow,也用iframe包含了另一个b.jsp,当在b.jsp中也有点击注册的链接,这时需要用到调用a.jsp中的loginWindow,因为如果你重新 ...
- USB Video Class及其实现
1 Video Class 基础概念Usb协议中,除了通用的软硬件电气接口规范等,还包含了各种各样的Class协议,用来为不同的功能定义各自的标准接口和具体的总线上的数据交互格式和内容.这些Class ...
- JavaScript 精髓整理篇之一(对象篇)postby:http://zhutty.cnblogs.com
废话篇头: 由于工作关系,所以写博文的时间有那么点~~,其实是输入法太懒了,都是输入法的错~~ 这一系列的博客将总结所有关于JavaScript语言的精髓,适合0基础到大师级别人物阅读. <Ja ...
- QlikView实现部分载入数据的功能(Partial Load)
问题背景: 一直非常想不通,公司花了N多钱请了一帮QlikView的Consultant做出来的solution居然没有涉及Reload的部分,以至于每次刷新数据都须要刷新整个Data Model,之 ...
- springmvc4+hibernate4分页查询功能
Springmvc+hibernate成为现在很多人用的框架整合,最近自己也在学习摸索,由于我们在开发项目中很多项目都用到列表分页功能,在此参考网上一些资料,以springmvc4+hibnerate ...
- sql server数据库将excel表中的数据导入数据表
一般有两种方法可以实现,一种是直接写sql语句,另外一种是利用sqlserver的管理工具实现.这里介绍的是后面一种方法. 步骤: 一.准备数据 1.将excel表另存为文本格式,注意文本格式需为ta ...
- 安卓状态栏通知Status Bar Notification
安卓系统通知用户三种方式: 1.Toast Notification 2.Dialog Notification 3.Status Bar Notification Status Bar Notifi ...
- JavaScript的数据类型转换
首先,由于JavaScript是弱类型语言(弱类型的语言的东西没有明显的类型,他能随着环境的不同,自动变换类型而强类型则没这样的规定,不同类型间的操作有严格定义,只有相同类型的变量才能操作,虽然系统也 ...