class ActionView::Helpers::DateTimeSelector
:nodoc:
def build_day_options(selected)
=> "
build_day_options(2)
If use_two_digit_numbers: true option is passed to DateTimeSelector
..."
=> "
build_day_options(2)
If day_format: ->(day) { day.ordinalize } option is passed to DateTimeSelector
..."
=> "
build_day_options(2)
Build select option HTML for day.
def build_day_options(selected) select_options = [] (1..31).each do |value| tag_options = { value: value } tag_options[:selected] = "selected" if selected == value text = day_name(value) select_options << content_tag("option", text, tag_options) end (select_options.join("\n") + "\n").html_safe end
def build_hidden(type, value)
build_hidden(:year, 2008)
Builds hidden input tag for date part and value.
def build_hidden(type, value) select_options = { type: "hidden", id: input_id_from_type(type), name: input_name_from_type(type), value: value, autocomplete: "off" }.merge!(@html_options.slice(:disabled)) select_options[:disabled] = "disabled" if @options[:disabled] tag(:input, select_options) + "\n".html_safe end
def build_options(selected, options = {})
=> "
build_options(15, start: 1, end: 31, step: 2)
If :step options is passed:
..."
=> "
build_options(15, start: 1, end: 31, use_two_digit_numbers: true)
If use_two_digit_numbers: true option is passed:
..."
=> "
build_options(15, start: 1, end: 31)
Build select option HTML from date value and options.
def build_options(selected, options = {}) options = { leading_zeros: true, ampm: false, use_two_digit_numbers: false }.merge!(options) start = options.delete(:start) || 0 stop = options.delete(:end) || 59 step = options.delete(:step) || 1 leading_zeros = options.delete(:leading_zeros) select_options = [] start.step(stop, step) do |i| value = leading_zeros ? sprintf("%02d", i) : i tag_options = { value: value } tag_options[:selected] = "selected" if selected == i text = options[:use_two_digit_numbers] ? sprintf("%02d", i) : value text = options[:ampm] ? AMPM_TRANSLATION[i] : text select_options << content_tag("option", text, tag_options) end (select_options.join("\n") + "\n").html_safe end
def build_options_and_select(type, selected, options = {})
def build_options_and_select(type, selected, options = {}) build_select(type, build_options(selected, options)) end
def build_select(type, select_options_as_html)
...
=> "
def build_select(type, select_options_as_html) select_options = { id: input_id_from_type(type), name: input_name_from_type(type) }.merge!(@html_options) select_options[:disabled] = "disabled" if @options[:disabled] select_options[:class] = css_class_attribute(type, select_options[:class], @options[:with_css_classes]) if @options[:with_css_classes] select_html = +"\n" select_html << content_tag("option", "", value: "", label: " ") + "\n" if @options[:include_blank] select_html << prompt_option_tag(type, @options[:prompt]) + "\n" if @options[:prompt] select_html << select_options_as_html (content_tag("select", select_html.html_safe, select_options) + "\n").html_safe end
def build_selects_from_types(order)
Given an ordering of datetime components, create the selection HTML
def build_selects_from_types(order) select = +"" first_visible = order.find { |type| !@options[:"discard_#{type}"] } order.reverse_each do |type| separator = separator(type) unless type == first_visible # don't add before first visible field select.insert(0, separator.to_s + public_send("select_#{type}").to_s) end select.html_safe end
def build_year_options(selected, options = {})
=> "
build_year_options(1998, start: 1998, end: 2000, year_format: ->year { "Heisei #{ year - 1988 }" })
If year_format option is passed
"
=> "
build_year_options(1998, start: 1998, end: 2000)
If year_format option is not passed
Build select option HTML for year.
def build_year_options(selected, options = {}) start = options.delete(:start) stop = options.delete(:end) step = options.delete(:step) select_options = [] start.step(stop, step) do |value| tag_options = { value: value } tag_options[:selected] = "selected" if selected == value text = year_name(value) select_options << content_tag("option", text, tag_options) end (select_options.join("\n") + "\n").html_safe end
def css_class_attribute(type, html_options_class, options) # :nodoc:
=> "date optional my-year"
css_class_attribute(:year, 'date optional', { year: 'my-year' })
Builds the CSS class value for the select element.
def css_class_attribute(type, html_options_class, options) # :nodoc: css_class = \ case options when Hash options[type.to_sym] else type end [html_options_class, css_class].compact.join(" ") end
def date_order
def date_order @date_order ||= @options[:order] || translated_date_order end
def day_name(number)
If the day_format: ->(day) { day.ordinalize } option is passed to DateTimeSelector:
day_name(1) # => "01"
If the use_two_digit_numbers: true option is passed to DateTimeSelector:
day_name(1) # => 1
Looks up day names by number.
def day_name(number) if day_format_lambda = @options[:day_format] day_format_lambda.call(number) elsif @options[:use_two_digit_numbers] "%02d" % number else number end end
def initialize(datetime, options = {}, html_options = {})
def initialize(datetime, options = {}, html_options = {}) @options = options.dup @html_options = html_options.dup @datetime = datetime @options[:datetime_separator] ||= " — " @options[:time_separator] ||= " : " end
def input_id_from_type(type)
Returns the id attribute for the input tag.
def input_id_from_type(type) id = input_name_from_type(type).gsub(/([\[(])|(\]\[)/, "_").gsub(/[\])]/, "") id = @options[:namespace] + "_" + id if @options[:namespace] id end
def input_name_from_type(type)
Returns the name attribute for the input tag.
def input_name_from_type(type) prefix = @options[:prefix] || ActionView::Helpers::DateTimeSelector::DEFAULT_PREFIX prefix += "[#{@options[:index]}]" if @options.has_key?(:index) field_name = @options[:field_name] || type.to_s if @options[:include_position] field_name += "(#{ActionView::Helpers::DateTimeSelector::POSITION[type]}i)" end @options[:discard_type] ? prefix : "#{prefix}[#{field_name}]" end
def month_name(number)
month_name(1) # => "January (01)"
If the :month_format_string option is passed:
month_name(1) # => "1 - January"
If the :add_month_numbers option is passed:
month_name(1) # => '01'
If the :use_two_month_numbers option is passed:
month_name(1) # => 1
If the :use_month_numbers option is passed:
month_name(1) # => "January"
Looks up month names by number (1-based):
def month_name(number) if @options[:use_month_numbers] number elsif @options[:use_two_digit_numbers] "%02d" % number elsif @options[:add_month_numbers] "#{number} - #{month_names[number]}" elsif format_string = @options[:month_format_string] format_string % { number: number, name: month_names[number] } else month_names[number] end end
def month_names
Returns translated month names, but also ensures that a custom month
def month_names @month_names ||= begin month_names = @options[:use_month_names] || translated_month_names month_names = [nil, *month_names] if month_names.size < 13 month_names end end
def prompt_option_tag(type, options)
prompt_option_tag(:month, prompt: 'Select month')
Builds a prompt option tag with supplied options or from default options.
def prompt_option_tag(type, options) prompt = \ case options when Hash default_options = { year: false, month: false, day: false, hour: false, minute: false, second: false } default_options.merge!(options)[type.to_sym] when String options else I18n.translate(:"datetime.prompts.#{type}", locale: @options[:locale]) end prompt ? content_tag("option", prompt_text(prompt, type), value: "") : "" end
def prompt_text(prompt, type)
def prompt_text(prompt, type) prompt.kind_of?(String) ? prompt : I18n.translate(:"datetime.prompts.#{type}", locale: @options[:locale]) end
def select_date
def select_date order = date_order.dup @options[:discard_hour] = true @options[:discard_minute] = true @options[:discard_second] = true @options[:discard_year] ||= true unless order.include?(:year) @options[:discard_month] ||= true unless order.include?(:month) @options[:discard_day] ||= true if @options[:discard_month] || !order.include?(:day) set_day_if_discarded [:day, :month, :year].each { |o| order.unshift(o) unless order.include?(o) } build_selects_from_types(order) end
def select_datetime
def select_datetime order = date_order.dup order -= [:hour, :minute, :second] @options[:discard_year] ||= true unless order.include?(:year) @options[:discard_month] ||= true unless order.include?(:month) @options[:discard_day] ||= true if @options[:discard_month] || !order.include?(:day) @options[:discard_minute] ||= true if @options[:discard_hour] @options[:discard_second] ||= true unless @options[:include_seconds] && !@options[:discard_minute] set_day_if_discarded if @options[:tag] && @options[:ignore_date] select_time else [:day, :month, :year].each { |o| order.unshift(o) unless order.include?(o) } order += [:hour, :minute, :second] unless @options[:discard_hour] build_selects_from_types(order) end end
def select_day
def select_day if @options[:use_hidden] || @options[:discard_day] build_hidden(:day, day || 1) else build_select(:day, build_day_options(day)) end end
def select_hour
def select_hour if @options[:use_hidden] || @options[:discard_hour] build_hidden(:hour, hour) else options = {} options[:ampm] = @options[:ampm] || false options[:start] = @options[:start_hour] || 0 options[:end] = @options[:end_hour] || 23 build_options_and_select(:hour, hour, options) end end
def select_minute
def select_minute if @options[:use_hidden] || @options[:discard_minute] build_hidden(:minute, min) else build_options_and_select(:minute, min, step: @options[:minute_step]) end end
def select_month
def select_month if @options[:use_hidden] || @options[:discard_month] build_hidden(:month, month || 1) else month_options = [] 1.upto(12) do |month_number| options = { value: month_number } options[:selected] = "selected" if month == month_number month_options << content_tag("option", month_name(month_number), options) + "\n" end build_select(:month, month_options.join) end end
def select_second
def select_second if @options[:use_hidden] || @options[:discard_second] build_hidden(:second, sec) if @options[:include_seconds] else build_options_and_select(:second, sec) end end
def select_time
def select_time order = [] @options[:discard_month] = true @options[:discard_year] = true @options[:discard_day] = true @options[:discard_second] ||= true unless @options[:include_seconds] order += [:year, :month, :day] unless @options[:ignore_date] order += [:hour, :minute] order << :second if @options[:include_seconds] build_selects_from_types(order) end
def select_year
def select_year if !year || @datetime == 0 val = "1" middle_year = Date.today.year else val = middle_year = year end if @options[:use_hidden] || @options[:discard_year] build_hidden(:year, val) else options = {} options[:start] = @options[:start_year] || middle_year - 5 options[:end] = @options[:end_year] || middle_year + 5 options[:step] = options[:start] < options[:end] ? 1 : -1 options[:leading_zeros] = false options[:max_years_allowed] = @options[:max_years_allowed] || 1000 if (options[:end] - options[:start]).abs > options[:max_years_allowed] raise ArgumentError, "There are too many years options to be built. Are you sure you haven't mistyped something? You can provide the :max_years_allowed parameter." end build_select(:year, build_year_options(val, options)) end end
def separator(type)
def separator(type) return "" if @options[:use_hidden] case type when :year, :month, :day @options[:"discard_#{type}"] ? "" : @options[:date_separator] when :hour (@options[:discard_year] && @options[:discard_day]) ? "" : @options[:datetime_separator] when :minute, :second @options[:"discard_#{type}"] ? "" : @options[:time_separator] end end
def set_day_if_discarded
If the day is hidden, the day should be set to the 1st so all month and year choices are
def set_day_if_discarded if @datetime && @options[:discard_day] @datetime = @datetime.change(day: 1) end end
def translated_date_order
def translated_date_order date_order = I18n.translate(:'date.order', locale: @options[:locale], default: []) date_order = date_order.map(&:to_sym) forbidden_elements = date_order - [:year, :month, :day] if forbidden_elements.any? raise StandardError, "#{@options[:locale]}.date.order only accepts :year, :month and :day" end date_order end
def translated_month_names
=> [nil, "Jan", "Feb", "Mar", "Apr", "May", "Jun",
If :use_short_month option is set
"November", "December"]
"August", "September", "October",
"April", "May", "June", "July",
=> [nil, "January", "February", "March",
Returns translated month names.
def translated_month_names key = @options[:use_short_month] ? :'date.abbr_month_names' : :'date.month_names' I18n.translate(key, locale: @options[:locale]) end
def year_name(number)
If the :year_format option is passed:
year_name(1998) # => 1998
Looks up year names by number.
def year_name(number) if year_format_lambda = @options[:year_format] year_format_lambda.call(number) else number end end