it-swarm.com.de

Separate Felder für Datum und Uhrzeit in Rails

Ich habe ein ActiveRecord-Modell Eventmit einer Datetime-Spalte starts_at. Ich möchte ein Formular vorlegen, in dem Datum und Uhrzeit für starts_at separat ausgewählt werden (z. B. "23-10-2010" für Datum und "18:00" für Uhrzeit). Diese Felder sollten durch die einzige Spalte starts_at unterstützt werden, und Validierungen sollten vorzugsweise auch gegen starts_at sein.

Ich kann natürlich mit virtuellen Attributen und Haken herumspielen, aber ich hätte gerne eine elegantere Lösung. Ich habe sowohl mit composed_of ( rdoc ) als auch mit Attributdekorator ( lighthouse discussion , github ) ohne Erfolg experimentiert.

Nachfolgend finden Sie einen groben Überblick über das, was ich möchte.

class Event < ActiveRecord::Base
  validates_presence_of :start_date
end

# View
# On submission this should set start_date.
form_for @event do |f|
  f.text_field :starts_at_date         # date-part of start_date
  f.text_field :starts_at_time_of_day  # time-of-day-part of start_date
  f.submit
end

Jede Hilfe geschätzt.

40
pgericson

Habe heute nach einem Rails-Projekt gesucht und bin auf dieses Juwel gestoßen:

https://github.com/shekibobo/time_splitter

Das Einstellen von DateTimes kann eine schwierige oder hässliche Angelegenheit sein, insbesondere über ein Webformular. Das Finden eines guten DatePicker oder TimePicker ist einfach, aber es kann schwierig sein, sie an beiden zu arbeiten. TimeSplitter generiert automatisch Zugriffsmethoden für Datum, Uhrzeit, Stunde und Minute für Ihre Datums- oder Uhrzeitattribute. Daher ist es einfach, verschiedene Formulareingaben zu verwenden, um verschiedene Teile eines Datumzeitfelds festzulegen.

Sieht aus, als würde es die Arbeit für Sie erledigen

9
asgeo1

Müssen Sie einen text_field in der Ansicht haben?

Soweit ich das beurteilen kann, können Sie ein date_time-Feld haben und dann einfach zwei verschiedene Eingabefelder verwenden, um die verschiedenen Teile des Felds festzulegen.

form_for @event do |f|
  f.date_select :starts_at
  f.time_select :starts_at, :ignore_date => true
  f.submit
end

Da die Helfer für Datums- und Uhrzeitauswahl des Rails fünf verschiedene Parameter festlegen (starts_at(1i) für den Jahresabschnitt, 2i für den Monatsabschnitt usw.), bedeutet dies, dass der date_select sie nur für den Datumsteil festlegt, während Sie :ignore_date => true an den. Übergeben time_select, es werden nur die Stunden und Minuten eingestellt.

Wenn Sie über einen text_field verfügen müssen, weiß ich nicht genau, wie Sie das tun sollen. Möglicherweise können Sie jedoch mit jQuery magic etwas tun, bevor Sie die datetime-Parameter einstellen, bevor Sie das Formular senden.

39
Frost

Die Verwendung von date_select und time_select ist ein guter Weg.

Ich wollte jedoch einen text_field für das Datum (damit ich eine JavaScript-Datumsauswahl verwenden kann).

Verwenden von strong_parameters oder Rails 4+:

models/event.rb

# Add a virtual attribute
attr_accessor :start_at_date

views/events/_form.html.haml

- # A text field for the date, and time_select for time
= f.label :start_at
= f.text_field :start_at_date, value: (f.object.start_at.present? ? f.object.start_at.to_date : nil)
= f.time_select :start_at, :ignore_date => true

Steuerungen/events_controller.rb

# If using a date_select, time_select, datetime_select
# Rails expects multiparameter attributes
# Convert the date to the muiltiparameter parts
def event_params
  if !!params[:event] && (params[:event]["start_at(4i)"].present? || params[:event]["start_at(5i)"].present?)

    if params[:event][:start_at_date].present?
      start_at_date = params[:event][:start_at_date]
    else
      start_at_date = Date.today
    end
    year  = start_at_date.match(/^(\d{4})[\-\/]/)[1]
    month = start_at_date.match(/[\-\/](\d{2})[\-\/]/)[1]
    day   = start_at_date.match(/[\-\/](\d{2})$/)[1]
    params[:event]["start_at(1i)"] = year
    params[:event]["start_at(2i)"] = month
    params[:event]["start_at(3i)"] = day
  end
  ...
3
d_rail

Eine elegante Lösung kann Folgendes bereitstellen: date_time_attribute gem :

class MyModel < ActiveRecord::Base
  include DateTimeAttribute

  date_time_attribute :starts_at
end

Sie können starts_at_date und starts_at_time separat einstellen:

form_for @event do |f|
  f.text_field :starts_at_date
  f.text_field :starts_at_time
  f.submit
end

# this will work too:
form_for @event do |f|
  f.date_select :starts_at_date
  f.time_select :starts_at_time, :ignore_date => true
  f.text_field  :starts_at_time_zone
  f.submit
end

# or
form_for @event do |f|
  f.date_select :starts_at_date
  f.text_field  :starts_at_time
  f.submit
end

Es erlaubt Ihnen auch, mit Zeitzonen zu spielen, Chronic usw. zu verwenden.

2
Sergei Zinin

Liegt das an einem Designproblem? Es ist wirklich viel einfacher, wenn Sie starts_at nur als Datetime-Datentyp speichern und Folgendes verwenden:

http://puna.net.nz/timepicker.htm#

Es läuft einfach über den Datumsfeldern, die Sie für Ihr Modell haben.

0
Chris Barretto