CActiveForm - customize error() and $.fn.yiiactiveform.updateInput

Hello Yii-community,

I’m currently up to the problem that I’d like to replace the default styling and technic to display the errors for a CActiveForm with enabled ajaxValidation and clientValidation.

Instead of the default method I’d like to use my custom method triggering qTip that is targeted to the input-field (http://craigsworks.com/projects/qtip2/docs/).

Currently I’m trying to overide the JS function $.fn.yiiactiveform.updateInput within a seperate JS-file but I think this is really dirty.

Is there a better solution to replace this method?

Kind regards,

Dominik

//Edit: My Current solution looks like this

ActiveForm.php




<?php

class ActiveForm extends CActiveForm 

{

	public function init() {

		parent::init();

		Yii::app()->getClientScript()->registerScriptFile('/js/'.Yii::app()->params['sysVersion'].'/form.js');

	}

	

	public function error($model,$attribute,$htmlOptions=array(),$enableAjaxValidation=true,$enableClientValidation=true)

	{

		$parentError = parent::error($model, $attribute, $htmlOptions, $enableAjaxValidation, $enableClientValidation);


		if (($error = $model->getError($attribute)))

		{

			$id=CHtml::activeId($model,$attribute);

			$inputID=isset($htmlOptions['inputID']) ? $htmlOptions['inputID'] : $id;

			unset($htmlOptions['inputID']);

			if(!isset($htmlOptions['id']))

				$htmlOptions['id']=$inputID.'_em_';


			Yii::app()->getClientScript()->registerScript('error_ipt-'.$inputID, "formError_show('{$inputID}', '{$error}');$('#{$htmlOptions['id']}').hide();");

		}


		//Keep the original Error in case of disabled javascript

		return $parentError;

	}

}



The used JS File form.js


function formError_show(inputID, message)

{

	var $el = $('#' + inputID);

	if ($el.length)

	{

		$el.qtip({

			content: {

				text : message

			},

			position: {

				my		: 'center left', // ...at the center of the viewport

				at		: 'center right',

				adjust: {

					x: -4

				}

			},

			show: {

				event: null,

				solo: false // ...and hide all other tooltips...

			},

			hide: {

				event:null

			},

			style: 'ui-tooltip-red ui-tooltip-shadow ui-tooltip-rounded'

		});

		$el.qtip('api').show();

	}

}


(function ($) {

	var getAFValue = function (o) {

		var type,

			c = [];

		if (!o.length) {

			return undefined;

		}

		if (o[0].tagName.toLowerCase() === 'span') {

			o.find(':checked').each(function () {

				c.push(this.value);

			});

			return c.join(',');

		}

		type = o.attr('type');

		if (type === 'checkbox' || type === 'radio') {

			return o.filter(':checked').val();

		} else {

			return o.val();

		}

	};


	/**

	 * updates the error message and the input container for a particular attribute.

	 * @param attribute object the configuration for a particular attribute.

	 * @param messages array the json data obtained from the ajax validation request

	 * @param form the form jQuery object

	 * @return boolean whether there is a validation error for the specified attribute

	 */

	$.fn.yiiactiveform.updateInput = function (attribute, messages, form) {

		attribute.status = 1;

		var $container,

			hasError = false,

			$el = form.find('#' + attribute.inputID);


		if ($el.length) {

			hasError = messages !== null && $.isArray(messages[attribute.id]) && messages[attribute.id].length > 0;

			$container = $.fn.yiiactiveform.getInputContainer(attribute, form);


			$container.removeClass(

				attribute.validatingCssClass + ' ' + 

				attribute.errorCssClass + ' ' + 

				attribute.successCssClass

			);


			if (hasError) {

				formError_show(attribute.inputID, messages[attribute.id][0]);

				

				$container.addClass(attribute.errorCssClass);

			} else if (attribute.enableAjaxValidation || attribute.clientValidation) {

				if ($el.qtip('api') != undefined)

					$el.qtip('api').hide();


				$container.addClass(attribute.successCssClass);

			}


			attribute.value = getAFValue($el);

		}

		return hasError;

	};

})(jQuery);

As I say, I’m not happy with this solution especially because of possible issues when upgrading Yii.

Is there a better solution that just doesn’t come to my mind?