所有动态项目的相同索引 - 嵌套动态表单 Yii2
Posted
技术标签:
【中文标题】所有动态项目的相同索引 - 嵌套动态表单 Yii2【英文标题】:Same index for all dynamic items - Nested dynamic form Yii2 【发布时间】:2016-05-25 08:58:03 【问题描述】:我得到所有新项目的相同索引(0)而不是递增索引。我不知道我的代码有什么问题和哪里有问题。我正在通过参考此演示 Nested Dynamic Form - Yii2 来解决此问题。对不起我的英语不好。
我的控制器
这是我的控制器。
public function actionUpdateperkara($id)
$model = $this->findModel($id);
$modelsPerkaraSatu = $model->tblMinitperkaras;
$modelsPerkaraDua = [];
$oldPerkaraDuas = [];
if (!empty($modelsPerkaraSatu))
foreach ($modelsPerkaraSatu as $indexPerkaraSatu => $modelPerkaraSatu)
$perkaraduas = $modelPerkaraSatu->tblMinitperkara2s;
$modelsPerkaraDua[$indexPerkaraSatu] = $perkaraduas;
$oldPerkaraDuas = ArrayHelper::merge(ArrayHelper::index($perkaraduas, 'per_id'), $oldPerkaraDuas);
if ($model->load(Yii::$app->request->post()))
// reset
$modelsPerkaraDua = [];
$oldPerkaraSatuIDs = ArrayHelper::map($modelsPerkaraSatu, 'perkara_id', 'perkara_id');
$modelsPerkaraSatu = ModelPerkara::createMultiple(TblMinitperkara::classname(), $modelsPerkaraSatu);
ModelPerkara::loadMultiple($modelsPerkaraSatu, Yii::$app->request->post());
$deletedPerkaraSatuIDs = array_diff($oldPerkaraSatuIDs, array_filter(ArrayHelper::map($modelsPerkaraSatu, 'perkara_id', 'perkara_id')));
// validate model and tblMinitperkaras models
$valid = $model->validate();
$valid = ModelPerkara::validateMultiple($modelsPerkaraSatu) && $valid;
$perkaraDuasIDs = [];
if (isset($_POST['TblMinitperkara2'][0][0]))
foreach ($_POST['TblMinitperkara2'] as $indexPerkaraSatu => $perkaraduas)
$perkaraDuasIDs = ArrayHelper::merge($perkaraDuasIDs, array_filter(ArrayHelper::getColumn($perkaraduas, 'per_id')));
foreach ($perkaraduas as $indexPerkaraDua => $perkaradua)
$data['TblMinitperkara2'] = $perkaradua;
$modelPerkaraDua = (isset($perkaradua['per_id']) && isset($oldPerkaraDuas[$perkaradua['per_id']])) ? $oldPerkaraDuas[$perkaradua['per_id']] : new TblMinitperkara2;
$modelPerkaraDua->load($data);
$modelsPerkaraDua[$indexPerkaraSatu][$indexPerkaraDua] = $modelPerkaraDua;
$valid = $modelPerkaraDua->validate();
$oldPerkaraDuasIDs = ArrayHelper::getColumn($oldPerkaraDuas, 'per_id');
$deletedPerkaraDuasIDs = array_diff($oldPerkaraDuasIDs, $perkaraDuasIDs);
if ($valid)
$transaction = Yii::$app->db->beginTransaction();
try
if ($flag = $model->save(false))
if (! empty($deletedPerkaraDuasIDs))
TblMinitperkara2::deleteAll(['per_id' => $deletedPerkaraDuasIDs]);
if (! empty($deletedPerkaraSatuIDs))
TblMinitperkara::deleteAll(['perkara_id' => $deletedPerkaraSatuIDs]);
foreach ($modelsPerkaraSatu as $indexPerkaraSatu => $modelPerkaraSatu)
if ($flag === false)
break;
$modelPerkaraSatu->butir_id = $model->butir_id;
if (!($flag = $modelPerkaraSatu->save(false)))
break;
if (isset($modelsPerkaraDua[$indexPerkaraSatu]) && is_array($modelsPerkaraDua[$indexPerkaraSatu]))
foreach ($modelsPerkaraDua[$indexPerkaraSatu] as $indexPerkaraDua => $modelPerkaraDua)
$modelPerkaraDua->perkara_id = $modelPerkaraSatu->perkara_id;
if (!($flag = $modelPerkaraDua->save(false)))
break;
if ($flag)
$transaction->commit();
return $this->redirect(['view', 'id' => $model->butir_id]);
else
$transaction->rollBack();
catch (Exception $e)
$transaction->rollBack();
return $this->render('_form_perkara', [
'model' => $model,
'modelsPerkaraSatu' => (empty($modelsPerkaraSatu)) ? [new TblMinitperkara] : $modelsPerkaraSatu,
'modelsPerkaraDua' => (empty($modelsPerkaraDua)) ? [[new TblMinitperkara2]] : $modelsPerkaraDua
]);
_form_perkara
这是我的表格。
<?php
use yii\helpers\html;
use yii\helpers\ArrayHelper;
use yii\helpers\Url;
use yii\widgets\ActiveForm;
use wbraganca\dynamicform\DynamicFormWidget;
use yii\jui\JuiAsset;
use yii\web\Response;
use yii\web\JsExpression;
use kartik\file\FileInput;
use kartik\date\DatePicker;
use kartik\time\TimePicker;
/* @var $this yii\web\View */
/* @var $model frontend\models\TblMinitbutiran */
/* @var $form yii\widgets\ActiveForm */
$this->title = 'Minit Mesyuarat : ' . $model->butir_id;
$this->params['breadcrumbs'][] = ['label' => 'Senarai Minit Mesyuarat', 'url' => ['index']];
$this->params['breadcrumbs'][] = ['label' => 'Minit Mesyuarat : ' . $model->butir_id, 'url' => ['view', 'id' => $model->butir_id]];
$this->params['breadcrumbs'][] = 'Butiran Perkara';
?>
<div>
<?php $form = ActiveForm::begin(['id' => 'dynamic-form']); ?>
<div class="panel panel-primary">
<div class="panel-heading"><b>Butiran Mesyuarat</b></div>
<div class="panel-body">
<div class="col-sm-3 ">
<?= $form->field($model, 'butir_bil')->textInput(['maxlength' => true]) ?>
</div>
<div class="col-sm-4 ">
<?= $form->field($model, 'butir_tarikh')->widget(DatePicker::classname(), [
'options' => ['placeholder' => 'pilih tarikh mesyuarat'],
'pluginOptions' => [
'format' => 'yyyy-mm-dd',
'endDate' => '+0d',
'autoclose'=>true
]
]); ?>
<?= $form->field($model, 'butir_masa')->widget(TimePicker::classname(), [
'pluginOptions' => [
'showMeridian'=>false
]
]); ?>
</div>
<div class="col-sm-5">
<?= $form->field($model, 'butir_tempat')->textarea(['rows' => 4]) ?>
</div>
</div>
</div>
<div class="panel panel-primary">
<div class="panel-heading"><b>Perkara</b></div>
<div class="panel-body">
<?php DynamicFormWidget::begin([
'widgetContainer' => 'dynamicform_wrapper',
'widgetBody' => '.container-items',
'widgetItem' => '.house-item',
'min' => 1,
'insertButton' => '.add-house',
'deleteButton' => '.remove-house',
'model' => $modelsPerkaraSatu[0],
'formId' => 'dynamic-form',
'formFields' => [
'perkara_bil',
'perkara_perkara',
],
]); ?>
<div>
<div>
<div style="overflow:hidden; height:30px;">
<div class="col-md-1 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:left"><b>BIL</b></div>
<div class="col-md-9 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:left"><b>PERKARA</b></div>
<div class="col-md-2 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:left"><b>TINDAKAN / MAKLUMAN</b></div>
</div>
</div>
<div class="container-items">
<?php foreach ($modelsPerkaraSatu as $indexPerkaraSatu => $modelPerkaraSatu): ?>
<div class="house-item">
<div class="col-md-1 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:center">
<?php
// necessary for update action.
if (! $modelPerkaraSatu->isNewRecord)
echo Html::activeHiddenInput($modelPerkaraSatu, "[$indexPerkaraSatu]perkara_id");
?>
<?= $form->field($modelPerkaraSatu, "[$indexPerkaraSatu]perkara_bil")->label(false)->textInput(['maxlength' => true]) ?>
</div>
<div class="col-md-9 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:center">
<?= $form->field($modelPerkaraSatu, "[$indexPerkaraSatu]perkara_perkara")->label(false)->textInput(['maxlength' => true]) ?>
</div>
<div class="col-md-2 alert alert-info" role="alert" style="padding:5px; height:50px; text-align:center">
<button type="button" class="add-house btn btn-success btn-xs"><span class="glyphicon glyphicon-plus"></span></button>
<button type="button" class="remove-house btn btn-danger btn-xs"><span class="glyphicon glyphicon-minus"></span></button>
</div>
<?= $this->render('_form_perkara2', [
'form' => $form,
'indexPerkaraSatu' => $indexPerkaraSatu,
'modelsPerkaraDua' => $modelsPerkaraDua[$indexPerkaraSatu],
]) ?>
</div>
<?php endforeach; ?>
</div>
</div>
<?php DynamicFormWidget::end(); ?>
</div>
</div>
<div class="form-group">
<?= Html::submitButton($model->isNewRecord ? 'Hantar' : 'Hantar', ['class' => 'btn btn-primary']) ?>
</div>
<?php ActiveForm::end(); ?>
</div>
<script type="text/javascript">
$(".dynamicform_wrapper").on("beforeInsert", function(e, item)
console.log("beforeInsert");
);
$(".dynamicform_wrapper").on("afterInsert", function(e, item)
console.log("afterInsert");
);
$(".dynamicform_wrapper").on("beforeDelete", function(e, item)
if (! confirm("Are you sure you want to delete this item?"))
return false;
return true;
);
$(".dynamicform_wrapper").on("afterDelete", function(e)
console.log("Deleted item!");
);
$(".dynamicform_wrapper").on("limitReached", function(e, item)
alert("Limit reached");
);
</script>
_form_perkara2
<?php
use yii\helpers\Html;
use wbraganca\dynamicform\DynamicFormWidget;
?>
<?php DynamicFormWidget::begin([
'widgetContainer' => 'dynamicform_inner',
'widgetBody' => '.container-rooms',
'widgetItem' => '.room-item',
'min' => 1,
'insertButton' => '.add-room',
'deleteButton' => '.remove-room',
'model' => $modelsPerkaraDua[0],
'formId' => 'dynamic-form',
'formFields' => [
'per_no',
'per_butiran',
'per_maklumat'
],
]); ?>
<div class="container-rooms" style="align:center">
<?php foreach ($modelsPerkaraDua as $indexPerkaraDua => $modelPerkaraDua): ?>
<div class="room-item">
<div class="col-md-1 alert alert-danger" role="alert" style="padding:5px; height:50px; text-align:center">
<button type="button" class="add-room btn btn-primary btn-xs"><span class="glyphicon glyphicon-plus"></span></button>
<button type="button" class="remove-room btn btn-warning btn-xs"><span class="glyphicon glyphicon-minus"></span></button>
</div>
<div class="col-md-1 alert alert-danger" role="alert" style="padding:5px; height:50px; text-align:center">
<?php
// necessary for update action.
if (! $modelPerkaraDua->isNewRecord)
echo Html::activeHiddenInput($modelPerkaraDua, "[$indexPerkaraSatu][$indexPerkaraDua]per_id");
?>
<?= $form->field($modelPerkaraDua, "[$indexPerkaraSatu][$indexPerkaraDua]per_no")->label(false)->textInput(['maxlength' => true]) ?>
</div>
<div class="col-md-8 alert alert-danger" role="alert" style="padding:5px; height:50px; text-align:center">
<?= $form->field($modelPerkaraDua, "[$indexPerkaraSatu][$indexPerkaraDua]per_butiran")->label(false)->textInput(['maxlength' => true]) ?>
</div>
<div class="col-md-2 alert alert-danger" role="alert" style="padding:5px; height:50px; text-align:center">
<?= $form->field($modelPerkaraDua, "[$indexPerkaraSatu][$indexPerkaraDua]per_maklumat")->label(false)->textInput(['maxlength' => true]) ?>
</div>
</div>
<?php endforeach; ?>
</div>
<?php DynamicFormWidget::end(); ?>
ModelPerkara 类
<?php
namespace frontend\models;
use Yii;
use yii\helpers\ArrayHelper;
class ModelPerkara extends \yii\base\Model
/**
* Creates and populates a set of models.
*
* @param string $modelClass
* @param array $multipleModels
* @return array
*/
public static function createMultiple($modelClass, $multipleModels = [])
$model = new $modelClass;
$formName = $model->formName();
$post = Yii::$app->request->post($formName);
$models = [];
if (! empty($multipleModels))
$keys = array_keys(ArrayHelper::map($multipleModels, 'perkara_id', 'perkara_id'));
$multipleModels = array_combine($keys, $multipleModels);
if ($post && is_array($post))
foreach ($post as $indexPerkaraSatu => $item)
if (isset($item['perkara_id']) && !empty($item['perkara_id']) && isset($multipleModels[$item['perkara_id']]))
$models[] = $multipleModels[$item['perkara_id']];
else
$models[] = new $modelClass;
unset($model, $formName, $post);
return $models;
检查员截图
input id in second div of "house-item" is same with the first one. This show that the index is not increments
【问题讨论】:
屏幕截图的链接已过期。请更新。 【参考方案1】:您需要在视图文件中添加 javascript 事件。
$js = '
jQuery(".dynamicform_wrapper").on("afterInsert", function(e, item)
jQuery(".dynamicform_wrapper .panel-title-address").each(function(index)
jQuery(this).html("Address: " + (index + 1))
);
);
jQuery(".dynamicform_wrapper").on("afterDelete", function(e)
jQuery(".dynamicform_wrapper .panel-title-address").each(function(index)
jQuery(this).html("Address: " + (index + 1))
);
);
';
$this->registerJs($js);
【讨论】:
很抱歉提出这个问题。我是 yii 的新手。还在学习过程中。在哪里添加javascript事件?在 标记或 中。感谢您的回复 您必须在视图文件中添加标签以上是关于所有动态项目的相同索引 - 嵌套动态表单 Yii2的主要内容,如果未能解决你的问题,请参考以下文章
动态嵌套表单总是创建一个额外的空白条目 - 使用 formtastic_coocoon