0

I am currently using the DatePicker in Android to let the user select a date. Is there a possibility to only allow the user to select Mondays and disable all other days for selection? I did not find anything in the Documentation.

Currently I am using this to show the DatePicker:

DatePickerDialog datePickerDialog = new DatePickerDialog(AddAppointment.this,
        new DatePickerDialog.OnDateSetListener() {

            @Override
            public void onDateSet(DatePicker view, int year,
                                  int monthOfYear, int dayOfMonth) {

            // Do stuff with the info
            }
        }, setYear, setMonth, setDay);
datePickerDialog.show();
ankuranurag2
  • 2,300
  • 15
  • 30
Nidhoegger
  • 4,973
  • 4
  • 36
  • 81
  • I don't think such a function is built in. You have to either write your own `DatePickerDialog` or just let the user choose a day/date and take the nearest Monday to it, depends on your requirements. There may be more options... – deHaar Jan 30 '19 at 12:43
  • I was afraid that this may be the answer :/. Is there a builtin control to select a Wekk of Year instead of a given date? – Nidhoegger Jan 30 '19 at 12:44
  • I don't think so... but you can always get the week of year the chosen date is in by using `java.time`. In the worst case, you have to do it **and** tell the user how his choice will be treated. – deHaar Jan 30 '19 at 12:45
  • Please tell us what you are trying to achieve. Do you want something like a `CalendarWeekPickerDialog` (which would be to be implemented)? Do you really want the user to select a calendar week or would selecting a date and calculating its calendar week be sufficient? – deHaar Jan 30 '19 at 12:51

3 Answers3

4

You can use this library Material Date Time Picker, here you can set an option to show specific dates, For Example:

datePicker.setSelectableDays(Calendar[] days)

And pass the array of Calendar as a parameter which contains all the selectable date.

for finding monday array you can use this logic:- Get all Fridays in a date Range in Java

Uday Nayak
  • 429
  • 4
  • 20
1

You can try to do it little bit differently. First, change font color of days user don't want to pick (all except Mondays) and than filter active day selected and disable functionality until Monday is selected.

Mārtiņš Ciekurs
  • 437
  • 1
  • 6
  • 25
1

You can calculate the calendar week of the chosen date or calculate the most recent Monday using one of the methods below. They are commented, so I keep the text short.

public class ExampleDateCalculation {

    public static void main(String[] args) {
        int dayOfMonth = 4;
        int monthOfYear = 3;
        int year = 2018;

        // create a java.time.LocalDate of the given integers
        LocalDate localDate = LocalDate.of(year, monthOfYear, dayOfMonth);

        // calculate the calendar week of it
        int calendarWeekTheLocalDateIsIn = getCalendarWeek(localDate);

        // calculate the last Monday before this date
        LocalDate lastMonday = getLastFrom(DayOfWeek.MONDAY, localDate);

        // create a formatter for your locale
        DateTimeFormatter germanDateFormatter = DateTimeFormatter.ofPattern("dd.MM.yyyy");

        System.out.println(localDate.format(germanDateFormatter)
                + " is in calendar week "
                + calendarWeekTheLocalDateIsIn
                + " of the system locale and the last Monday before was at "
                + lastMonday.format(germanDateFormatter));
    }

    /**
     * <p>
     * Gets the calendar week number of the given {@link LocalDate} based on the
     * {@link Locale} of the operating system.
     * </p>
     * 
     * @param localDate the date of the day
     * @return the calendar week number the day is in
     */
    public static int getCalendarWeek(LocalDate localDate) {
        WeekFields weekFields = WeekFields.of(Locale.getDefault());
        return localDate.get(weekFields.weekOfWeekBasedYear());
    }

    /**
     * <p>
     * Gets the date of the last given weekday or day of week starting from the
     * weekday of the given date. The method calculates the date of the nearest
     * weekday chronologically backwards.
     * </p>
     * <p>
     * <strong>For example:</strong><br>
     * If the weekday of the given date is a Monday and the given day of week is a
     * Tuesday, then this method will return the date of the Tuesday before today,
     * which is 6 days back in the past.
     * </p>
     * 
     * @param weekday the day of week whose date is to be determined
     * @param from    the date to start from calculating backwards
     * @return the date of the last given day of week starting from the given date
     */
    public static LocalDate getLastFrom(DayOfWeek weekday, LocalDate from) {
        DayOfWeek fromWeekday = from.getDayOfWeek();
        int fromWeekdayValue = fromWeekday.getValue();
        int weekdaysValue = weekday.getValue();
        int daysToSubtract = 0;

        /*
         * Calculate the days to go back and be beware of negative values by means of
         * case differentiation. Get the positive difference by subtracting the smaller
         * value from the larger one and subtract a week if the result would be 0.
         */
        if (fromWeekdayValue < weekdaysValue) {
            daysToSubtract = 7 - (weekdaysValue - fromWeekdayValue);
        } else if (fromWeekdayValue > weekdaysValue) {
            daysToSubtract = fromWeekdayValue - weekdaysValue;
        } else {
            daysToSubtract = 7;
        }

        return from.minusDays(daysToSubtract);
    }
}

If you want the user to only see calendar weeks or Mondays, follow the suggestions given in Uday Nayak's answer.

If anyone finds errors in or knows disadvantages of this code, please let me know.

deHaar
  • 17,687
  • 10
  • 38
  • 51