Adding multiple items

I have a form that lets a user enter their career history - it’s a very simple form with only 3 fields - type (dropdown), details (textfield) and year (dropdown).

Basically I want to include some dynamic functionality whereby the user can enter multiple items on the same page and then submit them all in one go. So for example there should be an "add another item" link which duplicates the same form fields below it.

Additionally the user should be able to remove an item from the list. There will be a main submit button at the bottom which saves all the data/changes.

Validation is also required, so whether this is done upon clicking the "add another item" link, or in the main submit is something else to think about.

I think I can do the jQuery for this but what I might struggle is capturing all the data and saving it individually - any tips for this?

I think you need to read this!

How to create/save more Model inputs and make them repeatable with jQuery

I am not wrong this wiki was made for an older version of Yii, but you can have an idea!!!

Check out this extension

it worked for me

doodle

Thanks got 2 doodle - I had a look at the demos for that plugin - one thing that I noticed was that the "remove" button will only remove the last added row - what if the user has added several rows and decides they need to remove row two? I think there should be a remove button on each row!

Pol - I can’t seem to get that example working :( The code is saving two different models and that makes it a bit more complex - any chance you take a look and amend for my requirements?

@GSTAR - yes I think I ran into that problem too. I believe that in my code to sort out the array I checked for a blank field so that it would remove that.

I 'll take a look at my code and post here if you like.

doodle

Yes please :)

I used this extension in two places on the same form, I will give you the code for the simpler implementation. The simple implementation was for a keyword field and the more complex one was for an author field. The authors had to be formatted in a very specific way because the result was a scientific publication. I can give you the code for the more complex version if you think it will help, but I doubt you’ll need it.

First, calling the widget in the form view file.


<?php $this->widget('application.extensions.appendo.JAppendo',array(

    'id' => 'keywordsTool',

    'form' => $form,

    'model' => $model,

    'maxRows'=>Yii::app()->params->maxWords,

    'labelAdd'=>'Add Keyword',

    'allowDelete'=>false,

    'viewName' => 'application.views.eventAbstract._keywords_form',

)); ?>

This is _keywords_form.php


<table class="appendo-gii" id="<?php echo $id ?>">

    <caption>

        <h4>Keywords</h4>

        <em>Please enter the keywords in the order that you would like them to appear. To add a keyword, click 'Add Keyword'

        </em>

        <div class="clear">Please choose a minimum of <?php echo Yii::app()->params->minWords ?> and a maximum of <?php echo Yii::app()->params->maxWords ?> keywords.</div>

        <div class="clear">To remove a keyword delete the text in the box, if you put a comma in your keyphrase it will count as more than one keyword.</div>


    </caption>

    <tbody>

        <tr>

            <th>Keyword or Phrase</th>

        </tr>

      

    <?php if ($model->keywords == null): ?>

        <tr>

            <td><?php echo CHtml::textField('keywordArray[]','',array('size'=>40)); ?></td>

        </tr>

    <?php else: ?>

<?php

$delim = ','; // this is the delimeter we will use

         $keywordArray = explode($delim,$model->keywords);

$keys =  count($keywordArray );


?>

        <?php for($i = 0; $i < $keys; ++$i): ?>

            <tr>

                <td><?php echo CHtml::textField('keywordArray[]',$keywordArray[$i],array('size'=>30)); ?></td>

        <?php endfor; ?>

    <?php endif; ?>

    </tbody>

</table>

This is the update method in the controller


public function actionUpdate($id)

	{

		$model=$this->loadModel($id);

                $status = null;

		$this->layout = '//layouts/column1';

		// Uncomment the following line if AJAX validation is needed

		// $this->performAjaxValidation($model);

                $states = array('accepted','scheduled','rejected','on-hold');

                foreach($states as $state){

                   if($model->swGetStatus()->getLabel() == $state)

                   {

                           $status = 1;

                           break;

                   }

                }

                

                

                if(MyUtils::abstractOwner($model->id) && $status == 1)

                {

                 Yii::app()->user->setFlash('restricted','You are no longer allowed to edit this abstract.');

		 $this->redirect(array('view','id'=>$model->id));

                }

		if(isset($_POST['EventAbstract']))

		{

			$model->attributes=$_POST['EventAbstract'];

			$keywordArray = (!isset($_POST['keywordArray']) ? array() : $_POST['keywordArray']); 

			$this->setKeywords($model,'keywords',$keywordArray);

                        $this->setAuthorField($model,$_POST['authorName'],$_POST['authorAffiliation'],$_POST['authorAffiliationLocation'],$_POST['authorRole'],$_POST['authorStudent']);                       if($model->save())

				$this->redirect(array('view','id'=>$model->id));

		}

		

		$this->render('update',array(

			'model'=>$model,

		));

	}



These two methods handle the array


        public function setKeywords($model,$field,$keys)

	{

            

            foreach(array_keys($keys) as $key)

                 {

                   if (strlen($keys[$key]) < 1)

                     {

                       unset($keys[$key]); //  take it out of the array

                     }

                 }

           $model->$field = (empty($keys) ? null : implode(',',$keys));

	}


        

	

	public function getKeywords($delimited)

	{

		$keys = explode(',',$delimited);

		return $keys;

	}

Let me know if you have any questions.

doodle