Android自定义实现日历控件

本文实例为大家分享了Android自定义实现日历控件的具体代码,供大家参考,具体内容如下

1. Calendar类

2. 布局

创建calendar_layout.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

android:padding="20sp"

android:orientation="vertical"

android:layout_width="match_parent"

android:layout_height="match_parent">

<RelativeLayout

android:id="@+id/titleRl"

android:layout_width="match_parent"

android:layout_height="30dp">

<TextView

android:id="@+id/lastTv"

android:text="上一月"

android:layout_alignParentLeft="true"

android:gravity="center"

android:layout_width="wrap_content"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/monthTv"

android:text="十一月"

android:gravity="center"

android:layout_centerHorizontal="true"

android:layout_width="wrap_content"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/nextTv"

android:text="下一月"

android:gravity="center"

android:layout_alignParentRight="true"

android:layout_width="wrap_content"

android:layout_height="30dp"></TextView>

</RelativeLayout>

<LinearLayout

android:id="@+id/weekLl"

android:orientation="horizontal"

android:layout_width="match_parent"

android:layout_height="wrap_content">

<TextView

android:id="@+id/Tv7"

android:text="日"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv1"

android:text="一"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv2"

android:text="二"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv3"

android:text="三"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv4"

android:text="四"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv5"

android:text="五"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

<TextView

android:id="@+id/Tv6"

android:text="六"

android:gravity="center"

android:layout_weight="1"

android:layout_width="0dp"

android:layout_height="30dp"></TextView>

</LinearLayout>

<GridView

android:id="@+id/calendarCv"

android:numColumns="7"

android:layout_width="match_parent"

android:layout_height="match_parent"></GridView>

</LinearLayout>

创建item_layout.xml

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"

android:layout_width="match_parent"

android:layout_height="match_parent">

<TextView

android:id="@+id/itemTv"

android:gravity="center"

android:layout_width="match_parent"

android:layout_height="match_parent"></TextView>

</LinearLayout>

在activity_main.xml中

<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"

xmlns:app="http://schemas.android.com/apk/res-auto"

xmlns:tools="http://schemas.android.com/tools"

android:layout_width="match_parent"

android:layout_height="match_parent"

tools:context=".MainActivity">

<com.aye.newcalendar.NewCalendar

android:id="@+id/calendarNc"

android:gravity="center"

android:layout_width="match_parent"

android:layout_height="match_parent"></com.aye.newcalendar.NewCalendar>

</androidx.constraintlayout.widget.ConstraintLayout>

3. 业务处理

创建NewCalendar类,继承LinearLayout

