
bbcjs.regex =
{
not_empty		: /^.+$/,
numeric			: /^\d+$/,
postcode		: /^[a-z]{1,2}\d{1,2}[a-z]? ?\d{1}[a-z]{2}$/i,
postcode_partial: /^[a-z]{1,2}\d{1,2}[a-z]?( ?\d{1}[a-z]{2})?$/i,
email			: /^[\w\d\._-]+@[\w\d-\.]+\.\w{2,4}(\.\w{2})?$/,
string			: /^[a-zA-Z\-\'_ \?]+$/,
age				: /^1?\d{1,2}$/,
date			: /^(\d{1,2}[\-|\/]\d{1,2}[\-|\/]\d{4})$/,
currency		: /^[\$\£]?\d+(\.\d{2})?$/
}
bbcjs.lib.string = {};
bbcjs.lib.string.obj2string = function (o, pd, vd)
{
//Have name1=val1&name2=val2 as defaults
if (typeof(pd)=="undefined") pd = "&";
if (typeof(vd)=="undefined") vd = "=";
var str = "", i, t="", cnt = 0;
if (typeof(o)=="object")
{
for (i in o)
{
cnt++;
if (typeof(o[i])=="object" && ((o[i].constructor==Object) || (o[i].constructor==Array) ))
{
t += i + vd + escape(bbcjs.lib.string.obj2string(o[i], pd, vd)) + pd;
}
else if (typeof(o[i])!="object")
{
t += i + vd + o[i] + pd;
}
}
str = t.substring(0, t.length-1);
}
else bbcjs.trace("obj2string expected typeof object, not "+typeof(o),1);
if (cnt==0) str = "_{}";
return str;
}
bbcjs.lib.string.string2obj = function (str, pd, vd)
{
//Have name1=val1&name2=val2 as defaults
if (typeof(pd)=="undefined") pd = "&";
if (typeof(vd)=="undefined") vd = "=";
var pairs = str.split(pd);
var i, j, o={}, pair=[], t;
for (i=0; i<pairs.length; i++)
{
pair = pairs[i].split(vd);
if (i==0 && (parseInt(pair[0])==0)) o = [];
if (pair.length==2)
{
t = unescape(pair[1]);
if (t.indexOf(vd)!=-1)
{
o[pair[0]] = bbcjs.lib.string.string2obj(t, pd, vd);
}
else
{
if (!isNaN(parseInt(pair[0]))) pair[0] = parseInt(pair[0]);
if (unescape(pair[1])!="_{}") o[pair[0]] = pair[1];
else o[pair[0]] = {};
}
}
else bbcjs.trace("WARNING: string2obj:: '"+pairs[i]+"' is not a proper name-val pair (using '"+pd+"' and '"+vd+"')",5);
}
return o;
}
bbcjs.lib.string.WordLimit = function (limit)
{
this.limit = limit;
this.type = 'WordLimit';
}
bbcjs.lib.string.countWords = function (str)
{
var matches = new Array();
matches = str.match(/\w+/g);
if (matches == null) return 0;
else return matches.length;
}
bbcjs.lib.string.WordLimit.prototype.validate = function (str)
{
return (bbcjs.lib.string.countWords(str) <= this.limit);
}
function sprintf()
{
if (!arguments || arguments.length < 1 || !RegExp)
{
return;
}
var str = arguments[0];
var re = /([^%]*)%('.|0|\x20)?(-)?(\d+)?(\.\d+)?(%|b|c|d|u|f|o|s|x|X)(.*)/;
var a = b = [], numSubstitutions = 0, numMatches = 0;
while (a = re.exec(str))
{
var leftpart = a[1], pPad = a[2], pJustify = a[3], pMinLength = a[4];
var pPrecision = a[5], pType = a[6], rightPart = a[7];
numMatches++;
if (pType == '%')
{
subst = '%';
}
else
{
numSubstitutions++;
if (numSubstitutions >= arguments.length)
{
bbcjs.trace('sprintf : Not enough function arguments (' + (arguments.length - 1)
+ ', excluding the string)\n'
+ 'for the number of substitution parameters in string ('
+ numSubstitutions + ' so far).',1);
}
var param = arguments[numSubstitutions];
var pad = '';
if (pPad && pPad.substr(0,1) == "'") pad = leftpart.substr(1,1);
else if (pPad) pad = pPad;
var justifyRight = true;
if (pJustify && pJustify === "-") justifyRight = false;
var minLength = -1;
if (pMinLength) minLength = parseInt(pMinLength);
var precision = -1;
if (pPrecision && pType == 'f')
precision = parseInt(pPrecision.substring(1));
var subst = param;
switch (pType)
{
case 'b':
subst = parseInt(param).toString(2);
break;
case 'c':
subst = String.fromCharCode(parseInt(param));
break;
case 'd':
subst = parseInt(param) ? parseInt(param) : 0;
break;
case 'u':
subst = Math.abs(param);
break;
case 'f':
subst = (precision > -1)
? Math.round(parseFloat(param) * Math.pow(10, precision))
/ Math.pow(10, precision)
: parseFloat(param);
break;
case 'o':
subst = parseInt(param).toString(8);
break;
case 's':
subst = param;
break;
case 'x':
subst = ('' + parseInt(param).toString(16)).toLowerCase();
break;
case 'X':
subst = ('' + parseInt(param).toString(16)).toUpperCase();
break;
}
var padLeft = minLength - subst.toString().length;
if (padLeft > 0)
{
var arrTmp = new Array(padLeft+1);
var padding = arrTmp.join(pad?pad:" ");
}
else
{
var padding = "";
}
}
str = leftpart + padding + subst + rightPart;
}
return str;
}
var printf = sprintf;
bbcjs.trace('<b><font color="green">jst_forms.js</font> was included.</b>',2);
bbcjs.forms 			= new Object();
bbcjs.forms.prototype 	= new bbcjs.Module("forms", 1, "$Revision: 1.34 $", "$Date: 2005/05/20 16:46:31 $");
bbcjs.forms.required = new Object();
bbcjs.forms.req_err	= new Object();
bbcjs.forms.valErrorMsg = "Please enter all required information correctly.";
bbcjs.forms.validate = function (f)
{
bbcjs.trace('<hr /><b>bbcjs.forms.validate('+f.name+')</b>...',2);
//Default return value is to return true to the system.
var retval = true, errorElement = " ", errorMsg = bbcjs.forms.valErrorMsg, val = "", i;
//Loop through all elements defined in the required object, as these are the ones needed.
for (i in bbcjs.forms.required)
{
bbcjs.trace("Checking element: <b>"+i+"</b>", 3);
//If we have a more complex validation to do (eg range) do so...
if ( (typeof(bbcjs.forms.required[i])=="object") && (typeof(bbcjs.forms.required[i].type)!="undefined") )
{
bbcjs.trace("&nbsp;&nbsp;Checking <b>"+bbcjs.forms.required[f[i].name].type+"</b> element",3);
if (!bbcjs.forms.validateComplex(f[i]))
{
val = bbcjs.forms.getValue(f[i]);
retval = false;
}
}
else
{
//Get the value of the elemnt from getValue
val = bbcjs.forms.getValue(f[i]);
if (val) val = val.toString();
bbcjs.trace("getValue returned element of type <b>"+typeof(val)+"</b>", 5);
//If we have an element which returned an array, just check that at least one was selected
if (typeof(val)=="object")
{
if (val.length==0) retval = false;
}
else
{
if (typeof(val)=="string") val = val.replace(/[\r|\n]/g, "");
if (typeof(val)=="undefined" || (!val.match(bbcjs.forms.required[i])) )
{
retval = false;
}
}
}
if (!retval)
{
//If we've not validated, set error message and break.
bbcjs.trace("&nbsp;&nbsp;Element does not validate! Value: "+val+"",3);
bbcjs.trace("&nbsp;&nbsp;&nbsp;&nbsp;Requires: "+bbcjs.forms.required[i],4);
errorElement = i;
break;
}
}
if (!retval)
{
//If the element that failed validation has a bespoke error message, use it.
if (typeof(bbcjs.forms.req_err[errorElement])!="undefined")	errorMsg = bbcjs.forms.req_err[errorElement];
// Added by benr - 4/5/04
// Only attempt to move the focus if the form element is not a hidden element
// Attempting to move the focus to hidden elements throws an exception
if (f[errorElement].type != "hidden") {
if (typeof(f[errorElement].focus)!="undefined") f[errorElement].focus();
}
alert(errorMsg);
}
//Debugging - set text colour to red or green dependent on return value.
var jst_fret_col = retval ? 'green' : 'red';
bbcjs.trace('<b>bbcjs.forms.validate</b> is returning <font color=\''+jst_fret_col+'\'><b>'+retval+'</b></font><hr />',2);
return retval;
}
bbcjs.forms.getRadioValue = function(fe)
{
var retval, i;
for (i=0; i<fe.length; i++)
{
if (fe[i].checked) retval = fe[i].value;
}
bbcjs.trace("getRadioValue is returning <b>"+retval+"</b>",5);
return retval;
}
bbcjs.forms.getCheckboxValues = function(fe)
{
var retval = [], i;
if (fe.length>0)
{
for (i=0; i<fe.length; i++)
{
if (fe[i].checked)
{
retval[retval.length] = fe[i].value;
}
}
}
else if (fe.checked) retval = fe.value;
else retval = "";
bbcjs.trace("getCheckboxValues is returning <b>"+retval+"</b>",5);
return retval;
}
bbcjs.forms.getSelectValue = function(sb)
{
var retval = sb.options[sb.selectedIndex].value;
bbcjs.trace("getSelectValues is returning <b>"+retval+"</b>",5);
return retval;
}
bbcjs.forms.getSelectValues = function(sb)
{
var retval = [], i;
for (i=0; i<sb.options.length; i++)
{
if (sb.options[i].selected && (sb.options[i].value!=""))
{
retval[retval.length] = sb.options[i].value;
}
}
bbcjs.trace("getSelectValues is returning <b>"+retval+"</b>",5);
return retval;
}
bbcjs.forms.validateComplex = function(fe)
{
var retval;
bbcjs.trace("bbcjs.forms.validateComplex() called...", 3);
switch (bbcjs.forms.required[fe.name].type)
{
case "range" : retval = bbcjs.forms.required[fe.name].contains(fe.value); break;
case "WordLimit" : retval = bbcjs.forms.required[fe.name].validate(fe.value); break;
default : retval = true;
}
bbcjs.trace("validateComplex is returning <b>'"+retval+"'</b>",4);
return retval;
}
bbcjs.forms.getValue = function(fe)
{
var typestring, t = "";
if ( (typeof(fe)!="object") && (typeof(fe)!="function"))
{
bbcjs.trace("WARNING - getValue expects type: form element, not '"+typeof(fe)+"'. Your element name may be wrong.",2);
return false;
}
//Set type of element, if type isn't defined, try to get from 0th element
if (typeof(fe.type)!="undefined") typestring = fe.type;
else if (typeof(fe.length)!="undefined") typestring = fe[0].type;
bbcjs.trace("<b>getValue()</b>, checking item of type <b>"+typestring+"</b>",4);
//switch on type...
switch (typestring)
{
case "radio" :
t = bbcjs.forms.getRadioValue(fe);
break;
case "checkbox"	:
t = bbcjs.forms.getCheckboxValues(fe);
break;
case "select-one" :
t = bbcjs.forms.getSelectValue(fe);
break;
case "select-multiple" :
t = bbcjs.forms.getSelectValues(fe);
break;
default :
t = fe.value;
break;
}
bbcjs.trace("getValue is returning <b>'"+t+"'</b>",4);
return t;
}
// Function:	bbcjs.forms.setValue (fe, str)
// Desc:	Set the value of a form element and update the user interface for radio buttons and check boxes
bbcjs.forms.setValue = function (fe)
{
var str = arguments[1], i;
bbcjs.trace('setValue function', 3);
bbcjs.trace(fe.type, 3);
if (fe.length>0 && fe.type != 'select-one' && fe.type != 'select-multiple')
{
bbcjs.trace('setValue for radio or checkbox', 3);
for (i=0; i<fe.length; i++)
{
if (fe[i].value == str){
fe[i].checked = true;
} else {
fe[i].checked = false;
}
}
}
// Added by benr
else if (fe.type == 'select-one')
{
bbcjs.trace('setValue for select-one', 3);
for (i=0;i<fe.length;i++)
{
if (fe[i].value == str)
{
fe.selectedIndex = i;
break;
}
}
}
else if (fe.type == 'select-multiple')
{
bbcjs.trace('setValue for select-multiple', 3);
for (i=0;i<fe.length;i++)
{
for (var j=1; j<arguments.length; j++)
{
if (fe.options[i].value == arguments[j])
{
fe.options[i].selected = true;
break;
}
}
}
}
else
{
bbcjs.trace('setValue for other', 3);
fe.value = str;
}
}
// Function:	bbcjs.forms.form2object
// Desc:	Returns an object that contains the result of doing a getValue on each element.
bbcjs.forms.form2object = function (f)
{
var o = new Object();
var t = "", i;
bbcjs.trace("form2object called on form named: '"+f.name+"'", 3);
//Loop through each form element and assign value to object "o"...
for (i=0; i<f.elements.length; i++)
{
if (f[i].name)
{
if ( (f[i].type == "checkbox") | (f[i].type == "radio") ) t = bbcjs.forms.getValue(f[f[i].name]);
else if (f[i].type != "submit") t = bbcjs.forms.getValue(f[i]);
else t = "";
if (!(t)) t = "";
o[f[i].name] = t;
}
}
bbcjs.trace("form2object returned: "+bbcjs.obj2list(o), 5);
return o;
}
// Function:	bbcjs.forms.form2cookie
// Desc:	Automatically converts form values into a cookie representation... is useful for page-to-page tracking.
//			Also requires the cookie module to be loaded
bbcjs.forms.form2cookie = function (f, name, exp, pth, dmn)
{
var retval = false, t = {}, c = {}, i=0;
if (bbcjs.cookies)
{
bbcjs.trace("form2cookie:: '"+f.name+"' -&gt; '"+name+"'",3);
t = bbcjs.forms.form2object(f);
//We need to ammend to a cookie instead of overwriting it... Thus we use cookieData...
if (bbcjs.cookies.cookieData[name])
{
c = bbcjs.cookies.cookieData[name];
for (i in t) c[i] = t[i];
t = c;
}
retval = bbcjs.cookies.setCookie(name, t, exp, pth, dmn);
}
else bbcjs.trace("form2cookie:: Could not find cookie module! Please include jst_cookies.",1);
return retval;
}
bbcjs.forms.limitTextareaWords = function ()
{
}

