Как заставить Drupal добавить поведение AHAH к элементу формы, возвращаемому через AHAH?

Итак, вот что я пытаюсь сделать:

<сильный>1. Я создаю и отображаю следующий элемент формы:

    $form['rb_download_' . $doc_id] = array(
      '#type' => 'submit',
      '#name' => 'doc_' . $doc_id,
      '#prefix' => "<div id='rb_doc_order_{$doc_id}'>",
      '#suffix' => '</div>',
      '#value' =>variable_get('rb_order_button', "buyOnline"),
      '#ahah'  => array(
         'event' => 'click',
         'path'  => "rb/case/doc_order_js/$case->nid/$doc_id",
         'wrapper' => "rb_doc_order_{$doc_id}",
         'effect' => 'fade',),
    );

<сильный>2. Функция действия возвращает и заменяет элемент выше новым элементом:

function rb_case_doc_order_js($case, $doc_id) {

  $button['rb_download_' . $doc_id] = array(

        '#type'         => 'submit',
        '#name'         => 'doc_' . $doc_id,
        '#prefix'       => "<div id='rb_doc_order_{$doc_id}'>",
        '#suffix'       => '</div>',
        '#value'        => variable_get('rb_order_confirm', "Remove from cart"),
  //'#attributes' => array('class' => 'ahah-processed'),
        '#ahah'         => array(

           'event'      => 'click',
           'path'       => "rb/case/doc_unorder_js/$case->nid/$doc_id",
           'wrapper'    => "rb_doc_order_{$doc_id}",
           'effect'     => 'fade',),

  );

  $output .= drupal_render($button);
  $output .= "<script type='text/javascript'>\n";
  $output .= "cart_block_item_count($count);\n";
  $output .= "Drupal.ahah;\n";
  $output .= "</script>\n";

  print drupal_json($output);

}

<сильный>3. В результате старая кнопка заменяется приведенной выше, но новая кнопка не AJAX активна.

Что мне нужно сделать, чтобы новый возвращаемый элемент был AHAH готов?


person dkinzer    schedule 01.09.2010    source источник


Ответы (1)


Ну, я не мог точно понять, как заставить файл делать вышеописанное. Но я придумал обходной путь (который в моем случае включает переключение между двумя разными значениями объекта элемента submit на стороне клиента, чтобы его поведение AHAH не терялось). На стороне сервера я просто проверяю разные значения и действую в зависимости от результатов:

<сильный>1. Определите элемент с другим значением в зависимости от условия

  if (empty($rb_item) ||($rb_item['node_checkout_nid'] != $node_checkout_nid)) {
    //if (true) {
    $form['rb_download_' . $doc_id] = array(
      '#type'   => 'submit',
      '#name'   => 'doc_' . $doc_id,
      '#prefix' => "<div id='rb_doc_download_{$doc_id}'>",
      '#suffix' => '</div>',
      '#value'  => variable_get('rb_doc_download_button', "buyOnline"),
      '#ahah'   => array(
         'event'   => 'click',
         'path'    => "rb/case/doc_download_js/$case->nid/$doc_id",
         'wrapper' => "rb_doc_download_{$doc_id}",
         'effect'  => 'none',
         'method'  => 'append',
    ),
    );
    unset($_SESSION['rb_case']['rb_dowload_' . $doc_id]);
  }
  else {
    $form['rb_download_' . $doc_id] = array(
      '#type' => 'submit',
      '#name' => 'doc_' . $doc_id,
      '#prefix' => "<div id='rb_doc_download_{$doc_id}'>",
      '#suffix' => '</div>',
      '#value' => variable_get('rb_return_button', "Remove from cart"),
      '#ahah'  => array(
         'event' => 'click',
         'path'  => "rb/case/doc_download_js/$case->nid/$doc_id",
         'wrapper' => "rb_doc_download_{$doc_id}",
         'effect'  => 'none',
         'method'  => 'append',
    ),
    );
  }

<сильный>2. Функция действия проверяет, какое значение имеет форма, и возвращает значение переключателя для элемента:

function rb_case_doc_download_js($case, $doc_id) {

  //Add code that will change how the form elements are rendered here ...

  //Now get form with possible new values and send toggle value back to the javascript on client side.

  $form_state = array('storage' => NULL, 'submitted' => FALSE);
  $form_build_id = $_POST['form_build_id'];
  $form = form_get_cache($form_build_id, $form_state);

  $args = $form['#parameters'];
  $form_id = array_shift($args);
  $form_state['post'] = $form['#post'] = $_POST;
  $form['#programmed'] = $form['#redirect'] = FALSE;

  //Toggle the form element value between <<Add to Cart>> and <<Remove from Cart>>
  $toggle_on  = variable_get('rb_doc_download_button', "buyOnline");
  $toggle_off = variable_get('rb_return_button', "Remove from cart");
  if ($form['rb_download_' . $doc_id]['#value'] == $toggle_on) {
    $toggle = $toggle_off;
    $form['rb_download_' . $doc_id]['#value'] = $toggle;
  }
  else {
    $toggle = $toggle_on;
    $form['rb_download_' . $doc_id]['#value'] = $toggle;
  }

  drupal_process_form($form_id, $form, $form_state);
  $form = drupal_rebuild_form($form_id, $form_state, $args, $form_build_id);

  $output .= "<script type='text/javascript'>\n";
  $output .= "cart_block_item_count($count);\n";
  $output .= "rb_button_toggle('rb_doc_download_{$doc_id}', '$toggle');\n";
  $output .= "</script>\n";

  print drupal_json($output);

}

<сильный>3. Функция JavaScript на стороне клиента изменяет значение элемента, но объект сохраняет свое поведение AJAX:

  /**
   * Change the button name
   */
  function rb_button_toggle(target, name) {
    alert(target);
    alert(name);
    if (target && name) {
      $(':submit', document.getElementById(target)).attr('value', name);
    }
  }

<сильный>4. И это работает для меня :)

Не стесняйтесь добавлять решение выше, если вы можете понять это.

person dkinzer    schedule 01.09.2010