【问题标题】:Disable specific dates of day in Android date picker在 Android 日期选择器中禁用特定日期
【发布时间】:2016-06-06 13:39:03
【问题描述】:

我正在使用 datePicker,我可以通过以下代码禁用今天的最后几天和 30 天后的晚些时候:

DatePickerDialog datePicker = new DatePickerDialog();

             Calendar calender = Calendar.getInstance();
             long today = calender.getTimeInMillis();
             final long oneDay = 24 * 60 * 60 * 1000L;

             Date previousDays = new Date(today - 1000);
             datePicker.setMinDate(DateToCalendar(previousDays));

             Date nextMonth = new Date(today + 30 * oneDay);
             datePicker.setMaxDate(DateToCalendar(nextMonth));

如果我想禁用每个月的星期五,我该怎么做?

【问题讨论】:

    标签: android datepicker


    【解决方案1】:

    你可以使用这个库Material Date Time Picker,在这里你可以设置一个选项来显示特定的日期,例如:

    datePicker.setSelectableDays(Calendar[] days)
    

    并将Calendar 的数组作为包含所有可选日期的参数传递。

    【讨论】:

    • 非常感谢,这很好用。我不知道为什么标准的安卓系统如此有限。
    • 如何通过上述库中的天数来禁用?假设如何禁用所有周末?
    • 创建一个不包括周末的日期数组并将其作为可选日期传递。
    【解决方案2】:

    使用自定义 DatePickerDialog

    在 build.gradle 中添加这个

    编译'com.wdullaer:materialdatetimepicker:3.5.1'

    实施

    DatePickerDialog.OnDateSetListener到你的班级

    并导入

    import com.wdullaer.materialdatetimepicker.date.DatePickerDialog; 而不是 'import android.app.DatePickerDialog;'

    并添加此方法

     private void showDatePicker() { 
    
        Calendar calendar = Calendar.getInstance();
    
        DatePickerDialog dpd = DatePickerDialog.newInstance(
                this,
                calendar.get(Calendar.YEAR),
                calendar.get(Calendar.MONTH),
                calendar.get(Calendar.DAY_OF_MONTH)
        );
        dpd.show(getActivity().getFragmentManager(), "DatePickerDialog");
    
        SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy");
        String a = "07-03-2018"; // example
    
        java.util.Date date = null;
    
        try {
            date = sdf.parse(a);
        } catch (ParseException e) {
            e.printStackTrace();
        }
    
        calendar = dateToCalendar(date);
        System.out.println(calendar.getTime());
    
        List<Calendar> dates = new ArrayList<>();
        dates.add(calendar);
        Calendar[] disabledDays1 = dates.toArray(new Calendar[dates.size()]);
        dpd.setDisabledDays(disabledDays1);
    
    }
    
        private Calendar dateToCalendar(Date date) {
            Calendar calendar = Calendar.getInstance();
            calendar.setTime(date);
            return calendar;
        }
    
    
    
    
    @Override
    public void onDateSet(DatePickerDialog view, int year, int monthOfYear, int dayOfMonth) {
    
        String date = dayOfMonth+"/"+(monthOfYear+1)+"/"+year;
        textview.setText(date);
    
    }
    

    调用 showDatePicker()。

    多天

    改变这个

         String[] holidays = {"07-03-2018","05-03-2018","10-03-2018"};
    
        java.util.Date date = null;
    
        for (int i = 0;i < holidays.length; i++) {
    
            try {
                date = sdf.parse(holidays[i]);
            } catch (ParseException e) {
                e.printStackTrace();
            }
    
            calendar = dateToCalendar(date);
            System.out.println(calendar.getTime());
    
            List<Calendar> dates = new ArrayList<>();
            dates.add(calendar);
            Calendar[] disabledDays1 = dates.toArray(new Calendar[dates.size()]);
            dpd.setDisabledDays(disabledDays1);
        }
    

    【讨论】:

      【解决方案3】:

      android datepicker 无法做到这一点,您需要为自己创建一个自定义选择器。见MaterialDateTimePicker

      要禁用星期日,您必须像这样传递数组

            GregorianCalendar g1=new GregorianCalendar();
            g1.add(Calendar.DATE, 1);
            GregorianCalendar gc = new GregorianCalendar();
            gc.add(Calendar.DAY_OF_MONTH, 30);
             List<Calendar> dayslist= new LinkedList<Calendar>();
      Calendar[] daysArray;
      Calendar cAux = Calendar.getInstance();
      while ( cAux.getTimeInMillis() <= gc.getTimeInMillis()) {
          if (cAux.get(Calendar.DAY_OF_WEEK) != 1) {
              Calendar c = Calendar.getInstance();
              c.setTimeInMillis(cAux.getTimeInMillis());
              dayslist.add(c);
          }
          cAux.setTimeInMillis(cAux.getTimeInMillis() + (24*60*60*1000));
      }
      daysArray = new Calendar[dayslist.size()];
      for (int i = 0; i<daysArray.length;i++)
      {
          daysArray[i]=dayslist.get(i);
      }
      datePickerDialog.setSelectableDays(daysArray);
      

      【讨论】:

      • 使用 Calendar.SUNDAY 而不是 1
      【解决方案4】:

      访问https://stackoverflow.com/a/44692231/6631959 最好的方法和易于理解... 如果您正在寻找如何禁用指定日期,那就更好了。 不是循环程序。给出任何确切的日期并禁用它。

      代码在这里::

      SimpleDateFormat sdf = new SimpleDateFormat("dd-MM-yyyy");
                          String a = "26-07-2017";
                          java.util.Date date = null;
                          try {
                              date = sdf.parse(a);
                              MainActivity obj = new MainActivity();
                              calendar = obj.dateToCalendar(date);
                              System.out.println(calendar.getTime());
                          } catch (ParseException e) {
                              e.printStackTrace();
                          }
      
                          List<Calendar> dates = new ArrayList<>();
                          dates.add(calendar);
                          Calendar[] disabledDays1 = dates.toArray(new Calendar[dates.size()]);
                          dpd.setDisabledDays(disabledDays1);
          private Calendar dateToCalendar(Date date) {
                  Calendar calendar = Calendar.getInstance();
                  calendar.setTime(date);
                  return calendar;
              }
      

      【讨论】:

        【解决方案5】:

        由于这里接受的答案依赖于 com.wdullaer 的自定义实现,我想提出另一个我刚刚使用标准 MaterialDatePicker 和自定义 DateValidator 实现的解决方案:

                    // Create a custom date validator to only enable dates that are in the list
                val customDateValidator = object: CalendarConstraints.DateValidator {
                    override fun describeContents(): Int {  return 0  }
                    override fun writeToParcel(dest: Parcel?, flags: Int) {    }
                    override fun isValid(date: Long): Boolean {
        
                        listOfPossibleDatesAsLong.forEach {
                            val itemDateTime = Calendar.getInstance()
                            itemDateTime.timeInMillis = it
        
                            val dateDateTime = Calendar.getInstance()
                            dateDateTime.timeInMillis = date
        
                            if(itemDateTime.get(Calendar.YEAR) == dateDateTime.get(Calendar.YEAR)
                                && itemDateTime.get(Calendar.MONTH) == dateDateTime.get(Calendar.MONTH)
                                && itemDateTime.get(Calendar.DAY_OF_MONTH) == dateDateTime.get(Calendar.DAY_OF_MONTH))
                                return true
                        }
                        return false
                    }
                }
        

        除了 CalendarConstraints 中的其他约束,现在只需设置 customDateValidator,这也可以与 setStart(...) 和 setEnd(...) 一起使用

                // Build constraints.
                val constraintsBuilder =
                    CalendarConstraints.Builder().apply {
                            // other constraints
                            setValidator(customDateValidator)
                        }
                    }
        

        然后定义datePicker并显示出来

                val datePicker =
                    MaterialDatePicker.Builder.datePicker()
                        .setTitleText("Select date")
                        .setSelection(MaterialDatePicker.todayInUtcMilliseconds())
                        .setCalendarConstraints(constraintsBuilder.build())
                        .build()
        
                datePicker.addOnPositiveButtonClickListener {
                    // Respond to positive button click...
                }
        
                datePicker.show(parentFragmentManager, "tag")
        

        我需要承认,我不明白如果没有正确实施 describeContents 和 writeToParcel 是否会对任何事情产生负面影响,也许可以在这里讨论。但是,就我的目的而言,这非常有效。

        【讨论】:

        • 我在验证器中比较日期的方式在真实设备上不起作用,所以我更新了上面的代码。
        【解决方案6】:

        试试Android Material Date and Timepicker

        来源Link

        周日和周六禁用。

        您还可以使用 setDisabledDays() 方法禁用任何特定日期

                    //Disable all SUNDAYS and SATURDAYS between Min and Max Dates
                    for (Calendar loopdate = min_date_c; min_date_c.before(max_date_c); min_date_c.add(Calendar.DATE, 1), loopdate = min_date_c) {
                        int dayOfWeek = loopdate.get(Calendar.DAY_OF_WEEK);
                        if (dayOfWeek == Calendar.SUNDAY || dayOfWeek == Calendar.SATURDAY) {
                            Calendar[] disabledDays =  new Calendar[1];
                            disabledDays[0] = loopdate;
                            datePickerDialog.setDisabledDays(disabledDays);
                        }
                    }
        

        【讨论】:

          【解决方案7】:

          使用MaterialDatePicker 中的https://github.com/material-components/material-components-android

          在选择器中禁用周末的示例

          val constraintsBuilder =
                  CalendarConstraints.Builder().setValidator(DateValidatorWeekdays()).build()
          
              MaterialDatePicker.Builder.datePicker().setCalendarConstraints(constraintsBuilder).build()
                  .show(childFragmentManager, "Data_Picker")
          

          DateValidator 类:

          https://github.com/material-components/material-components-android/blob/master/catalog/java/io/material/catalog/datepicker/DateValidatorWeekdays.java

          【讨论】:

            猜你喜欢
            • 2014-05-15
            • 1970-01-01
            • 2022-01-12
            • 1970-01-01
            • 1970-01-01
            • 2020-08-25
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多