¿Cómo establecer un campo de tipo de tiempo mediante programación?

8

Creo un tipo de entidad de contenido personalizado.

Quiero un campo para la hora del evento.

Como no hay un campo de tiempo, sino un tipo de tiempo de datos, creo un complemento para un campo personalizado:

FieldType: TimeItem.php

/**
 * Plugin implementation of the 'time' field type.
 *
 * @FieldType(
 *   id = "time",
 *   label = @Translation("Time Field"),
 *   description = @Translation("Permet la creation d'un champ de type time"),
 *   default_widget = "time_widget",
 *   default_formatter = "time_formatter"
 * )
 */

  /**
   * {@inheritdoc}
   */
  public static function schema(FieldStorageDefinitionInterface $field_definition) {
    return array(
        'columns' => array(
            'value' => array(
                'description' => 'The time value.',
                'type' => 'int',
                'length' => 6,
            ),
        ),

    );
  }

Intento cambiar el tipo a tiempo (para mysql) pero el error mysql me devuelve un valor nulo para el tipo. Así que uso int para el tiempo de la tienda en segundo lugar.

FieldWidget: TimeWIdget.php

/**
* {@inheritdoc}
*/
public function formElement(FieldItemListInterface $items, $delta, array $element, array &$form, FormStateInterface $form_state) {
$value = isset($items[$delta]->value) ? $items[$delta]->value : '';
$element += array(
'#type' => 'time', //HTML5 input
'#default_value' => $value,
'#size' => 4,
'#element_validate' => array(
array($this, 'validate'),
),
);

return $element;
}

Mi entidad:

 $fields['heure_evenement'] = BaseFieldDefinition::create('time')
        ->setLabel(t('test'))
        ->setDescription(t('test'))
        ->setRequired(TRUE)
        ->setDefaultValue('')
        ->setDisplayOptions('view', array(
            'label' => 'above',
            'type' => 'string',
            'weight' => 3,
        ))
        ->setDisplayOptions('form', array(
            'weight' => 3,
        ))
        ->setDisplayConfigurable('form', TRUE)
        ->setDisplayConfigurable('view', TRUE);

Todo funciona, excepto una cosa, el tiempo de tipo de entrada HTML5

Drupal conoce algunas entradas en html5 pero no todas ... escriba tel, correo electrónico, número, rango, color, fecha, fecha y hora está bien, pero no solo el tiempo de tipo.

Así que esperaba obtenerlo con un complemento personalizado, pero no ...

Editar 1

La única forma que he encontrado es crear 2 selecciones para este tipo:

public function formElement(FieldItemListInterface $items, $delta, array $element, array &$form, FormStateInterface $form_state) {
$value = isset($items[$delta]->value) ? $items[$delta]->value : '';

    //heure
    for($i=0;$i<=24;$i++){
        $hour[]=$i;
    }

    //minutes
    for($i=0;$i<=59;$i++){
        $minutes[]=$i;
    }


$element += array('hour'=>array(
    '#title'=>t('Hour'),
    '#type' => 'select',
    '#options'=>$hour,
    '#default_value' => $value,
    '#element_validate' => array(
    array($this, 'validate'),
    ),
)
);

    $element += array('minutes'=>array(
        '#title'=>t('Minutes'),
        '#type' => 'select',
        '#options'=>$minutes,
        '#default_value' => $value,
        '#element_validate' => array(
            array($this, 'validate'),
        ),
    )
    );


return $element;
}

¿Alguna idea sobre esto?

Kevin
fuente
Necesito un tipo de campo como este, ¿puedes compartir tu código en github o en otro lugar?
Adrian Cid Almaguer
Puede usar el módulo drupal.org/project/time_field .
Lost Koder

Respuestas:

12

La propiedad del elemento de formulario se #typerefiere a un tipo de elemento, no a un elemento HTML. Está bien definir sus propios tipos de elementos (o tipos de temas), y puede proporcionar su propio marcado. Esto se puede hacer implementando un complemento RenderElement .

Actualizar:

También puede usar el datetimeelemento render y deshabilitar la parte de la fecha.

$element['#date_date_element'] = 'none';

Actualización 2:

El formulario de comentarios tiene un ejemplo de una matriz de representación que usa el datetimetipo. Entonces, dado que como guía,

  $form['time_without_date'] = array(
    '#type' => 'datetime',
    '#title' => $this->t('Time without date'),
    // HTML 5 time element format can be H:i
    '#default_value' => DrupalDateTime::createFromFormat('Y-m-d H:i:s', '1970-01-01 20:00', 'UTC'),
    '#size' => 20,
    '#date_date_element' => 'none',
    // This sets html 5 time element use explicitly, probably not necessary.
    '#date_time_element' => 'time',
  );
mradcliffe
fuente
2
También recordé algo sobre el elemento datetime. Debería poder establecer nonela parte de la fecha y recuperar solo la parte de la hora.
mradcliffe
@mradcliffe ¿Podría proporcionar instrucciones detalladas para este novato? Si puedo hacer que funcione, ¡no dudaría en darte la recompensa! ¡Gracias!
Chris Happy
¿Hay algo en particular en lo que estés atrapado? Probablemente sea difícil publicar código en un comentario, pero me aseguraría de que en su matriz de formulario se establezcan las propiedades de elemento apropiadas (claves con '#'). Actualizaré la respuesta con algunos ejemplos de api.drupal.org en un momento.
mradcliffe
1
Él creó otra pregunta aquí: drupal.stackexchange.com/questions/227029/… , ya que su pregunta era más específica para el widget de campo que para formar elementos de API.
mradcliffe 01 de
1
@AdrianCidAlmaguer Sí, he compartido el código aquí . Consideraré transformarlo en Github. ¡Espero eso ayude!
Chris Happy