Php drupal 7文本字段#默认值_在重建表单后被忽略

Php drupal 7文本字段#默认值_在重建表单后被忽略,php,ajax,drupal-7,Php,Ajax,Drupal 7,注:我是drupal新手。我正在基于ajax示例开发一个模块:add_more和autocomplete。这样做的目的是创建一个表单,在该表单中,我可以将访问者添加到一次访问中,在texfield中输入使用ajax的LDAP连接填充的人员。这个很好用 问题是我希望能够删除任何我想要的访问者(而不仅仅是最后一个) 我有一个addvisitor按钮,它添加了一个字段集,其中包含访问者姓名的textfield,还有一个suppress按钮(对不起,没有图像,我的声誉太低)。这意味着3个访问者,3个字段

注:我是drupal新手。我正在基于ajax示例开发一个模块:add_more和autocomplete。这样做的目的是创建一个表单,在该表单中,我可以将访问者添加到一次访问中,在texfield中输入使用ajax的LDAP连接填充的人员。这个很好用

问题是我希望能够删除任何我想要的访问者(而不仅仅是最后一个)

我有一个addvisitor按钮,它添加了一个字段集,其中包含访问者姓名的textfield,还有一个suppress按钮(对不起,没有图像,我的声誉太低)。这意味着3个访问者,3个字段集及其“抑制”按钮

当用户单击访问者的suppress按钮时,我将其删除,并要求重新生成表单,但Drupal会继续显示第一个名称,就好像我已抑制了最后一个名称一样

function gaz_edit_visit_form($form, &$form_state) {
    [...]
  // Build the fieldset with the proper number of names. We'll use
  // $form_state['num_names'] to determine the number of textfields to build.
  if (empty($form_state['num_names'])) {
    $form_state['num_names'] = 1;

    $form['visitors_fieldset']['name'][0] = array(
      '#type' => 'fieldset',
      '#title' => 'Visiteur 1'
    );

    $form['visitors_fieldset']['name'][0]['visitor'] = array(
      '#type' => 'textfield',
      '#title' => t('Nom du visiteur'),
      '#autocomplete_path' => 'gaz/visit/edit_visit_autocomplete_callback',
    );

    $form['visitors_fieldset']['add_name'] = array(
      '#type' => 'submit',
      '#value' => t('Ajouter un visiteur'),
      '#submit' => array('ajax_example_add_more_add_one2'),
      '#ajax' => array(
        'callback' => 'ajax_example_add_more_callback2',
        'wrapper' => 'visitors-fieldset-wrapper',
      ),
    );
  }
  else {
    for ($i = 0; $i < $form_state['num_names']; $i++) {
      $form['visitors_fieldset']['name'][$i] = array(
        '#type' => 'fieldset',
        '#title' => 'Visiteur ' . ($i + 1),
      );

      $form['visitors_fieldset']['name'][$i]['visitor'] = array(
        '#type' => 'textfield',
        '#title' => t('Nom du visiteur'),
        '#autocomplete_path' => 'gaz/visit/edit_visit_autocomplete_callback',
        '#default_value' => $form_state['values']['visitors_fieldset']['name'][$i]['visitor'],
      );

      if ($form_state['num_names'] > 1) {
        $form['visitors_fieldset']['name'][$i]['remove_visitor' . $i] = array(
          '#type' => 'submit',
          '#value' => t('Supprimer'),
          '#submit' => array('gaz_visitors_remove'),
          '#ajax' => array(
            'callback' => 'ajax_example_add_more_callback2',
            'wrapper' => 'visitors-fieldset-wrapper',
          ),
          '#gaz_visitor_index' => $i,
        );
      }

      $form['visitors_fieldset']['add_name'] = array(
        '#type' => 'submit',
        '#value' => t('Ajouter un visiteur'),
        '#submit' => array('ajax_example_add_more_add_one2'),
        '#ajax' => array(
          'callback' => 'ajax_example_add_more_callback2',
          'wrapper' => 'visitors-fieldset-wrapper',
        ),
      );
    }
  }

  $form['submit'] = array(
    '#type' => 'submit',
    '#value' => t('Confirm'),
  );

  return $form;
}
重建过程结束时的$form(即gaz_edit_visit_form函数的结束)似乎没有问题,包括文本字段的默认值,但drupal用其他值填充它们。如果我有3个访问者,然后删除访问者2,我希望看到1和3的名称,但我看到1和2的名称。再一次,$form。。。看起来不错,不再有用户2的痕迹


我想我错过了眼前的大象,但我看不见它

请尝试浏览本教程。您创建表单的方式是错误的,这就是为什么不删除您想要的内容。

当Drupal执行AJAX重建时,其执行顺序是:

  • 以您提交的状态生成表单
  • 验证表单内容
  • 执行东西(我想,打电话给你的#提交处理程序)
  • 重新生成要显示的窗体
  • 返回输出(调用ajax回调)
$form_state['values']是在第一步中构建的。如果你想在第四步中使用它,就像你所做的那样。。。那很好,但你需要记住这一点

它解释了为什么您删除的访客数据仍在其中。您有(num+1)个处于$form_状态的访问者['values']

如何解决这个问题?这取决于您想如何更改代码,这取决于您。一种方法是使用两个计数器,其中第二个计数器与$i相同,但在某一点上它可以额外增加1个计数器,以跳过删除的值: (未测试代码)


我将看一看这个教程。在快速查看之后,我看不出有什么不同。我的代码基于drupal的add_more示例,但我可能在复制/粘贴中遗漏了一些东西!也许你没有漏掉任何代码,但是在drupal中有很多方法可以制作表单,它们在某些情况下有效,但在另一些情况下失败,但是,只有一两种方法是正确的,并且一切都很顺利。soory对于后面的回答:我被转移到了另一个最优先的项目,所以我在这一个项目上的工作稍微少一些:-(不管怎样,我没发现,看着你给我指出我做错了什么的图图。它们看起来真的很像。这一定比我想象的要复杂。
function gaz_visitors_remove($form, &$form_state) {
  array_splice($form_state['values']['visitors_fieldset']['name'], $form_state['triggering_element']['#gaz_visitor_index'], 1);
  if ($form_state['num_names'] > 1) {
    $form_state['num_names']--;
  }
  $form_state['rebuild'] = TRUE;
}
$i2 = -1;
for (...) {
  $i2++;
  if (!empty($form_state['#triggering_element']) && $form_state['#triggering_element']['#value'] == t('Supprimer') && $form_state['#triggering_element']['#gaz_visitor_index'] == $i) {
    // OK, we pressed this button to delete a visitor, this one has been deleted so skip it.
    $i2++
  }
  ...
    '#default_value' => $form_state['values']['visitors_fieldset']['name'][$i2]['visitor']
  ...