views:

183

answers:

3

I am currently using jquery ui datepicker for forms that have date inputs. The problem is on my current form I need the user to just select a month. How would I got about doing this using jquery ui date picker?

A: 

I'm not aware of a jQuery datepicker where the UI of the widget operates on month and year only.

An alternative approach: Masked Input Plugin.

Using mm/yyyy as an example:

$("#date").mask("99/9999");

micahwittman
A: 

What about ignoring the selected day in the display (and forcing the date to the 1st for some consistency):

$('.selector').datepicker({
    dateFormat: 'mm/yyyy',
    onSelect: function(dateText, inst) {
        $(this).datepicker('setDate', dateText.replace(/[0-9]{2}$/, '01'));
    }
});

Or else you could do the same thing on the server (although its less obvious to the user).

For the sake of usability you might need to say something like "Choose any day in the desired month".

Rob Van Dam
+4  A: 

You could take advantage of the configurability of jQuery UI's datepicker and use some CSS and JavaScript to achieve the behavior you've described. The following solution uses CSS to hide the calendar portion of the datepicker and some JavaScript to handle the month and year selection:

Working Demo

http://jsbin.com/uzafo (editable via http://jsbin.com/uzafo/edit)

Full Source

monthAndYear.css

.ui-datepicker.monthAndYear {
  width: 20em;
}
.ui-datepicker.monthAndYear .ui-datepicker-calendar {
  display: none;
}
.ui-datepicker.monthAndYear .ui-datepicker-header {
  margin-bottom: 0.2em;
}

monthAndYear.js

var monthAndYear = {
  /**
   * datepicker doesn't update the input field since
   * we don't actually select a date, so we have to 
   * manually determine the selected month and year
   * and update the input field ourselves.
  **/
  getMonthAndYear: function (dateText, instance) {
    if (!instance.settings.monthAndYear) {
      return;
    }

    var
      selectedYear = instance.selectedYear,
      selectedMonth = instance.selectedMonth,
      selectedDate = new Date(selectedYear, selectedMonth),
      dateFormat = 
        instance.settings.originalDateFormat ||
        instance.settings.dateFormat ||
        $.datepicker.regional[''].dateFormat;

    $(this).val($.datepicker.formatDate(dateFormat, selectedDate));
  },

  /**
   * If we want to use normal datepickers on the same page
   * we have to add and remove the modified styles accordingly
  **/
  styleMonthAndYear: function (input, instance) {
    var
      dpDiv = instance.dpDiv,
      className = 'monthAndYear';
    if (instance.settings.monthAndYear) {
      dpDiv.addClass(className);
    }
    else {
      dpDiv.removeClass(className);
    }
  }
}

main.js

$.datepicker.setDefaults({
  beforeShow: monthAndYear.styleMonthAndYear,
  onClose: monthAndYear.getMonthAndYear
});

$(function () {
  $('#vanillaDatePicker').datepicker();

  $('#modifiedDatepickerOne').datepicker({
    monthAndYear: true
  });

  $('#modifiedDatepickerTwo').datepicker({
    monthAndYear: true,
    changeYear: true
  });

  /**
   * We have to do a bit of trickery here, in order to use a
   * dateFormat ('yy-mm') that datepicker normally wouldn't accept.
   * We parse the date manually and clear the dateFormat setting
   * in order to force datepicker to use the defaultDate setting.
   * We also save the original dateFormat so that we can
   * use it later in getMonthAndYear.
  **/
  $('#modifiedDatepickerThree').datepicker({
    monthAndYear: true,
    changeYear: true,
    dateFormat: 'yy-mm',
    beforeShow: function (input, instance) {
      monthAndYear.styleMonthAndYear.call(this, input, instance);

      var 
        date = $.datepicker.parseDate('yy-mm-dd', input.value + '-01'),
        originalDateFormat =
          instance.settings.dateFormat ||
          instance.settings.originalDateFormat;

      return {
        originalDateFormat: originalDateFormat,
        dateFormat: '',
        defaultDate: date
      };
    }
  });
});

main.html

<!doctype html>
<html lang="en">
  <head>
    <title>jQuery UI datepicker Month and Year Modification</title>
    <meta http-equiv="Content-type" content="text/html; charset=utf-8" />

    <script src="http://ajax.googleapis.com/ajax/libs/jquery/1.3.2/jquery.min.js" type="text/javascript"></script>
    <link rel="stylesheet" href="http://ajax.googleapis.com/ajax/libs/jqueryui/1.7.2/themes/base/jquery-ui.css" type="text/css" />
    <script src="http://ajax.googleapis.com/ajax/libs/jqueryui/1.7.2/jquery-ui.min.js" type="text/javascript"></script>

    <link rel="stylesheet" href="monthAndYear.css" type="text/css" />
    <script src="monthAndYear.js" type="text/javascript"></script>

    <script src="main.js" type="text/javascript"></script>
  </head>
  <body>
    <h1>jQuery UI datepicker Month and Year Modification</h1>

    <h2>Vanilla datepicker</h2>
    <input type="text" id="vanillaDatePicker" value="03/20/2009" />

    <h2>Modified datepicker</h2>
    <input type="text" id="modifiedDatepickerOne" value="03/20/2009" />

    <h2>Modified datepicker with a dropdown to change the year</h2>
    <input type="text" id="modifiedDatepickerTwo" value="03/20/2009" />

    <h2>Modified datepicker with custom date format</h2>
    <input type="text" id="modifiedDatepickerThree" value="2009-03" />
  </body>
</html>
brianpeiris
this is perfect.
Roeland
+1 brianpeiris - those are really nicely done!
micahwittman
Thanks guys, glad I could help.
brianpeiris