Calendar Date Select Magic For Rails
Calendar Date Select is a new(ish) “date and time picker”, developed by Tim Harper, designed primarily for developers to use in Rails applications. It uses the standard Prototype JavaScript library, and is easily installed as a Rails plugin:
script/plugin install http://calendardateselect.googlecode.com/svn/tags/calendar_date_select
The demo seems to be down, but here is some more detailed info: http://ianli.com/site/HowTo/UseCalendarDateSelectRailsPlugin. You can also see the original contents of the demo site about halfway down the Google Code wiki for the project: http://code.google.com/p/calendardateselect/wiki/CalendarDateSelect
On the surface this is a very easy plugin to install and use. It seems the common problem is that there is very little documentation available and the demo server is down. After installing the gem, I was able to run “gem server” and view the rdoc for the plugin. A couple of things I thought would be helpful to repost here:
Form Helpers:
calendar_date_select(object, method, options={})
Similar to the difference between text_field_tag and text_field, this method behaves like text_field
It receives the same options as calendar_date_select_tag. Need for time selection is automatically detected by checking the corresponding column meta information of Model#columns_hash
calendar_date_select_tag( name, value = nil, options = {})
Similar to text_field_tag, but adds a calendar picker, naturally.
Arguments
+name+ - the html name of the tag
+value+ - When specified as a string, uses value verbatim. When Date, DateTime, Time, it converts it to a string basd off the format set by CalendarDateSelect#format=
+options+ - ...
Options
:embedded
Put the calendar straight into the form, rather than using a popup type of form.
<%= calendar_date_select_tag "name", "2007-01-01", :embedded => true %>
:hidden
Use a hidden element instead of a text box for a pop up calendar. Not compatible with :embedded => true. You‘ll probably want to use an onchange callback to do something with the value.
<%= calendar_date_select_tag "hidden_date_selector", "", :hidden => "true", :onchange => "$('cds_value').update($F(this));" %>
:image
Specify an alternative icon to use for the date picker.
To use /images/groovy.png:
<%= calendar_date_select_tag "altered_image", "", :image => "groovy.png" %>
:minute_interval
Specifies the minute interval used in the hour/minute selector. Default is 5.
<%= calendar_date_select_tag "month_year_selector_label", "", :minute_interval => 15 %>
:month_year
Customize the month and year selectors at the top of the control.
Valid values:
* "dropdowns" (default) - Use a separate dropdown control for both the month and year
* "label" - Use static text to show the month and the year.
<%= calendar_date_select_tag "month_year_selector_label", "", :month_year => "label" %>
:popup => ‘force‘
Forces the user to use the popup calendar by making it‘s text-box read-only and causing calendar_date_select to override it‘s default behavior of not allowing selection of a date on a target element that is read-only.
<%= calendar_date_select_tag "name", "2007-01-01", :popup => "force" %>
:time
Show time in the controls. There‘s three options:
* +true+ - show an hour/minute selector.
* +false+ - don't show an hour/minute selector.
* +"mixed"+ - Show an hour/minute selector, but include a "all day" option - allowing them to choose whether or not to specify a time.
:year_range
Limit the year range. You can pass in an array or range of ruby Date/Time objects or FixNum‘s.
<%= calendar_date_select_tag "e_date", nil, :year_range => 10.years.ago..0.years.from_now %>
<%= calendar_date_select_tag "e_date", nil, :year_range => [0.years.ago, 10.years.from_now] %>
<%= calendar_date_select_tag "e_date", nil, :year_range => 2000..2007 %>
<%= calendar_date_select_tag "e_date", nil, :year_range => [2000, 2007] %>
CALLBACKS
The following callbacks are available:
* before_show / after_show
* before_close / after_close
* after_navigate - Called when navigating to a different month. Passes first parameter as a date object refering to the current month viewed
* onchange - Called when the form input value changes
<%= calendar_date_select_tag "event_demo", "",
:before_show => "log('Calendar Showing');" ,
:after_show => "log('Calendar Shown');" ,
:before_close => "log('Calendar closing');" ,
:after_close => "log('Calendar closed');",
:after_navigate => "log('Current month is ' + (param.getMonth()+1) + '/' + (param.getFullYear()));",
:onchange => "log('value changed to - ' + $F(this));"
}}}
All callbacks are executed within the context of the target input element. If you‘d like to access the CalendarDateSelect object itself, you can access it via "this.calendar_date_select".
For example:
<%= calendar_date_select_tag "event_demo", "", :after_navigate => "alert('The current selected month is ' + this.calendar_date_select.selected_date.getMonth());" ,
For use with Form Builders
calendar_date_select(method, options = {})
Controllers:
In my application, I am using a custom form builder, so I used the calendar_date_elect with the form builder. The options hash appears to be the same as in the other view tags, so I just passed along what I needed:
<%= f.calendar_date_select "date", :embedded => true, :year_range => 1.year.ago..5.years.from_now, :time => false %>
I was pleased to discover that, utilizing some of the magic of Rails, the date property on my event was automatically turned into a datetime attribute, and on editing, was reloaded into the calendar as expected.