How to display Progress on the form?

I am learning the this interesting framework and need your help in continuing my journey. Here is the situation:

I have a user registration form that calls UserController.actionRegister() where the new record is saved(). Then I send an email to the user and finally redirect the user to a predetermined page. I want to display a message (ajax message) like "Saving Data", "Sending Email", "Email Sent", etc. as the program completes various stages of actionRegister(). I believe that I need to place some sort of active label on the form and change its text as actionRegister() moves to the next step. Could you please put me on the right track?

Thank you so much.

Take a look to CWebUser setFLash and getFlash.

Those function saves in the state of the user a message for render in the next page.

For example you can write after saving:




$model->save();

Yii::app()->user()->setFlash('success', 'Item saved');

$this->redirect('index');



That will make so you have the message saved for this request and the next one.

In the main layout you can write the code for show the message:




<?php if ($message=Yii::app()->getFlash('success')):?>

<div class="success"><?php echo $message?></div>



That will work after the redirect, because the message are available even in the next one request.

If you want to do it with ajax, you have to send the message in some Json variable and then manage with javascript somehow.

Zaccaria,

Thanks for your suggestions. The first method will work only when the new (redirect) page is displayed. However, I want to display the progress message on the current page (similar to the what Google displays when one clicks the Send button on Google Mail, such as, Sending, Still Working, Your messaage has been sent). I need something that can update a label on the current page without redisplaying the page. I have some experience with Prado where it was quite simple. I could place an ActiveLabel or ActiveTextbox component in the page layout file and assign it an ID and define an AjaxCallBack function. Then in the page class file (similar to Yii Controller), I could set new value for any active component in AjaxCallBack function by referring to the component ID, e.g.


...->StatusLabel->Value = "Sending";

I am looking for similar functionality in Yii, which is similar to your second suggestion. Any suggestion how it can be done in Yii?

Forgot about ActiveLabel of Prado!!!

Yii is completely different, there is nothing of similar.

You can try with something like that:

In the controller:




$item->save();

$message='item saved';

if (Yii::app()->request->isAjaxRequest)

{

	echo CJSON::encode(

		array(

			'html'=>$this->renderPartial('view', $data, true),

			'flash'=>$message

			)

	);

	exit;

}

else

{

	Yii::app()->user->setFlash('success', $message);

	$this->render('view', $data, true);

}




this will send your message and your html to your function. The ajax should do something like that:




$.ajax({

	type: 'POST',

	url: url',

	success: function (response){

		data=JSON.parse(response);

		if (data.status=='success')

		{

			$('#divToUpdate').html(data.html);

			setFlash('success', data.flash);

		}

		else

		{

		...

		}

		

	}

});




Set flash is a javascript function that displays your flash message. So you should create a div like that:


<div id="#flashSuccess" style="display:none;"></div>

And a js function like this one:




function setFlash(type, message)

{ 

    $('#flashSuccess').html(message);

    $('#flashSuccess').fadeIn();



That is a very clean solution.

If you don’t want to implement all this machine in controller and view, you can always roughly write




<script type="text/javascript">

setFlash('success', <?php $message?>);

</script>



in the view that you renderPartial. That will call the setFlash and everithing will work fine.

zaccaria, Thank you so much for your quick response.

I tried to implement the first solution suggested by you, however, I did not get the desired result. Here is what I did in the User Registration form corresponding to UserController’s actionRefister()

Code in the view file


<div id="#flashSuccess" style="display:none;"></div>


<script>

    function setFlash(type, message)

{

    $('#flashSuccess').html(message);

    $('#flashSuccess').fadeIn();

}

</script>

...

...

		<?php echo CHtml::submitButton($model->isNewRecord ? 'Register' : 'Save'); ?>


		<?php echo CHtml::ajaxButton('Create User',array(),array('submit'=>array('register'))); ?>




Here, the first button is a regular submit button that calls Controller’s actionRegister and the second is ajax button.

This is partial actionRegister code in UserController.php




	public function actionRegister()

	{

		//$model=new User;

		$model=new User('register');

		

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

		{

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

			if($model->save()) {

				// Registration Successful. Send Email

			     $message = "Sending Message... Please Wait Dear";

                            if (Yii::app()->request->isAjaxRequest) {

                               

                                echo CJSON::encode(array(

                                            'html'=>$this->renderPartial('formregister', $data, true),

                                            'flash'=>$message

                                            )

                                        );

                                exit; 

                            } else {

                                Yii::app()->user->setFlash('success', $message);

                                //$this->render('register', $data, true);

                                //$this->render('register');

                            }

                            // Code to Send Email 

                            // If success, want to display message: Email Sent... 

				



Problem: I could not test the message display part, as nothing happens when the the Ajax button is clicked (perhaps it is not a post request!). Any suggestion, what should be done to workaround the issue?

Is a bit difficult to answer to this question.

Why ajax is not working is one of the most difficult part to deebug. You should use FireBug or something like that for check what is the browser sending to the server and what the server is responding.

My code was meant like "pseudo-code", not like working one. For example the line:




 'html'=>$this->renderPartial('formregister', $data, true),



There is no $data set, maybe you have a php notice.

Check what is answering the server and post here, I will try to help you