1

I am creating a custom paginator in Drupal 7.

The paginator is working fine, the only problem is that every time I click to the next page button, increases the step in 2 (For example I can see pages 0,2,4,6,etc...)and that's because the submit button is executed twice and increases the number of the page by two.

As you can see in the callback I use AJAX to replace two different sections on the page, and that might be the cause.

Any idea?

Submit function:

function club_paginator_form_submit($form, &$form_state) {
$values = $form_state['values'];

if ($form_state['triggering_element']['#value'] == '>')
{
    $form_state['values']['current_page'] = intval($form_state['values']['current_page'])+1;
}
else
{
    $form_state['values']['current_page'] = intval($form_state['values']['current_page'])-1;
}

$form_state['rebuild'] = TRUE;

}

Forms: (...)

$form['next'] = array(
    '#name' => 'paginator-next',
    '#type' => 'submit',
    '#value' => t('>'),
    '#weight' => 5,
    "#ajax" => array(
        "callback" => "ajax_club_paginator_next",
        "effect" => "fade",
    ),
    '#prefix' => '<div id="club-paginator-page-replace">'.$page.'</div>',
    '#attributes' => array('class' => array('button')),
    '#submit' => array('club_paginator_form_submit'),
);

(...)

Callback:

function ajax_club_paginator_next($form, &$form_state)
{
    $page = intval($form_state['values']['current_page']);

    $html = '';
    $html .= '<div id="club-paginator-content-replace">';
    $html .= draw_clubes_page($page);
    $html .= '</div>';

    $paginator = '<div id="paginator">';
    $form = drupal_get_form('club_paginator_form', $page);
    $paginator .= drupal_render($form);
    $paginator .= '</div>';

    return array(
        '#type' => 'ajax',
        '#commands' => array(
            ajax_command_replace("#club-paginator-content-replace", $html),
            ajax_command_replace("#paginator", $paginator)
        )
    );
}
5
  • Could you provide more info? Such us paginator mockup?
    – Codium
    Nov 23 '13 at 0:34
  • 1
    When you remove one of the commands do you still have to problem of incrementing the value by 2? Nov 23 '13 at 11:16
  • No. That's the problem. I have to find another place to put the submit logic Nov 23 '13 at 12:10
  • (UPDATE) apparently yes. I don't know if there's some cache... It seemed to worked once but know it has the same workflow. Nov 23 '13 at 12:35
  • (UPDATE 2) drupal_get_form('club_paginator_form', $page); is calling the second submit logic. Any idea on how to stop that? Nov 23 '13 at 12:51
1

I Finally found the error...

drupal_get_form was calling the submission again, I was creating a new form like the one I was substituing, but I was also updating the old.

Instead of creating a new form, I just used the $form variable instead of drupal_get_form.

Please find the new logic below!

function ajax_club_paginator_next($form, &$form_state)
{
    $page = intval($form_state['values']['current_page']);

    $html = '';
    $html .= '<div id="club-paginator-content-replace">';
    $html .= draw_clubes_page($page);
    $html .= '</div>';

    $paginator = '<div id="paginator">';

    //Not Needed!
    //$form = drupal_get_form('club_paginator_form', $page);

    $paginator .= drupal_render($form);
    $paginator .= '</div>';

    return array(
        '#type' => 'ajax',
        '#commands' => array(
            ajax_command_replace("#club-paginator-content-replace", $html),
            ajax_command_replace("#paginator", $paginator)
        )
    );
}
1

In addition to Xavi's excellent answer to his question...

watch out for unnecessary use of drupal_get_form within an ajax callback function

e.g.

function your_callback($form, &$form_state) {
  $commands = array();
  $commands[] = ajax_command_replace('#result', drupal_render(drupal_get_form('your_form')['result']));
  return array('#type' => 'ajax', '#commands' => $commands);
}

It is only necessary to use drupal_get_form in the above callback if you need to deal with a different form from the one invoking the callback. If that's not the case, stick to the version below

function your_callback($form, &$form_state) {
  $commands = array();
  $commands[] = ajax_command_replace('#result', drupal_render($form['result']));
  return array('#type' => 'ajax', '#commands' => $commands);
}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.