jQuery UI DatePicker: Disable Specified Days

jQuery Calendar Picker

One project I'm currently working on requires jQuery. The project also features a datepicker for requesting a visit to their location. jQuery UI's DatePicker plugin was the natural choice and it does a really nice job. One challenge I encountered was the need to prevent specific days from being picked. Here's the jQuery JavaScript I used to accomplish that.

The jQuery JavaScript

/* create an array of days which need to be disabled */
var disabledDays = ["2-21-2010","2-24-2010","2-27-2010","2-28-2010","3-3-2010","3-17-2010","4-2-2010","4-3-2010","4-4-2010","4-5-2010"];

/* utility functions */
function nationalDays(date) {
	var m = date.getMonth(), d = date.getDate(), y = date.getFullYear();
	//console.log('Checking (raw): ' + m + '-' + d + '-' + y);
	for (i = 0; i < disabledDays.length; i++) {
		if($.inArray((m+1) + '-' + d + '-' + y,disabledDays) != -1 || new Date() > date) {
			//console.log('bad:  ' + (m+1) + '-' + d + '-' + y + ' / ' + disabledDays[i]);
			return [false];
		}
	}
	//console.log('good:  ' + (m+1) + '-' + d + '-' + y);
	return [true];
}
function noWeekendsOrHolidays(date) {
	var noWeekend = jQuery.datepicker.noWeekends(date);
	return noWeekend[0] ? nationalDays(date) : noWeekend;
}

/* create datepicker */
jQuery(document).ready(function() {
	jQuery('#date').datepicker({
		minDate: new Date(2010, 0, 1),
		maxDate: new Date(2010, 5, 31),
		dateFormat: 'DD, MM, d, yy',
		constrainInput: true,
		beforeShowDay: noWeekendsOrHolidays
	});
});

The base code is taken from this forum post. You'll note that I created an array of dates in string format which also accommodates for comparing year.

I'd like to see jQuery UI implement a standard way of disabling days. Their DatePicker is very nice though so I can't complain too much!


