Le caselle di controllo selezionate (tassonomia) popolano un nuovo elenco di selezione con i valori delle caselle selezionate


7

* domanda con risposta: aiuto necessario con hook_node_submit nel modulo personalizzato per salvare i dati *


In Drupal 7, ho un tipo di contenuto personalizzato. In questo, esiste un riferimento a più termini per selezionare le categorie per quel contenuto.

Ora devo essere in grado di selezionarne una dalla categoria precedentemente selezionata e contrassegnarla in qualche modo come categoria "principale".

Diciamo che ho un campo di riferimento a più termini selezionati con le seguenti opzioni:

Apples
Bananas
Pears
Oranges
Grapes
Pineapples

L'utente seleziona Mele, Pere e Uva. Ora ho bisogno di:

  1. Crea a livello di programmazione un altro campo per ognuno di questi selezionati, magari con un callback ajax, e disponi di pulsanti di opzione in modo che io possa selezionare solo uno dei termini selezionati quale sia la mia categoria principale.
  2. Crea un campo radio accanto agli elementi contrassegnati, magari anche con ajax, dove posso selezionare quello principale tra quelli selezionati.

Qualcuno ha qualche idea in merito?

Per essere più chiari, ho un sacco di questi elenchi su un tipo di contenuto. Ripetere ogni elenco come un singolo elenco di valori non è un'opzione.

Immagino che la mia scommessa migliore sia quella di utilizzare hook_form_alter()una sorta di callback AJAX per creare un singolo pulsante di opzione accanto alla casella di spunta che l'utente ha appena spuntato o creare a livello di codice un nuovo elenco di campi radio per ciascun elemento selezionato nell'elenco specificato.

Aggiornamento: Ok, ho deciso che il modo migliore per farlo sarebbe quello di creare un modulo personalizzato che utilizza ajax per creare un pulsante di opzione per ogni casella di controllo selezionata, consentendo di selezionare l'elemento che dovrebbe essere usato come elemento principale.

Quindi ho usato hook_form_alter()per aggiungere una #after_buildfunzione in quanto dobbiamo attendere il rendering del modulo prima di poter accedere ai valori del termine fiscale.

Ecco il mio modulo finora. Uso molti commenti, quindi dovrebbe essere chiaro cosa sto cercando di fare:

MYMODULE.module

/**
 * Implementation of HOOK_form_alter()
 * Do the ajax form alteration
 */
function MYMODULE_form_alter(&$form, &$form_state, $form_id) {

  // 1.CONTENT FORM
  // I created a custom content type 'content' and added a term
  // reference to it 
  if($form_id == 'content_node_form') {

    // tax term ref is the main part, so let us
    // remove title and body fields
    unset($form['body']);
    unset($form['title']);

    // do our stuff after the form has been rendered ...
    $form['#after_build'][] = 'MYMODULE_after_build';

  }
}

/**
 * after_build function for content_node_form
 */
function MYMODULE_after_build(&$form, &$form_state) {

    dsm($form);  

    // In the after_build call we can now actually use the 
    // element_children function to grab the values of the fields that
    // don't start with a hash tag #
    // in this test case 1,2,3,4 and 5

    // wrap each of the elements rendered ...
    foreach(element_children($form['field_taxonomy']['und']) as $key) {

      $form['field_taxonomy']['und'][$key] += array(

        // this is added before the element and then replaced by our callback ..
        // we use the $key value in the id so that we know which div to replace 
        // depending on which checkbox is checked ...
        '#prefix' => '<div class="taxonomy_term_wrapper">
                        <div id="callback_replace_'.$key.'">Replace Me ' . $key . '</div>',

        // this is added after the element so we basically wrap around it ..
        '#suffix' => '</div>',

        // add some ajax stuff here ...
        '#ajax' => array(
          // name of the callback function to call upon change
          'callback' => 'MYMODULE_callback',
          // the id of the element that will be replaced
          'wrapper' => 'callback_replace_'.$key,
          // replace the wrapper
          'method' => 'replace',
          // what kind of effect do we want ...
          'effect' => 'fade',
          // show progress on callback
          'progress' => array('type' => 'throbber'),
        ),
      ); 



      if (!empty($form_state['values']['field_taxonomy']['und'][$key])) {
        // the form to show upon change ...
        $form['field_taxonomy']['und']['main_cat'] = array(
          // we want a radio button
          '#type' => 'radio',
          '#title' => t('Test Title'),
          '#description' => t('Test Description ...'),
          '#default_value' => empty($form_state['values']['field_taxonomy']['und'][$key]) ?
                              $form_state['values']['field_taxonomy']['und'][$key] :
                              $form_state['values']['field_taxonomy']['und'][$key],
        );
      }

    }

  return $form;
} 

function MYMODULE_callback($form, $form_state) {
 return $form['field_taxonomy']['und']['main_cat'];
}

Ecco come appare attualmente prima di selezionare una casella:

Ecco come appare attualmente prima di selezionare una casella

L'HTML del modulo renderizzato è il seguente:

immagine dello schermo


Non è proprio una risposta in quanto tale, ma prova a dare un'occhiata al modulo Esempi. Ha alcuni esempi in forma ajax che potrebbero aiutarti lungo la tua strada :) drupal.org/project/examples
Chapabu

Ciao Chapabu, grazie per la tua risposta. Ho usato gli esempi Ajax, ma il mio problema risiede nel fatto che devo usare after_build per aggiungere il mio codice e ora sono sconcertato dal fatto che non fa nulla ... Ho aggiunto molto più codice sopra - compresi i miei progressi finora con il modulo. Forse puoi vedere gli errori
tecjam

hmm..l'unica cosa che posso (rapidamente) vedere diversamente nel tuo after_build è il formato. Nei documenti Drupal dice che dovrebbe apparire così: $ form ['# after_build'] => array ('MYMODULE_after_build');
Chapabu,

Credo $ form ['# after_build'] => array ('MYMODULE_after_build'); è uguale a $ form ['# after_build'] [] = 'MYMODULE_after_build'; - Nota il []
tecjam

Inoltre, la funzione after_build sembra funzionare bene poiché racchiude i termini della mia tassonomia nei miei div personalizzati e aggiunge i miei div sostitutivi. Solo il callback non funziona ..
tecjam

Risposte:


1

creare gli elementi come caselle di controllo. dopo che sono stati selezionati, mostra un elenco a discesa con questi elementi o un altro pulsante di opzione per selezionare la categoria principale. è possibile nascondere il secondo menu a discesa utilizzando il seguente codice fino a selezionare le prime caselle di controllo.

'#states' => array(
'visible' => array(
':input[name="your checkbox"]' => array('checked' => TRUE),
 ),
)

aggiungilo all'elemento che vuoi nascondere.Questo sarà visibile solo quando la casella è selezionata.


0

Che ne dici di due elenchi, uno intitolato primario che accetta una selezione, l'altro multiplo. Sarà comunque necessario rivolgersi al secondo elenco o selezione per eliminare le duplicazioni.


Ciao e grazie per la tua risposta. Sì, certo che funzionerebbe. Tuttavia, ho un sacco di elenchi nella pagina di creazione del contenuto e averli tutti due volte non è un'opzione. Ho semplicemente chiarito la domanda sopra per fare un esempio.
tecjam,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.