Using Session To Keep Active Tab

<Scenario>: I designed tabs page by CTabview, below is simple code in a view page, which just for your test. For example, you can add it into /protected/views/site/index.php, so you can see the tabs in your site, when you access: localhost/yourproject/index.php




    $this->widget('CTabView', array(

	'tabs'=>array(

	    'Tab1'=array(

		'title'='My Tab1',

		'content'='This is tab1.',

	    )

	    'Tab2'=array(

		'title='My Tab2',

		'content'='This is tab2, and click <a href="http://www.yiiframework.com/">here</a>.',

	    ),

    ));



Then click ‘My Tab2’ in tabs, you will see content in Tab2, then click url link to page, then when you are back to your page, it always display the default active tab, “My Tab1” in the page. How can I keep active tab when I am back?

<Method>:My first thought is to save current active tab into session data, so I need call AJAX script to submit active tab number to server side PHP script, so PHP code can save that in the session, then next page load it will display the active tab you last clicked.

<Solution>:I found CTabView is called jquery.yiitab.js, which is in /framework/web/js/source folder. You can see the code:




		yiitab: function() {


			function activate(id) {

				var pos = id.indexOf("#");

				if (pos>=0) {

					id = id.substring(pos);

				}

				var $tab=$(id);

				var $container=$tab.parent();

				$container.find('>ul a').removeClass('active');

				$container.find('>ul a[href="'+id+'"]').addClass('active');

				$container.children('div').hide();

				$tab.show();

			}

			this.find('>ul a').click(function(event) {

				var href=$(this).attr('href');

				var pos=href.indexOf('#');

				activate(href);			

				if(pos==0 || (pos>0 && (window.location.pathname=='' || window.location.pathname==href.substring(0,pos))))

					return false;

			});



Which will switch the active tab, once you click a new tab. You will see another jquery.yiitab.js in /assets/962ac65e/, the script is exactly same. An assets folder is normally used to store documents that are used in the creation of a webpage on client side, so you can add you code in this jquery.yiitab.js for test, after your code is correct, you can move your changes into /framework/web/js/source, the original code. Many people don’t like to change original code, you can copy that code to your own folder, like hefi did in http://www.yiiframework.com/forum/index.php/topic/1951-ctabview-change-active-tab/page__p__10899__hl__ctabview+active#entry10899

Here I will change add code in jquery.yiitab.js directly to show you the solution quickly and easily, so you can see the result immediately, but I am tryint to keep minimum changes on original code.

So in above code add "ajaxCall();" after "activate(href);" like below:




			this.find('>ul a').click(function(event) {

				var href=$(this).attr('href');

				var pos=href.indexOf('#');

				activate(href);

				//add ajax code to send id to session[activetab]

				ajaxCall(href);  //This ajaxCall is from /protected/views/site/js/ajaxScript.js, can be changed by your self

				if(pos==0 || (pos>0 && (window.location.pathname=='' || window.location.pathname==href.substring(0,pos))))

					return false;

			});



Now, you need claim this ajaxCall function and handle that in your PHP code.

Create ajaxScript.js to your /protected/view/site/, if you like you can create /js/ directory only for js code. I created that, so the code in /protected/views/site/js/ajaxScript.js:




ajaxCall = function ajaxCall(a){

            alert('in ajaxcall, and your active tab ='+a); //if you can see this pop up alert, then that means you code is working

            jQuery.ajax({

                // The url must be appropriate for your configuration;

                // this works with the default config of 1.1.11

                url: 'index.php/site/ajaxProcessor',

                type: "POST",

                data: {ajaxData: a},  

                 });

            };



Now, you can see we need add one action in siteController.php to handle your ajax data.

/protected/controllers/SiteController.php




	/**

	 * Performs the AJAX Processor.

	 * @param store current active tab id in session

	 */

	public function actionAjaxProcessor()

	{

		$a = $_POST['ajaxData'];	

		Yii::app()->session['activetab'] = str_replace('#', '', $a); //you need remove '#' in href mark.

	}



The last step, back to your CTabView claim code /protected/views/site/index.php,

load your ajaxScript.js before the PageTitle:




<?php

/* @var $this SiteController */

$baseUrl = Yii::app()->baseUrl;

$cs=Yii::app()->getClientScript();

$cs->registerScriptFile($baseUrl.'/protected/views/site/js/ajaxScript.js');

$this->pageTitle=Yii::app()->name;

?>



Then add code to get active tab data from session.




    //claim your active tab:

    $activetab = Yii::app()->session['activetab']?Yii::app()->session['activetab']:'Tab1';

    $this->widget('CTabView', array(

	'tabs'=>array(

	    'Tab1'=array(

		'title'='My Tab1',

		'content'='This is tab1.',

	    )

	    'Tab2'=array(

		'title='My Tab2',

		'content'='This is tab2, and click <a href="http://www.yiiframework.com/">here</a>.',

	    ),

        'activeTab'=>$activetab,

    ));



To test that, you need log into the system, not as guest, make sure the session is working. Sometimes the session is not working to the guest user.

Hope it can give you some helps.