atd-calendar_date_select 1.11.20090109 → 1.11.20090110

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,223 @@
1
+ # Various helpers available for use in your view
2
+ module CalendarDateSelect::FormHelpers
3
+
4
+ # Similar to text_field_tag, but adds a calendar picker, naturally.
5
+ #
6
+ # == Arguments
7
+ #
8
+ # +name+ - the html name of the tag
9
+ # +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=
10
+ # +options+ - ...
11
+ #
12
+ # == Options
13
+ #
14
+ # === :embedded
15
+ #
16
+ # Put the calendar straight into the form, rather than using a popup type of form.
17
+ #
18
+ # <%= calendar_date_select_tag "name", "2007-01-01", :embedded => true %>
19
+ #
20
+ # === :hidden
21
+ #
22
+ # 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.
23
+ #
24
+ # <span id='cds_value' />
25
+ # <%= calendar_date_select_tag "hidden_date_selector", "", :hidden => "true", :onchange => "$('cds_value').update($F(this));" %>
26
+ #
27
+ # === :image
28
+ #
29
+ # Specify an alternative icon to use for the date picker.
30
+ #
31
+ # To use /images/groovy.png:
32
+ #
33
+ # <%= calendar_date_select_tag "altered_image", "", :image => "groovy.png" %>
34
+ #
35
+ # === :minute_interval
36
+ #
37
+ # Specifies the minute interval used in the hour/minute selector. Default is 5.
38
+ #
39
+ # <%= calendar_date_select_tag "month_year_selector_label", "", :minute_interval => 15 %>
40
+ #
41
+ # === :month_year
42
+ #
43
+ # Customize the month and year selectors at the top of the control.
44
+ #
45
+ # Valid values:
46
+ # * "dropdowns" (default) - Use a separate dropdown control for both the month and year
47
+ # * "label" - Use static text to show the month and the year.
48
+ #
49
+ # <%= calendar_date_select_tag "month_year_selector_label", "", :month_year => "label" %>
50
+ #
51
+ # === :popup => 'force'
52
+ #
53
+ # 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.
54
+ #
55
+ # <%= calendar_date_select_tag "name", "2007-01-01", :popup => "force" %>
56
+ #
57
+ # === :time
58
+ #
59
+ # Show time in the controls. There's three options:
60
+ #
61
+ # * +true+ - show an hour/minute selector.
62
+ # * +false+ - don't show an hour/minute selector.
63
+ # * +"mixed"+ - Show an hour/minute selector, but include a "all day" option - allowing them to choose whether or not to specify a time.
64
+ #
65
+ # === :year_range
66
+ #
67
+ # Limit the year range. You can pass in an array or range of ruby Date/Time objects or FixNum's.
68
+ #
69
+ # <%= calendar_date_select_tag "e_date", nil, :year_range => 10.years.ago..0.years.from_now %>
70
+ # <%= calendar_date_select_tag "e_date", nil, :year_range => [0.years.ago, 10.years.from_now] %>
71
+ # <%= calendar_date_select_tag "e_date", nil, :year_range => 2000..2007 %>
72
+ # <%= calendar_date_select_tag "e_date", nil, :year_range => [2000, 2007] %>
73
+ #
74
+ # == CALLBACKS
75
+ #
76
+ # The following callbacks are available:
77
+ #
78
+ # * before_show / after_show
79
+ # * before_close / after_close
80
+ # * after_navigate - Called when navigating to a different month. Passes first parameter as a date object refering to the current month viewed
81
+ # * onchange - Called when the form input value changes
82
+ #
83
+ # <%= calendar_date_select_tag "event_demo", "",
84
+ # :before_show => "log('Calendar Showing');" ,
85
+ # :after_show => "log('Calendar Shown');" ,
86
+ # :before_close => "log('Calendar closing');" ,
87
+ # :after_close => "log('Calendar closed');",
88
+ # :after_navigate => "log('Current month is ' + (param.getMonth()+1) + '/' + (param.getFullYear()));",
89
+ # :onchange => "log('value changed to - ' + $F(this));"
90
+ #
91
+ # }}}
92
+ #
93
+ # 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".
94
+ #
95
+ # For example:
96
+ #
97
+ # <%= calendar_date_select_tag "event_demo", "", :after_navigate => "alert('The current selected month is ' + this.calendar_date_select.selected_date.getMonth());" ,
98
+ def calendar_date_select_tag( name, value = nil, options = {})
99
+ options, javascript_options = calendar_date_select_process_options(options)
100
+ value = CalendarDateSelect.format_time(value, javascript_options)
101
+
102
+ javascript_options.delete(:format)
103
+
104
+ options[:id] ||= name
105
+ tag = javascript_options[:hidden] || javascript_options[:embedded] ?
106
+ hidden_field_tag(name, value, options) :
107
+ text_field_tag(name, value, options)
108
+
109
+ calendar_date_select_output(tag, options, javascript_options)
110
+ end
111
+
112
+ # Similar to the difference between +text_field_tag+ and +text_field+, this method behaves like +text_field+
113
+ #
114
+ # 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
115
+ def calendar_date_select(object, method, options={})
116
+ obj = options[:object] || instance_variable_get("@#{object}")
117
+
118
+ if !options.include?(:time) && obj.class.respond_to?("columns_hash")
119
+ column_type = (obj.class.columns_hash[method.to_s].type rescue nil)
120
+ options[:time] = true if column_type == :datetime
121
+ end
122
+
123
+ use_time = options[:time]
124
+
125
+ if options[:time].to_s=="mixed"
126
+ use_time = false if Date===(obj.respond_to?(method) && obj.send(method))
127
+ end
128
+
129
+ options, javascript_options = calendar_date_select_process_options(options)
130
+
131
+ options[:value] ||=
132
+ if(obj.respond_to?(method) && obj.send(method).respond_to?(:strftime))
133
+ obj.send(method).strftime(CalendarDateSelect.date_format_string(use_time))
134
+ elsif obj.respond_to?("#{method}_before_type_cast")
135
+ obj.send("#{method}_before_type_cast")
136
+ elsif obj.respond_to?(method)
137
+ obj.send(method).to_s
138
+ else
139
+ nil
140
+ end
141
+
142
+ tag = ActionView::Helpers::InstanceTag.new_with_backwards_compatibility(object, method, self, options.delete(:object))
143
+ calendar_date_select_output(
144
+ tag.to_input_field_tag( (javascript_options[:hidden] || javascript_options[:embedded]) ? "hidden" : "text", options),
145
+ options,
146
+ javascript_options
147
+ )
148
+ end
149
+
150
+ private
151
+ # extracts any options passed into calendar date select, appropriating them to either the Javascript call or the html tag.
152
+ def calendar_date_select_process_options(options)
153
+ options, javascript_options = CalendarDateSelect.default_options.merge(options), {}
154
+ callbacks = [:before_show, :before_close, :after_show, :after_close, :after_navigate]
155
+ for key in [:time, :valid_date_check, :embedded, :buttons, :clear_button, :format, :year_range, :month_year, :popup, :hidden, :minute_interval] + callbacks
156
+ javascript_options[key] = options.delete(key) if options.has_key?(key)
157
+ end
158
+
159
+ # if passing in mixed, pad it with single quotes
160
+ javascript_options[:time] = "'mixed'" if javascript_options[:time].to_s=="mixed"
161
+ javascript_options[:month_year] = "'#{javascript_options[:month_year]}'" if javascript_options[:month_year]
162
+
163
+ # if we are forcing the popup, automatically set the readonly property on the input control.
164
+ if javascript_options[:popup].to_s == "force"
165
+ javascript_options[:popup] = "'force'"
166
+ options[:readonly] = true
167
+ end
168
+
169
+ if (vdc=javascript_options.delete(:valid_date_check))
170
+ if vdc.include?(";") || vdc.include?("function")
171
+ raise ArgumentError, ":valid_date_check function is missing a 'return' statement. Try something like: :valid_date_check => 'if (date > new(Date)) return true; else return false;'" unless vdc.include?("return");
172
+ end
173
+
174
+ vdc = "return(#{vdc})" unless vdc.include?("return")
175
+ vdc = "function(date) { #{vdc} }" unless vdc.include?("function")
176
+ javascript_options[:valid_date_check] = vdc
177
+ end
178
+
179
+ javascript_options[:popup_by] ||= "this" if javascript_options[:hidden]
180
+
181
+ # surround any callbacks with a function, if not already done so
182
+ for key in callbacks
183
+ javascript_options[key] = "function(param) { #{javascript_options[key]} }" unless javascript_options[key].include?("function") if javascript_options[key]
184
+ end
185
+
186
+ javascript_options[:year_range] = format_year_range(javascript_options[:year_range] || 10)
187
+ [options, javascript_options]
188
+ end
189
+
190
+ def calendar_date_select_output(input, options = {}, javascript_options = {})
191
+ out = input
192
+ if javascript_options[:embedded]
193
+ uniq_id = "cds_placeholder_#{(rand*100000).to_i}"
194
+ # we need to be able to locate the target input element, so lets stick an invisible span tag here we can easily locate
195
+ out << content_tag(:span, nil, :style => "display: none; position: absolute;", :id => uniq_id)
196
+ out << javascript_tag("new CalendarDateSelect( $('#{uniq_id}').previous(), #{options_for_javascript(javascript_options)} ); ")
197
+ else
198
+ out << " "
199
+ out << image_tag(options[:image],
200
+ :onclick => "new CalendarDateSelect( $(this).previous(), #{options_for_javascript(javascript_options)} );",
201
+ :style => 'border:0px; cursor:pointer;',
202
+ :class=>'calendar_date_select_popup_icon')
203
+ end
204
+ out
205
+ end
206
+
207
+ def format_year_range(year) # nodoc
208
+ return year unless year.respond_to?(:first)
209
+ return "[#{year.first}, #{year.last}]" unless year.first.respond_to?(:strftime)
210
+ return "[#{year.first.year}, #{year.last.year}]"
211
+ end
212
+ end
213
+
214
+ # Helper method for form builders
215
+ module ActionView
216
+ module Helpers
217
+ class FormBuilder
218
+ def calendar_date_select(method, options = {})
219
+ @template.calendar_date_select(@object_name, method, options.merge(:object => @object))
220
+ end
221
+ end
222
+ end
223
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: atd-calendar_date_select
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.11.20090109
4
+ version: 1.11.20090110
5
5
  platform: ruby
6
6
  authors:
7
7
  - Tim Harper
@@ -41,6 +41,7 @@ files:
41
41
  - js_test/unit/cds_helper_methods.html
42
42
  - js_test/unittest.js
43
43
  - lib/calendar_date_select/calendar_date_select.rb
44
+ - lib/calendar_date_select/form_helpers.rb
44
45
  - lib/calendar_date_select/includes_helper.rb
45
46
  - lib/calendar_date_select.rb
46
47
  - Manifest.txt