public class NewCalendar extends LinearLayout {

private TextView lastTv,nextTv,dateTv;

private GridView calendarGv;

private Calendar calendar=Calendar.getInstance(); //日历控件初始化

//重写三个构造方法

public NewCalendar(Context context) {

super(context);

}

public NewCalendar(Context context, @Nullable AttributeSet attrs) {

super(context, attrs);

initControl(context); //绑定控件

}

public NewCalendar(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {

super(context, attrs, defStyleAttr);

initControl(context); //绑定控件

}

private void initControl(Context context){

bindControl(context); //绑定控件

bindControlEvent(); //绑定控件事件

}

//绑定控件事件方法

private void bindControlEvent() {

renderCalendar();

//“下一月”点击事件

nextTv.setOnClickListener(new OnClickListener() {

@Override

public void onClick(View v) {

calendar.add(Calendar.MONTH,+1); //月份+1

renderCalendar();

}

});

//“上一个”点击事件

lastTv.setOnClickListener(new OnClickListener() {

@Override

public void onClick(View v) {

calendar.add(Calendar.MONTH,-1); //月份-1

renderCalendar();

}

});

}

private void renderCalendar() {

SimpleDateFormat sdf = new SimpleDateFormat("MMM yyy"); //日期格式化

dateTv.setText(sdf.format(calendar.getTime())); //设置月份

ArrayList<Date> cells = new ArrayList<>();

Calendar calendar1 = (Calendar) calendar.clone(); //克隆日历对象

calendar1.set(Calendar.DAY_OF_MONTH, 1); //置于当月第一天;

int prevDays = calendar1.get(Calendar.DAY_OF_WEEK) - 1; //获取上个月最后一天是星期几

calendar1.add(Calendar.DAY_OF_MONTH, -prevDays); //第一天

int maxCount = 6 * 7; //设置每个月最大天数

//循环存入集合中

while (cells.size() < maxCount) {

cells.add(calendar1.getTime());

calendar1.add(Calendar.DAY_OF_MONTH, 1); //日期+1

}

//设置适配器

calendarGv.setAdapter(new CalendarAdapter(getContext(),cells));

}

//适配器

private class CalendarAdapter extends ArrayAdapter<Date>{

LayoutInflater layoutInflater;

public CalendarAdapter(@NonNull Context context,ArrayList<Date> days) {

super(context, R.layout.item_layout,days);

layoutInflater=LayoutInflater.from(context);

}

@NonNull

@Override

public View getView(int position, @Nullable View convertView, @NonNull ViewGroup parent) {

Date date=getItem(position);

ViewHolder viewHolder;

if (convertView==null){ //初始化绑定

convertView=layoutInflater.inflate(R.layout.item_layout,parent,false);

viewHolder=new ViewHolder();

viewHolder.itemTv=convertView.findViewById(R.id.itemTv);

convertView.setTag(viewHolder);

}

viewHolder= (ViewHolder) convertView.getTag();

int day=date.getDate();

viewHolder.itemTv.setText(String.valueOf(day)); //赋值

return convertView;

}

class ViewHolder{

TextView itemTv;

}

}

private void bindControl(Context context) {

LayoutInflater inflater=LayoutInflater.from(context);

inflater.inflate(R.layout.calendar_layout,this);

lastTv=findViewById(R.id.lastTv);

nextTv=findViewById(R.id.nextTv);

dateTv=findViewById(R.id.dateTv);

calendarGv=findViewById(R.id.calendarGv);

}

}

3. 定制UI

在适配器getView()方法中,个性化日历界面

Date now=new Date();

Boolean isTheSameMonth=false; //是否与当前月份相同

//判断显示的日期月份与当前月份相同

if (date.getMonth()==now.getMonth()) { //月份相同

isTheSameMonth = true;

}

//若显示的日期月份与当前月份相同,则设置字体颜色是黑色

if (isTheSameMonth) {

viewHolder.itemTv.setTextColor(Color.parseColor("#000000"));

}

//设置当前日期字体为红色

if (now.getDate()==date.getDate()&&now.getMonth()==date.getMonth()&&now.getYear()==date.getYear()){

viewHolder.itemTv.setTextColor(Color.parseColor("#ff0000"));

}

4. 事件监听

在NewCalendar中,首先编写长按事件的接口,然后设置适配器点击事件

//长按事件接口

public interface NewCalendarListener{

void onItemClick(Date date);

}

//适配器长按事件

calendarGv.setOnItemLongClickListener(new AdapterView.OnItemLongClickListener() {

@Override

public boolean onItemLongClick(AdapterView<?> parent, View view, int position, long id) {

if (listener==null){

return false;

}else {

//获取长按的位置,传入onItemClick方法中

listener.onItemClick((Date) parent.getItemAtPosition(position));

return true;

}

}

});

在MainActivity中,实现长按事件接口并重写方法,实现长按某个日期弹出Toast显示当前长按日期。

@Override

protected void onCreate(Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_main);

NewCalendar calendar=findViewById(R.id.calendarNc);

calendar.listener=this;

}

//MainActivity实现长按事件接口

@Override

public void onItemClick(Date date) {

DateFormat df= SimpleDateFormat.getDateInstance();

Toast.makeText(this,df.format(date),Toast.LENGTH_SHORT).show();

}

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。

以上是 Android自定义实现日历控件 的全部内容, 来源链接: utcz.com/p/244105.html

回到顶部