I assume you are using Symfony 2.0. I read that the form component has changed a bit in 2.1.
I had a similar problem - I wanted to have a datetime field that uses separate widgets to enter the date and time (hour).
First of all, you need to create a separate type of form for this field (which is actually a form in itself).
My code is similar to this (modified for this example):
class MyDateTimeType extends AbstractType { public function buildForm(FormBuilder $builder, array $options) { $builder ->add('date', 'date', array( 'label' => 'label.form.date', 'input' => 'datetime', 'widget' => 'single_text', 'format' => 'yyyy-MM-dd', 'error_bubbling' => true )) ->add('time', 'time', array( 'label' => 'label.form.time', 'input' => 'datetime', 'widget' => 'choice', 'error_bubbling' => true )); $builder->appendClientTransformer(new DateTimeToDateTimeArrayTransformer()); } public function getDefaultOptions(array $options) { return array( 'label' => 'label.form.date', 'error_bubbling' => false ); } public function getParent(array $options) { return 'form'; } public function getName() { return 'my_datetime'; } }
As you can see, this is a form (do not confuse it), but we will use it as one logical field. The one that includes the data converter. It must split one instance of DateTime by date and time to obtain data for two subfields when the form is displayed and vice versa when the form is submitted.
The error_bubbling parameters ensure that errors generated by subfields join our new subfield and do not propagate to the top-level form, but you may have a great goal.
My data converter looks like this:
class DateTimeToDateTimeArrayTransformer implements DataTransformerInterface { public function transform($datetime) { if(null !== $datetime) { $date = clone $datetime; $date->setTime(12, 0, 0); $time = clone $datetime; $time->setDate(1970, 1, 1); } else { $date = null; $time = null; } $result = array( 'date' => $date, 'time' => $time ); return $result; } public function reverseTransform($array) { $date = $array['date']; $time = $array['time']; if(null == $date || null == $time) return null; $date->setTime($time->format('G'), $time->format('i')); return $date; } }
Finally, you can use it like this:
$builder->add('startDate', 'my_datetime', array( 'label' => 'label.form.date' ));
You must register it as a service in order to use it by an alias, otherwise execute it directly ( new MyDateTimeType() ).
This may not be the nicest solution, but it is also a form component in Symfony 2.0.