Comments

  1. Mark

    I have to admit, I wish Mootools came with such a wide variaty of UI plugins…

    All and all, I think you accomplished your goal very well! Good stuff.

  2. Salih Gedik

    Nice. But I rarely need jQ. Mootools FTW isn’t it?

  3. Simeon

    Nice post! Can be easily expanded by populating he “disabledDays” using PHP to find all weekends, holidays, etc. I wonder what the performance impact is though if you span across several years as a typical selection might allow?

  4. Savageman

    @mark: you should try this Mootools DatePicker (also works for time): http://www.monkeyphysics.com/mootools/script/2/datepicker

    Doesn’t have a beforeShowDay option though…

  5. Douglas Neiner

    I would remove all the MooTools helpers :) and just use the jQuery native $.inArray function:

    Change this line: ArrayContains(disabledDays,(m+1) + ‘-’ + d + ‘-’ + y) to this instead: $.inArray(disabledDays,(m+1) + ‘-’ + d + ‘-’ + y) != -1

    Then you don’t need to two other functions from MooTools.

  6. Douglas Neiner

    @Douglas Neiner: Sorry, flip the arguments. $.inArray( value, array )

  7. David Walsh

    @Douglas Neiner: I’m a complete MooTools nerd — I didn’t even think to check the jQuery API. Will update.

  8. Josh Stauffer

    Interesting dilema and solution. My problem with the jQuery Datepicker is figuring out how to store selected start and end dates in a cookie.

  9. Brad Zickafoose

    Is it possible to have the DatePicker block out today’s date as well as past dates from being selected, only allowing tomorrow and future dates available for selection?

  10. David Walsh

    @Brad Zickafoose: The code above actually automatically disables today and all previous days.

  11. Brad Zickafoose

    @David Walsh: oh nice… silly me. :-)

  12. James

    Hi,

    This code is nice, very helpful. But I am pretty new to jQuery, in asp.net I use some code to generate the dates in the array but the single digits are formatted with a zero like 01 for January etc. So when my arrays are formatted they use zero and the dates are not being blocked out on the calendar, could anyone advise the best solution so that the code will accept 0x numbers?

    Many thanks.

  13. Alex Ho

    Thanks David!

    I built an internal application for my department and I am using the datepicker plugin as well. I don’t think anyone will ever select a day on the weekend. I might as well disable it too.

  14. Alex Ho

    Oh wait, apparently there’s already a built-in function for removing weekends!

    Thanks for the script though.

  15. Neha

    Hello,

    Really nice plugin! Can we do that same with mootools???
    Any link??

    thanks!!

  16. billski

    Thanks for the great plugin. This is the best version of datepicker I found, and I tested many. The blocked dates, and blocked current date are exactly what I needed. It was easy for a beginner like me to implement.

  17. nyett

    hi, do you know how to take the national days from MySQL database and disable those days on datepicker?? need your help plssssss

  18. Jonathan

    How do you edit this to include the current date?

  19. Jonathan

    How do you edit this to include todays date?

  20. ajaxgoogle

    Please someone write normal Datepicker as Jquery has in Mootools!

  21. Andrew Pokoj

    First off, great script from what I can understand… I just started to teach myself javascript and I can’t seem to to enable the weekends so I can just make a custom array for the two months i need the calendar for (Fri/Sat in Sept, and our operating schedule in Oct this year)

    How would I go about doing this?

  22. Boni

    yeah i need to include todays date also.. thanks

  23. Boni

    i created a 2nd textbox and now i have 2 ‘#firstDate’ and ‘#endDate’

    i want ‘#endDate’ display dates the same date as #firstDate’ with future dates. Possible? thanks

  24. nyett

    @Boni: do you want the EndDate has the same that as FirstDate or the EndDate disable the dates before the firstDate??

  25. nyett

    @Boni: do you want the EndDate has the same that as FirstDate or the EndDate disable the dates before the firstDate?? So, the endDate always bigger than the firstDate.

  26. Yun

    Wht do i have to do make it to disable dates between “2-21-2010″ and “2-24-2010″?

  27. mitja.GTI

    Hi,
    all i see is every date disabled in you demo. This i could really use, so i would love you to update this post with a working solution.
    Thanks.

  28. mitja.GTI

    Hi,
    all i see is every date disabled in you demo. This i could really use, so i would love you to update this post with a working solution.
    Thanks.

  29. Matt

    Maybe I’m just missing something, but why is there a for loop in this code? It seems like you are simply doing the $.inArray multiple times on the same date. Amy I missing something?

  30. savita

    Checked the demo it was not working, so just update line #9 with the following code and it is working for me now!!!.

    if($.inArray((m+1) + ‘-’ + d + ‘-’ + y,disabledDays) != -1 )

  31. Nicole

    Thank you for sharing this, huge time saver!!!

  32. Fastenwandern

    Hey David,

    your site is very nice, but when i open the calendar no date is enabled. What shall I do?

    Bye Thomas

  33. Séb

    Hello there,

    Nice read.

    I have a question though,

    How can i disable all the day before the current date ?

    Regards, Séb.

    • Séb

      Dumb question sorry :)

      function noBefore(date){
      if (date < new Date()){
      return [false];
      }
      return [true];
      }

    • Harish

      Use this:

      minDate: 0

      its more easy and efficient.

    • mike

      Seb I wanted the same result – to disable all previous dates but I cant seem to get your version working. Old dates are still selectable using the below:

      function noBefore(date){
      if (date < new Date()){
      return [false];
      }
      return [true];
      }

      jQuery(document).ready(function() {
      jQuery('#datepicker').datepicker({
      minDate: new Date(2011, 5, 1),
      dateFormat: 'dd/mm/yy',
      constrainInput: true,
      beforeShowDay: noBefore
      });
      });

      @Harish: Wasn't sure what minDate was meant to replace.

      I''m not a coder so I'm just grabbing code here and trying to mesh it together.

  34. Jeremy

    Great post, however I’d like to know how to do this on several different datepickers on the same form with varying different selections. i.e. one datepicker can only chooses saturdays and the other can only pick sundays. Any idea?

    • Matt

      Jeremy,

      You are simply telling the object to call noWeekendsOrHolidays before displaying each date. So if you have two date pickers, you are going to have to initializations and you can simply have each initialization call separate functions.

      Hope I didn’t misunderstand the question. Hope that helps.

      Matt

  35. Patricia

    Thanks alot for that very helpfull post, David!

  36. Jon

    From the code above, what is the point of this for loop? It seems that disabledDays[i] is only used in a comment.

    for (i = 0; i date) {
    //console.log('bad: ' + (m+1) + '-' + d + '-' + y + ' / ' + disabledDays[i]);
    return [false];
    }
    }

    I changed it to:
    if($.inArray((m+1) + ‘-’ + d + ‘-’ + y,disabledDays) != -1 || new Date() > date) {
    //console.log(‘bad: ‘ + (m+1) + ‘-’ + d + ‘-’ + y + ‘ / ‘ + disabledDays[i]);
    return [false];
    }

    This is much faster because we are not iterating on the disabledDays array.

  37. Jon

    From the code above, what is the point of this for loop? It seems that disabledDays[i] is only used in a comment.

    for (i = 0; i date) {
    //console.log(‘bad: ‘ + (m+1) + ‘-’ + d + ‘-’ + y + ‘ / ‘ + disabledDays[i]);
    return [false];
    }
    }

    I changed it to:

    if($.inArray((m+1) + ‘-’ + d + ‘-’ + y,disabledDays) != -1 || new Date() > date) {
    return [false];
    }

    This is much faster because we are not iterating on the disabledDays array.

  38. Sadaf Chohan

    Thankx for such a brilliant script it solved my problem in few hours … i modified it according to my requirement … My requirement was to highlight the user defined days on the calendar … Thank you so much for this helping code it was real useful and easy to understand

  39. Tokes

    I couldn’t get this to work for some reason, it just disabled weekends and did not disable any of the dates in the disabledDays array.

    Here is what I did: http://tokenposts.blogspot.com/2011/05/jquery-datepicker-disable-specific.html

  40. mike

    whoops…fixed code post:


    function noBefore(date){
    if (date < new Date()){
    return [false];
    }
    return [true];
    }

    /* create datepicker & timepicker*/
    jQuery(document).ready(function() {
    jQuery('#datepicker').datepicker({
    minDate: new Date(2011, 5, 1),
    dateFormat: 'dd/mm/yy',
    constrainInput: true,
    beforeShowDay: noBefore
    });
    });

  41. Virendra Dugar

    Well, there is a better way to disable only the weekends.

    $(function() {
    $(‘#’).datepicker({
    beforeShowDay: $.datepicker.noWeekends
    });
    });

    http://jquerybyexample.blogspot.com/2010/07/disable-weekends-in-jquery-ui.html

  42. Virendra Dugar

    Well, there is a better way to disable only the weekends.


    $(function() {
    $('#').datepicker({
    beforeShowDay: $.datepicker.noWeekends
    });
    });

    http://jquerybyexample.blogspot.com/2010/07/disable-weekends-in-jquery-ui.html

  43. Stefan Gabos

    See also http://stefangabos.ro/jquery/zebra-datepicker/ where the disabling of dates is much easier using a syntax similar to cron’s

  44. Timur

    Damn it David. Is there anything your blog does not have. All the solutions are here. Thank you very much :)

  45. Gulio

    Thanks for this nice code. Is there any simple way to just only disable the disableddays, but keep showing the weekends?

    Thanks already!

  46. Gulio

    Fixed already:

    return [0] ? nationalDays(date) : noWeekend;

  47. jitesh

    Hi, david can you please tell me how can i change css of specific dates..?

  48. Thom

    Thanks a bunch! Your walk-through totally did the trick on a resort-booking application I’m working on!


Be Heard!

Share your thoughts without being a jerk! And wrap your code in <code> tags, f00!

Name*:
Email*:
Website: