web-dev-qa-db-fra.com

Changer de classe sur le wrapper div d'un élément de formulaire

Existe-t-il un moyen d'ajouter ou de modifier une classe dans un wrapper de formulaire (les div) à l'aide de l'API de formulaire?

Ou est-ce juste fait avec la fonction thème?

Si oui, quelle fonction de thème est utilisée pour changer cela?

11
chrisjlee

Vous pouvez remplacer theme_form_element() normalement si vous souhaitez modifier le thème globalement. Si vous souhaitez modifier un seul élément de formulaire spécifique, je suis conscient de deux choix.

  1. Vous pouvez enregistrer une nouvelle fonction de thème pour le type particulier d'élément de formulaire qui vous intéresse (par exemple, champ de texte). Vous créez ensuite cette fonction de thème (basée sur l'original, par exemple. theme_textfield() ) mais qui n'appelle pas theme('form_element', ...) à la fin (vous pouvez soit gérer à la fois le wrapper et l'élément dans la fonction de thème, ou vous pouvez créer une fonction de thème de wrapper distincte et l'utiliser). Enfin, vous ajoutez une propriété #theme À un élément de formulaire particulier, et cet élément obtiendra votre thème personnalisé.

  2. Vous pouvez créer un fichier de modèle appelé form_element.tpl.php Qui a simplement le comportement par défaut de theme_form_element() puis utiliser hook_preprocess_form_element() pour ajouter une suggestion de modèle. Ensuite, vous créez le nouveau modèle qui correspond à la suggestion. Vous entendez souvent des gens mentionner que les modèles sont légèrement plus lents que les fonctions, et pour un appel à thème aussi fréquemment utilisé, j'imagine que les gens hésitent à utiliser un modèle. Je n'ai cependant jamais fait de mesures pour cela moi-même. De plus, vous devez avoir suffisamment de contexte au stade du prétraitement pour pouvoir faire la suggestion.

5
Andy

Je sais que c'est un super vieux fil, mais j'ai appris à modifier des éléments de formulaire et à ajouter des classes. Je me suis mis à créer un module personnalisé:

function yourtheme_custom_form_alter(&$form, &$form_state, $form_id) {
 case'webform_number_whatever':
   _yourtheme_form_add_wrapper($form['submitted']['yourfieldhere'], array('form-field-some-style', 'not-label', 'whatever-other-styles-you-want'));
 break;
}

function _yourtheme_form_add_wrapper(&$element, $classes = array(), $type = array('form-item', 'form-type-textfield'), $removeTitle = FALSE){
  $element['#prefix'] = '<div class="' . implode(" ", $classes) . '"><div class="' . implode(" ", $type) . '">';
  $element['#suffix'] = '</div></div>';
}
4
tdm

Pour modifier le "wrapper", vous devez remplacer form_element. Fondamentalement, tous les éléments du formulaire sont rendus avec le thème form_element theme_form_element($element,$value); (fichier form.inc)

Donc, pour changer la façon dont cela rend vos éléments de formulaire, copiez simplement cette fonction dans votre dossier template.php et renommez-la en: phptemplate_form_element($element,$value)

vous pouvez maintenant apporter des modifications et elles seront utilisées à la place de la fonction d'origine

  1. Copiez theme_form_element($element,$value); de form.inc
  2. Collez-le dans (votre thème) template.php
  3. renommez-le en: phptemplate_form_element($element,$value)
  4. effacer tout le cache de thème
  5. apportez les modifications que vous souhaitez et elles seront utilisées.
3
Andre

Vous pouvez utiliser la propriété wrapper_attributes.

$form['example'] = [
  '#type' => 'textfield',
  '#title' => $this->t('Example'),
  '#wrapper_attributes' => ['class' => ['wrapper-class']],
];
1
ya.teck

Surtout, theme_form_element ne modifiera que le div wrapper parent direct et cela peut ne pas être la cible prévue pour les effets CSS.

[Bien que non programmatique, si l'on veut simplement appliquer une classe au top-wrapper d'un champ de noeud (c'est wrapper, wrapper, wrapper) on peut supposer utiliser le module "Field group" en sélectionnant "Manage Fields" pour un type de contenu particulier et sélectionnez "Ajouter un nouveau groupe" comme simple DIV. Ensuite, l'étiquette peut être supprimée et les classes souhaitées attribuées au wrapper supplémentaire (mais maintenant nous avons encore plus de wrappers) - avec une imbrication illimitée]

0
user24737

Rendez les attributs de wrapper configurables!

Créez votre propre fonction de thème d'élément de formulaire dans votre thème ... sites/all/themes/MY_THEME/theme/form-element.theme.inc

function my_theme_form_element($variables) {
  $element = &$variables['element'];

  $attributes = isset($element['#my_theme_wrapper_attributes']) ?
    $element['#my_theme_wrapper_attributes'] : array();

  ...

  $output = '<div' . drupal_attributes($attributes) . '>' . "\n";

  ...
}

Ensuite, vous pouvez faire des choses comme ça ...

function my_module_form_alter(&$form, &$form_state, $form_id) {
  $form['account']['mail']['#my_theme_wrapper_attributes']['class'][] = 'form-field--inline';
}
0
doublejosh

Il y a des cas où ni #prefix/#suffix Ni #attributes => array('class') ne donnent les résultats souhaités. Mon cas particulier est l'ajout d'une classe à la div ajax-wrapper autour d'un élément managed_file. #prefix/#suffix Crée un nouveau conteneur et #attributes/'class' Modifie la classe d'un élément interne, pas le plus externe.

Le div extérieur le plus normal est juste

<div id="edit-doc1--XX-ajax-wrapper">

ce qui est difficile à cibler en CSS. Je peux cibler [id^="edit-doc"] Ou [id$="-ajax-wrapper"] Mais les deux ciblent plus que les éléments que je voulais.

La solution que j'ai trouvée est d'ajouter un élément #process au formulaire et de manipuler manuellement le code de l'élément. Voici l'attribut #process Ajouté à la déclaration de l'élément de formulaire:

$form['doc1'] = array(
  '#type' => 'managed_file',
  '#process' => array('mymodule_managed_file_process'),
);

Et voici la fonction mymodule_managed_file_process():

function mymodule_managed_file_process($element, &$form_state, $form) {

  // Call the original function to perform its processing.
  $element = file_managed_file_process($element, $form_state, $form);

  // Add our own class for theming.
  $element['#prefix'] = str_replace(
    'id=',
    'class="managed-file-wrapper" id=',
    $element['#prefix']
  );

  return $element;
}

S'appuyer sur la substitution de chaînes n'est pas très portable, alors utilisez str_replace À vos risques et périls. Ce code, cependant, modifie en effet le DIV le plus externe pour ajouter la classe nécessaire:

<div class="managed-file-wrapper" id="edit-doc1--XX-ajax-wrapper">
0
Joseph Cheek

Vous pourriez utiliser

'#prefix' => '<div class="new_class">', '#suffix' => '</div>'

et cela l'enroulera

0
Alex