// personyze.com
if (!window._S_T) _S_T =
{	server_id: 0,
	uid: null,
	busy: 2, // event load in progress; 0: idle; 1: delay; 2: querying
	timer: null, // event load timeout resource
	script_load_asked: {},
	html_input_state: {},
	html_input_state_changed_times: 0,
	filter_a: {}, // executed actions
	t_on_p_total: 0, // time on page total (sec) (is used by install_focus)
	t_on_p_focused: 0, // time on page in focus (sec) (is used by install_focus)
	start_time: 0, // is used by install_focus
	blocks: {}, // currently blocking action IDs
	occured_queue: [],
	page_groups: [], // array of group ids; which groups current location.href matches to?
	conds: {}, // e.g. {c1:0, c2:0, c10:[9,1,0]} - keys - IDs of conditions matched on this page. only conditions that appear in containers or sticky are listed. regular conds appear as c1:0, sticky conds appear as c10:[remain_sessions, reset_session_cnt, match_again]
	user_data: {},
	time_formats: {time:'%H:%M:%S', time_short:'%H:%M', date:'%Y %b %d', date_short:'%y/%m/%d', datetime:'%Y %b %d %H:%M:%S', datetime_short:'%y/%m/%d %H:%M'},
	temp_funcs: {},
	async: false,
	ready: false, // will be set to true when first log-visit will finish (bringing actions and containers)
	task_interval: 1500,
	act: {},
	act_params: {},
	default_containers: {},
	session_cookie_props:
	[	'_sid',
		'_inew',
		'_ls',
		'_lurl', // last URL
		'_lrfr', // last referrer
		'_la', // last activity
		'_so', // social sources
		'_li' // login id
	],
	a_timers: [], //"action timeouts"
	_doc: document,
	_window: window,
	_containers_e:[],
	_queue:[], //"images not in container"
	_queue_o:{}, //"images not in container"
	isIE: /*@cc_on!@*/false,
	conts_timer: null, // setTimeout for initializing containers
		get_win_4_evt: function(evt) {
		if ((evt == 'mouseup' || evt == 'keyup') && _S_T.isIE) {
			return document.body;
		}
		return _S_T._window;
	},
	get_left_btn: function() {
		return _S_T.isIE ? 1 : 0;
	},
	add_to_queue: function(rid, a) {
		var key = rid+","+a;
		if (key in _S_T._queue_o) return;
		_S_T._queue_o[key] = 1;
		_S_T._queue.push([rid,a]);
	},
	remove_from_queue: function(rid, a) {
		var key = rid+","+a;
		if (!(key in _S_T._queue_o)) return;
		delete _S_T._queue_o[key];
		for (var i=_S_T._queue.length-1;i>=0;--i) {
			var o = _S_T._queue[i];
			if (o[0] == rid && o[1] == a) {
				_S_T._queue.splice(i,1);
				return;
			}
		}
	},
	add_css: function(elem, css)
	{	if (!css) return;
		if (typeof(css) == 'string')
		{	elem.style.cssText += ';'+css;
		}
		else if (css.length != null)
		{	for (var i=0; i<css.length; i++) _S_T.add_css(elem, css[i]);
		}
		else if (typeof(css) == 'object')
		{	for (var p in css)
			{	if (!(p in {}))
				{	if (p.indexOf && p.indexOf('-')!=-1)
					{	p = p.toLowerCase().replace(/-\w/g, function($0) {return $0.charAt(1).toUpperCase()});
					}
					try {elem.style[p] = css[p]} catch (e) {window.console && console.error(e)}
				}
			}
		}
	},
	select_child: function(elem, node_name, or_create)
	{	node_name = (node_name+'').toUpperCase();
		var child = elem && elem.firstChild;
		while (child && child.nodeName.toUpperCase()!=node_name)
		{	child = child.nextSibling;
		}
		if (elem && !child && or_create)
		{	child = document.createElement(node_name);
			elem.appendChild(child);
		}
		return child;
	},
	id: function(id, find_all)
	{	id = (''+id).replace(/^\s+/, '').replace(/\s+$/, '');
		if (!id) return find_all ? [] : null;
		var elem, func = 'querySelector' + (find_all ? 'All' : '');
		if (document[func])
		{	if (/^\w[\w\d\-\[\]]*$/.test(id))
			{	if (id.indexOf('[') == -1)
				{	id += ',#'+id+',*[name="'+id+'"]';
				}
				else
				{	id = '*[id="'+id+'"],*[name="'+id+'"]';
				}
			}
			try {elem = document[func](id)} catch(e) {}
			return elem;
		}
		var is_id = /^#\w[\w\d\-]*$/.test(id);
		if (is_id)
		{	id = id.substring(1);
		}
		try {elem = document.getElementById(id)} catch(e) {}
		if (elem)
		{	return find_all ? [elem] : elem;
		}
					if (is_id)
			{	return find_all ? [] : null;
			}
			if (id in _S_T.containers)
			{	_S_T.find_all_containers();
				elem = _S_T.containers[id].elems;
				if (elem) return find_all ? elem : elem[0];
			}
			_S_T.task_interval = 8000; // i'm about to do heavy tasks
			if (_S_T.querySelectorAll && !/MSIE 6/.test(navigator.appVersion))
			{	elem = _S_T.querySelectorAll(id);
				return find_all ? elem : elem[0];
			}
			var is_parent = function(base, inside)
			{	while (inside)
				{	inside = inside.parentNode;
					if (inside == base) return true;
				}
				return false;
			};
			var find_inside = function(found, base, nodeName, id, className)
			{	if (id)
				{	var e = document.getElementById(id);
					if (e && (!nodeName || (e.nodeName+'').toLowerCase()==nodeName) && (!className || _S_T.has_class(e, className)) && is_parent(base, e))
					{	found.push(e);
					}
				}
				else
				{	for (var i=0; i<base.childNodes.length; i++)
					{	var e = base.childNodes.item(i);
						if (e.nodeType == base.nodeType)
						{	if ((!nodeName || (e.nodeName+'').toLowerCase()==nodeName || e.name && (e.name+'').toLowerCase()==nodeName) && (!className || _S_T.has_class(e, className)))
							{	found.push(e);
							}
							find_inside(found, e, nodeName, id, className);
						}
					}
				}
			};
			id = id.toLowerCase();
			var alts = id.split(',');
			var result = [];
			for (var a=0; a<alts.length; a++)
			{	found = [document.body || document.documentElement];
				var len = 0;
				var callback = function(all, nodeName, id, className)
				{	len += all.length;
					if (nodeName || id || className)
					{	var found2 = [];
						for (var i=0; i<found.length; i++)
						{	find_inside(found2, found[i], nodeName, id.substring(1), className.substring(1));
						}
						found = found2;
					}
				};
				(' '+alts[a]).replace(/\s+([\w\d\-]*)(#[\w\d\-]+|)(\.[\w\d\-]+|)/g, callback);
				if (len==alts[a].length+1 && found.length>0)
				{	if (!find_all) return found[0];
					result = result.concat(found);
				}
			}
			return !find_all ? result[0] : result;
			},
		/*@cc_on // based on technique by Paul Young (http://ajaxian.com/archives/creating-a-queryselector-for-ie-that-runs-at-native-speed)
		querySelectorAll: function(selector)
		{	var head = document.documentElement.firstChild;
			var styleTag = document.createElement("STYLE");
			head.appendChild(styleTag);
			if (!_S_T.qsResult) _S_T.qsResult = {};
			var inst_id = ''+Math.random();
			_S_T.qsResult[inst_id] = [];

			styleTag.styleSheet.cssText = selector + '{x:expression(_S_T.qsResult["'+inst_id+'"] && _S_T.qsResult["'+inst_id+'"].push(this))}';
			window.scrollBy(0, 0);
			head.removeChild(styleTag);

			var result = _S_T.qsResult[inst_id];
			delete _S_T.qsResult[inst_id];
			return result;
		},
	@*/
	has_class: function(elem, className)
	{	return (' '+elem.className+' ').replace(/\s/, ' ').toLowerCase().indexOf(' '+className+' ') != -1;
	},
	find_all_containers: function()
	{	if (_S_T.find_all_containers_found) return;
		_S_T.find_all_containers_found = true;
		var all = document.getElementsByTagName('*');
		var is_simple = /^\.?\w[\w\d\-]*$/;
		for (var html_id in _S_T.containers)
		{	if (!_S_T.containers[html_id].elems && is_simple.test(html_id))
			{	var found = [];
				if (html_id.charAt(0) == '.')
				{	html_id = html_id.substring(1);
					for (var i=0, j=all.length; i<j; i++)
					{	if (_S_T.has_class(all[i], html_id))
						{	found.push(all[i]);
						}
					}
				}
				else
				{	for (var i=0, j=all.length; i<j; i++)
					{	if (all[i].name==html_id || all[i].nodeName==html_id)
						{	found.push(all[i]);
						}
					}
				}
				_S_T.containers[html_id].elems = found;
			}
		}
	},
		unfind_all_containers: function()
	{				for (var html_id in _S_T.containers) delete _S_T.containers[html_id].elems;
			_S_T.find_all_containers_found = false;
			},
	qelem: function(qelem_id, find_all, root_node)
	{	var P_CLASS=0, P_ATTRIBUTES=1, P_STYLE=2;
		if (typeof(qelem_id) == 'string')
		{	return _S_T.id(qelem_id, find_all);
		}
		var subiter = function(elem, parent_score, qelem_id, step, return_found)
		{	var node_name = qelem_id[step][0];
			var node_index = qelem_id[step][1];
			var diff = qelem_id[step][2];
			for (var e=elem&&elem.firstChild, i=0; e; e=e.nextSibling)
			{	var cur_node_name = e.nodeName.toLowerCase();
				if (cur_node_name == 'tbody')
				{	subiter(e, parent_score, qelem_id, step, return_found);
				}
				else if (cur_node_name == node_name)
				{	var score = 1; // node_name matched
					if (diff)
					{	for (var j=0; j<diff.length; j++)
						{	var prop_name = diff[j][0];
							var prop_subname = diff[j][1];
							var value = diff[j][2];
							if (prop_name == P_CLASS)
							{	if (((' '+e.className+' ').indexOf(' '+prop_subname+' ')!=-1) ^ !value)
								{	score++;
								}
							}
							else if (prop_name == P_ATTRIBUTES)
							{	if (e.getAttribute(prop_subname) == value)
								{	score++;
								}
							}
							else if (prop_name == P_STYLE)
							{	if (e.style[prop_subname] == value)
								{	score++;
								}
							}
						}
						score = score / diff.length;
					}
					if (i++ == node_index)
					{	score++; // node_index matched
					}
					var max_score = (diff && diff.length || 0) + 2; // +1 point for node_name match, +1 point for node_index match
					return_found.push({elem:e, score:score/max_score*parent_score});
				}
			}
		};
		var iter = function(elem, parent_score, qelem_id, step)
		{	var found = [];
			subiter(elem, parent_score, qelem_id, step, found);
			if (step+1 >= qelem_id.length)
			{	return found;
			}
			var final_found = [];
			for (var i=0; i<found.length; i++)
			{	final_found = final_found.concat(iter(found[i].elem, found[i].score, qelem_id, step+1));
			}
			return final_found;
		};
		var elem;
		if (qelem_id.length)
		{	var first_tag = qelem_id[0][0];
			var found = first_tag.charAt(0)!='#' ?
				iter(root_node || document.body, 1.0, qelem_id, 0) :
				iter(document.getElementById(first_tag.substring(1)), 1.0, qelem_id, 1);
			found.sort(function(a, b) {return b.score - a.score});
			elem = found[0] && found[0].elem;
		}
		return !find_all ? elem : elem ? [elem] : [];
	},
	qelem_id_to_css: function(qelem_id)
	{	var P_CLASS=0, P_ATTRIBUTES=1, P_STYLE=2;
		if (typeof(qelem_id) == 'string')
		{	return qelem_id;
		}
		var ie_ver = !_S_T.isIE ? 0 : parseInt(navigator.appVersion.substring(navigator.appVersion.indexOf('MSIE')+4));
		var without_arrs =
		(	_S_T.isIE && ie_ver<7
		);
		var without_attrs =
		(	_S_T.isIE && ie_ver<7
		);
		var without_nth =
		(	_S_T.isIE && ie_ver<9
		);
		var arr = without_arrs ? ' ' : ' > ';
		var css = 'body';
		for (var i=0, j=qelem_id.length; i<j; i++)
		{	var tag = qelem_id[i][0];
			var index = qelem_id[i][1];
			var distinct = qelem_id[i][2];
			if (i==0 && tag.charAt(0)=='#')
			{	css = tag;
				continue;
			}
			var classes='', attrs='';
			if (distinct)
			{	for (var m=0, n=distinct.length; m<n; m++)
				{	var prop_name = distinct[m][0];
					var prop_subname = distinct[m][1];
					var value = distinct[m][2];
					if (prop_name == P_CLASS)
					{	if (value)
						{	classes += '.'+prop_subname;
						}
					}
					else if (prop_name == P_ATTRIBUTES)
					{	if (value && !without_attrs)
						{	attrs += '['+prop_subname+'="'+value+'"]';
						}
					}
				}
			}
			if (tag == 'tr')
			{	css += arr + 'tbody';
			}
			css += arr + tag + classes + attrs;
			if (!without_nth)
			{	css += ':nth-of-type(' + (index+1) + ')';
			}
		}
		return css;
	},
	get_comp_style: function(elem, default_value)
	{	try
		{	return elem.currentStyle || document.defaultView.getComputedStyle(elem, null) || default_value || {};
		}
		catch (e)
		{	return default_value || {};
		}
	},
	clone_style: function(elem)
	{	var comp_style = _S_T.get_comp_style(elem);
		var sa = [];
		for (var s in comp_style)
		{	if (typeof(comp_style[s])!='function' && isNaN(parseInt(s)) && !(s in {}))
			{	sa.push(s.replace(/([a-z])([A-Z])/g, function($0, $1, $2) {return $1+'-'+$2.toLowerCase()})+':'+comp_style[s]);
			}
		}
		elem.setAttribute('style', sa.join(';'));
		for (var n=elem.firstChild; n; n=n.nextSibling)
		{	if (n.nodeType == elem.nodeType)
			{	_S_T.clone_style(n);
			}
		}
	},
	apply_html_changes: function(html_changes)
	{	for (var i=0; i<html_changes.length; i++)
		{	var change = html_changes[i];
			var elems = _S_T.qelem(change.qelem_id, true);
			for (var j=0; j<elems.length; j++)
			{	var elem = elems[j];
				if (change.inner_html)
				{	var html=[], base=elem.innerHTML;
					for (k=0; k<change.inner_html.length; k++)
					{	var h = change.inner_html[k];
						if (typeof(h) == 'string')
						{	html.push(_S_T.subst_user_data(h));
						}
						else
						{	var pos=h[0], len=h[1]||0;
							if (pos < 0) pos += base.length;
							if (len <= 0) len = base.length + len - pos;
							html.push(base.substr(pos, len));
						}
					}
					elem.innerHTML = html.join('');
				}
				if (change.attrs)
				{	for (var k in change.attrs)
					{	if (change.attrs[k] == null)
						{	elem.removeAttribute(k);
						}
						else
						{	elem.setAttribute(k, change.attrs[k]);
						}
					}
				}
				if (change.style)
				{	for (var k in change.style)
					{	elem.style[k] = change.style[k];
					}
				}
				if (change.dup)
				{	for (var k=change.dup-1; k>=0; k--)
					{	elem.parentNode.insertBefore(elem.cloneNode(true), elem);
					}
				}
				if (change.drag)
				{	var el = _S_T.qelem(change.drag_qelem_id);
					if (el)
					{	el.style.position = 'static';
						_S_T.clone_style(el);
						switch (change.drag)
						{	case 'before': elem.parentNode.insertBefore(el, elem); break;
							case 'after': elem.parentNode.insertBefore(el, elem.nextSibling); break;
							case 'inside': elem.appendChild(el); break;
						}
					}
				}
				if (change.rm)
				{	elem.parentNode.removeChild(elem);
				}
				if (change.add_elem)
				{	var  el_add = document.createElement(change.add_elem);
					if (change.ae_inner_html)
					{	el_add.innerHTML = change.ae_inner_html;
					}
					if (change.ae_style)
					{	el_add.style.cssText = change.ae_style;
					}
					if (change.ae_attrs)
					{	for (var j in change.ae_attrs)
						{	try
							{	if (!(j in {})) el_add.setAttribute(j, change.ae_attrs[j]);
							}
							catch (ex)
							{	window.console && console.error(ex);
							}
						}
					}
					switch (change.ae_where)
					{	case 'before': elem.parentNode.insertBefore(el_add, elem); break;
						case 'after': elem.parentNode.insertBefore(el_add, elem.nextSibling); break;
						case 'inside': elem.appendChild(el_add); break;
					}
				}
			}
		}
	},
	htmlspecialchars: function(text)
	{	return (''+text).replace(/&/g, '&amp;').replace(/</g, '&lt;').replace(/>/g, '&gt;').replace(/"/g, '&quot;').replace(/'/g, '&#39;');
	},
	dechex: function(n, digit_places)
	{	var s = '';
		for (var i=0; i<digit_places; i++, n>>=4) s = '0123456789ABCDEF'.charAt(n & 0xF) + s;
		return s;
	},
	json_encode_str_arr: function(value)
	{	if (value instanceof Array)
		{	var result = [];
			for (var i=0, j=value.length; i<j; i++)
			{	result.push(json_encode_str_arr(value[i]));
			}
			return '['+result.join(',')+']';
		}
		else
		{	var quote = function(m) {return m=='\\' ? '\\u005C' : m=="'" ? "\\u0027" : m=='"' ? '\\u0022' : m=='\r' ? '\\r' : m=='\n' ? '\\n' : '\\u'+_S_T.dechex(m.charCodeAt(0), 4)};
			return '"'+(value+'').replace(/[\\'"<>&\0-\x1F\u0080-\uFFFF]/g, quote)+'"';
		}
	},
	get_cookie_domain: function()
	{	var domain='';
		for (var host in this.domains)
		{	if (host.substr(0, 2) == '*.')
			{	host = host.substring(2);
			}
			var domain2 = null;
			if (host.lastIndexOf(location.host)+location.host.length == host.length)
			{	domain2 = ';domain='+location.host;
			}
			else if (location.host.lastIndexOf(host)+host.length == location.host.length)
			{	domain2 = ';domain='+host;
			}
			if (domain2 && (domain=='' || domain2.length<domain.length))
			{	domain = domain2;
			}
		}
		return domain;
	},
	cookie_obj: function(name, new_value, set_new_value, attrs)
	{	name = encodeURIComponent(name);
		var obj = {};
		if (!set_new_value)
		{	var func = function(a, k, v) {obj[decodeURIComponent(k)] = decodeURIComponent(v)};
			decodeURIComponent((document.cookie.match(new RegExp('\\b'+name+'=([^;]+)')) || ['', ''])[1]).replace(/([^&=]+)=([^&]*)/g, func);
		}
		if (new_value || set_new_value)
		{	for (var i in (new_value || {})) obj[i] = new_value[i];
			var value = '';
			for (var i in obj)
			{	if (obj[i]!==null && typeof(obj[i])!='function')
				{	value += (value ? '&' : '') + encodeURIComponent(i) + '=' + encodeURIComponent(obj[i]);
				}
			}
			var exp = !new_value ? 1970 : name.charAt(0)=='_' ? 0 : 2100;
			exp = exp ? ';expires='+new Date(exp, 1, 1).toGMTString() : '';
			var c = name+'='+encodeURIComponent(value)+exp+(attrs || ';path=/'+this.get_cookie_domain());
			if (c.length >= (window.MAX_COOKIE_SIZE || 4096))
			{	throw new Error('Cookie "'+name+'" is too long');
			}
			document.cookie = c;
		}
		return obj;
	},
	params_obj: function(new_value, set_new_value, a, rid, throw_error)
	{	var obj = {};
		var new_str = '';
		var url_changed = false;
		var func = function(a, k_enc, v_enc)
		{	k = decodeURIComponent(k_enc);
			v = decodeURIComponent(v_enc);
			if (new_value && (k in new_value) && new_value[k]!=v)
			{	url_changed = true; // param is to be modified/removed
				if (new_value[k] != null)
				{	obj[k] = new_value[k];
					new_str += '&' + k_enc + '=' + encodeURIComponent(new_value[k]);
				}
			}
			else if (!new_value || !set_new_value || (k in new_value))
			{	obj[k] = v;
				new_str += '&' + k_enc + '=' + v_enc;
			}
			else
			{	url_changed = true; // param is to be removed
			}
		};
		location.search.replace(/^\?/, '').replace(/([^=&]+)=([^&]*)/g, func);
		for (var new_k in (new_value || {}))
		{	if (!(new_k in obj))
			{	obj[new_k] = new_value[new_k];
				url_changed = true; // param is to be added
				new_str += '&' + encodeURIComponent(new_k) + '=' + encodeURIComponent(new_value[new_k]);
			}
		}
		if (new_value)
		{	if (url_changed)
			{	if (a && rid)
				{	_S_T.redirect(a, rid, {search: new_str.substring(1)}, throw_error);
				}
				else
				{	location.search = '?' + new_str.substring(1);
				}
				return true;
			}
			if (throw_error) throw new Error("Tried to redirect to same URL");
			return false;
		}
		return obj;
	},
	get_cookie: function(name)
	{	return decodeURIComponent((document.cookie.match(new RegExp('\\b'+encodeURIComponent(name)+'=([^;]+)')) || ['', ''])[1]);
	},
	get_param: function(name)
	{	return decodeURIComponent((('?'+location.search).match(new RegExp('[\\?&]'+encodeURIComponent(name)+'=([^&]+)')) || ['', ''])[1]);
	},
	add_cont_event: function(elem, event, f, html_id) {
		_S_T._containers_e.push([event, html_id, _S_T.add_e(elem, 'on'+event, f)]);
	},
	end_session: function()
	{	_S_T.add_e(window, 'onbeforeunload', function() {_S_T.cookie_obj('_stat_track_s_id', null, true)});
	},
	__get_disp: function() {
		return function(){
			var ap=Array.prototype, c=arguments.callee, ls=c._listeners, t=c.target;
			if (c.caller) return;//must be top level function for events
			var r = t && t.apply(this, arguments)!==false;
			var lls = [].concat(ls);
			for(var i in lls){
				if(!(i in ap)){
					lls[i].apply(this, arguments);
				}
			}
		}
	},
	add_e: function(source, method, listener) {
		var f = source[method];
		if(!f||!f._listeners){
			var d = _S_T.__get_disp();
			d.target = f;
			d._listeners = [];
			f = source[method] = d;
		}
		return f._listeners.push(listener);
	},
	remove_e: function(source, method, handle){
		var f = source[method];
		if(f && f._listeners && handle--){
			delete f._listeners[handle];
		}
	},
	reg_onready: function(func)
	{	var p = 'reg_onready_156403';
		var loaded = function()
		{	/*@cc_on if (!window.addEventListener) {try{document.documentElement.doScroll('left')} catch (e) {return false} return true}@*/
			return ('uninitialized|loading').indexOf(document.readyState) == -1;
		};
		if (window[p+'_called'] || loaded())
		{	return setTimeout(func, 1);
		}
		if (!window[p])
		{	window[p] = function() {window[p+'_called']=true; window[p]=function() {}};
			var prev_onload = window.onload;
			window.onload = function() {prev_onload && prev_onload(); window[p]()};
			if (document.addEventListener)
			{	document.addEventListener('DOMContentLoaded', function() {window[p]()}, false);
			}
			else if (window.addEventListener && document.attachEvent)
			{	document.attachEvent('DOMContentLoaded', function() {window[p]()});
			}
			else
			{	(window[p+'_t'] = function() {loaded() ? window[p]() : setTimeout(window[p+'_t'], 400)})();
			}
		}
		var orig = window[p];
		window[p] = function() {orig(); func()};
	},
	Queue: function()
	{	this.ondone = null;
		this.n = 0;

		this.add = function()
		{	this.n++;
			var _this = this;
			return function()
			{	if (--_this.n == 0) _this.ondone && _this.ondone();
			};
		};

		this.wait = function(ondone)
		{	if (this.n == 0)
			{	ondone && ondone();
			}
			else
			{	this.ondone = ondone;
			}
		};
	},
	fire_actions: function(a, not_get_chains, ondone)
	{	var queue = new _S_T.Queue;
		if (a) for (var i=0; i<a.length; i++) for (var j=1; j<a[i].length; j++)
		{	var aid = ''+a[i][j], rid = a[i][0], pg = _S_T.actions_pagegroups && _S_T.actions_pagegroups['a'+aid];
			if ((aid in _S_T.filter_a) || aid in new this.SessCnt('noacts').get() || pg>0 && !_S_T.page_in_group(pg)) continue;
			var at = _S_T.get_atime(aid);
							var bypass_others = _S_T.fire_action(aid, rid, at, queue.add());
				if (bypass_others) return;
					}
		queue.wait(ondone);
	},
		stop_a: function(a) {
		try{clearTimeout(_S_T.a_timers[a]); _S_T.close_action(a);} catch(e) {}
	},
	fire_action: function(a, rid, at, ondone)
	{	//window.console && console.log('action: ', a, rid, at);
		var bypass_others = false;
		var stage_3 = function()
		{	var params = _S_T.act_params[a];
			if (params)
			{	var act = _S_T.act[params.action_type];
				var took_done = false;
				var exec = function()
				{	try
					{	bypass_others = act.onexec(a, rid, params);
						if (!act.requires_container) // done and doesn't require container
						{	_S_T.occured(-1, a, 3, 0, rid, 1);
						}
					}
					catch (e)
					{	if (window.console) console.log('Problem during execution of action '+a+' (rid='+rid+'). Details: '+e.message, e);
					}
					ondone && !took_done && ondone();
				};
				if (act.is_blocking)
				{	_S_T.block_action(a, !!act.set_ondone);
				}
				if (act.set_ondone)
				{	act.set_ondone
					(	function()
						{	_S_T.unblock_action(a);
							ondone && ondone();
						}
					);
					took_done = true;
				}
				act.is_immediate ? exec() : _S_T.reg_onready(exec);
			}
			else
			{	if (window.console) console.log('Problem during execution of action '+a+' (rid='+rid+'). No params received.');
			}
		};
		var stage_2 = function()
		{	_S_T.load_libs(_S_T.act_params[a].js_filenames, stage_3, ondone);
		};
		_S_T.load_libs(a, stage_2, ondone);
		return bypass_others;
	},
	init_page_events: function(iter)
	{	if (document.body)
		{	for (var html_id in _S_T.containers) this.init_page_event(html_id);
		}
		else // MSIE hack
		{	if (!iter) iter = 0;
			iter<100 && setTimeout('_S_T.init_page_events('+(iter+1)+')', 300);
		}
	},
	init_page_event: function(html_id)
	{	if (html_id==-5 || html_id==-6 || html_id==-7 || html_id==-8)
		{	var e_name = ['mouseup', 'mouseup', 'keyup', 'scroll'][-5 - html_id];
			this.add_cont_event
			(	_S_T.get_win_4_evt(e_name), e_name, function(e)
				{	var evt = _S_T._window.event || e, callee = arguments.callee;
					if
					(	html_id==-5 && evt.button==_S_T.get_left_btn() ||
						html_id==-6 && evt.button==2 ||
						html_id==-7 ||
						html_id==-8 && !callee._scroll_timeout
					)
					{	_S_T.occured(html_id, 1, 2, 0, _S_T.get_visit_id(), 0);
						if (html_id == -7)
						{	callee._scroll_timeout = 1;
							setTimeout(function() {delete callee._scroll_timeout}, 1000);
						}
					}
				},
				html_id
			);
		}
		else if (html_id==-9 || html_id==-10)
		{	var set_flag = function()
			{	var is_in = _S_T.is_url_in(this.href);
				if (is_in && (html_id==-9) || !is_in && (html_id==-10))
				{	var s = _S_T.inner_text(this).substr(0, 150);
					if (s == '') s = this.href.substr(0, 150);
					_S_T.occured(is_in ? -9 : -10, s, 0, 0, 0, (is_in ? 1 : 3));
				}
				clearTimeout(_S_T._a_flag_timeout);
				_S_T._a_flag = 1;
				_S_T._a_flag_timeout=setTimeout('_S_T._a_flag=0', 1000);
				return true;
			};
			this.reg_onready
			(	function()
				{	setTimeout(function()
					{	var hls = document.getElementsByTagName('A');
						for (var i=0, len=hls.length; i<len; ++i)
						{	_S_T.add_e(hls[i], 'onclick', set_flag);
						}
					}, 10);
				}
			);
			var unload = function()
			{	if (_S_T.cookie_obj('stat_track_u_id').uid && !_S_T._a_flag) _S_T.raise_event_focus(1);
			};
			this.add_e(window, 'onbeforeunload', unload);
		}
	},
	init_containers: function()
	{	clearTimeout(_S_T.conts_timer);
		_S_T.unfind_all_containers();
		var c = _S_T.containers;
		var all_inited = true;
		for (var html_id in c)
		{	if ((c[html_id].tp & ~c[html_id].inited))
			{	try
				{	// c[html_id] is {id:container_id, tp:container_types, ac:action_ids, em:style_override_empty, oc:style_override_occupied, ud:units_direction, uc:units_count_max, udf:user_data_format, ghm:grab_html_mask_regexp, cn:[1,2,-3], a:placed_action_id, rid:record_id, html:html, inited:0} // a, rid and html are assigned when action is put
					_S_T.init_container(html_id, c[html_id], _S_T.id(html_id));
				}
				catch (e)
				{	if (!_S_T.cont_errors) _S_T.cont_errors = {};
					if (!_S_T.cont_errors[html_id]) _S_T.cont_errors[html_id] = 0;
					if (_S_T.cont_errors[html_id]++ > 12)
					{	c[html_id].inited = c[html_id].tp;
					}
					window.console && console.log(e.message);
				}
				if (c[html_id].tp != c[html_id].inited) all_inited = false;
			}
		}
		if (all_inited || _S_T.task_interval == 8000 && new Date().getTime()-_S_T.start_time > 16000)
		{	_S_T.conts_timer = null;
		}
		else
		{	_S_T.conts_timer = setTimeout('_S_T.init_containers()', _S_T.task_interval); // try to init not inited containers later
		}
	},
	init_container: function(html_id, c, elem, noraise)
	{	if (!c.inited) c.inited = 0;
		var tp = c.tp & ~c.inited;
		if (tp == 0) return;
		if (c.cn && c.cn.length)
		{	var ok=0, found=0;
			for (var i=c.cn.length-1; i>=0; i--)
			{	if (c.cn[i] < 0)
				{	if (('c'+(-c.cn[i])) in _S_T.conds) return; // don't use container if condition matches
				}
				else
				{	found = 1; // if there were no positive containers - that means ok
					if (('c'+c.cn[i]) in _S_T.conds) ok = 1; // use container if condition matches
				}
			}
			if (found && !ok) return;
		}
		if (!elem && c.html && c.html.length)
		{	elem = _S_T.try_create_container(html_id);
		}
		if (elem)
		{	if (((tp) & 1))
			{	this.add_css(elem, c.a==null ? c.em : c.oc);
				if (!c._stop && c.a != null)
				{	try
					{	var step = c.ud == 'bt' || c.ud == 'rl' ? -1 : 1;
						var start = step==1 ? 0 : c.html.length-1;
						for (var i=start; i>=0 && i<c.html.length; i+=step)
						{	c.html[i].attach(elem); // this calls unblock when done
						}
						var e = c.a.join();
						c._stop = 1; // avoiding this will cause actions be reported many times
						if (!noraise)
						{	this.occured(html_id, e, 3, 1, c.rid, 1);
						}
					}
					catch (e)
					{	if (window.console) console.log('Problem insert HTML to container '+c.id, e.message, e);
					}
				}
				c.inited |= 1;
			}
			if (((tp) & 6))
			{	if (elem.value != null)
				{	var f = function() {_S_T.occured(html_id, (_S_T.id(html_id).value||'').substr(0, 150), 1, tp & 32774, 0, 0)};
					var bf = function() {_S_T.occured(html_id, (_S_T.id(html_id).value||'').substr(0, 150), 1, tp & 32774, 0, 2)};
					this.add_cont_event(elem, 'keyup', f, html_id);
					this.add_cont_event(elem, 'mouseup', f, html_id);
					this.add_cont_event(elem, 'blur', bf, html_id);
					c.inited |= 32774;
				}
			}
			if (((tp) & 8))
			{	this.add_cont_event(elem, 'click', function() {_S_T.occured(html_id, 1, 2, 8, 0, 1)}, html_id);
				c.inited |= 8;
			}
			if (((tp) & 16))
			{	this.add_cont_event(elem, 'click', function() {_S_T.filter_a={}; _S_T.occured(html_id, '', 0, 16, 0, 2)}, html_id);
				c.inited |= 16;
			}
			if (((tp) & 32))
			{	this.add_cont_event(elem, 'mouseover', function() {_S_T.occured(html_id, 1, 2, 32, 0, 0)}, html_id);
				c.inited |= 32;
			}
			if (((tp) & 2048))
			{	_S_T.occured(html_id, 1, 2, 2048, 0, 2);
				c.inited |= 2048;
			}
			if (((tp) & 448))
			{	if (!c.inited_event && ((tp) & 384))
				{	c.inited_event = 1;
					this.add_cont_event(_S_T._window, 'unload', function() {_S_T.grab_html.call(_S_T, html_id);}, null);
				}
				if (this.grab_html(html_id) !== false)
				{	c.inited |= c.tp & 32832; // 'grab html' and 'grab volatile html' must never have been initialized, so grab continues
				}
			}
			if (((tp) & 512) && this.get_visit_id()) // get_visit_id() is false before the user data are ready
			{	var v = this.subst_user_data(c.udf);
				elem.value!=null ? elem.value=v : elem.innerHTML=this.htmlspecialchars(v);
				c.inited |= 512;
			}
		}
		if (((tp) & 8192))
		{	var value = _S_T.apply_ghm(this.get_param(html_id), c.ghm);
			if (value != '')
			{	_S_T.occured(html_id, value, 1, tp & 8192, 0, 0);
				c.inited |= 8192;
			}
		}
		if (((tp) & 69632))
		{	c.inited |= tp & 69632;
		}
	},
	try_create_container: function(html_id)
	{	var default_containers = _S_T.default_containers;
		if (html_id in default_containers)
		{	return default_containers[html_id];
		}
		var elem = null;
		if (document.body)
		{	if (html_id == 'personyze-default-top')
			{	elem = document.createElement('div');
				document.body.insertBefore(elem, document.body.firstChild);
			}
		}
		return elem;
	},
	grab_html: function(html_id)
	{	if (_S_T.html_input_state_changed_times >= 100) return null; // returns null if not grabbed and no need to grab in future
		var c = _S_T.containers;
		var obj = _S_T.id(html_id);
		var s = _S_T.apply_ghm(_S_T.inner_text(obj), c[html_id].ghm).substr(0, 150);
		if (s && s != _S_T.html_input_state[html_id]) // if there is content && if content is changed...
		{	_S_T.html_input_state_changed_times++;
			_S_T.html_input_state[html_id] = s;
			_S_T.occured(html_id, s, ((c[html_id].tp) & 256) ? 0 : 1, c[html_id].tp & 33216, 0, ((c[html_id].tp) & 256) ? 2 : 1);
			return true; // true: grabbed
		}
		return false; // false: not grabbed
	},
	apply_ghm: function(text, regexp) // Apply "grab_html_mask_regexp" on text. Will catch first reference, e.g., if applying "\s*(.*?)\s*" on " foobar " will return "foobar". If the first char of mask is '-', it's not a part of PCRE, but it means negative assertion - will replace matched fragment(s) with empty string and return what is remained.
	{	if (!text) text = '';
		if (!regexp) return text;
		if ((''+regexp).charAt(0) != '*')
		{	var m = text.match(new RegExp(regexp));
			text = !m || m[1]==null ? '' : m[1];
		}
		else
		{	text = text.replace(new RegExp(regexp.substring(1), 'g'), '');
		}
		return text.replace(/^\s+/, '').replace(/\s+$/, '');
	},
	inner_text: function(elem)
	{	if (!elem) return '';
		if (elem.innerText != null) return elem.innerText;
		return (elem.innerHTML || '').replace(/<script[^>]*>[\S\s]*?<\/script>/ig, '')
			.replace(/<style[^>]*>[\S\s]*?<\/style>/ig, '').replace(/<[^>]*>/g, '').replace(/&nbsp;/ig, ' ').replace(/&lt;/ig, '<')
			.replace(/&gt;/ig, '>').replace(/&quot;/ig, '"').replace(/&amp;/ig, '&').replace(/\s+/g, ' ')
			.replace(/^\s+/, '').replace(/\s+$/, '');
	},
	keys: function(hash)
	{	var keys = [];
		if (hash && typeof(hash)=='object') for (var i in hash) if (!(i in {})) keys.push(i);
		return keys;
	},
		put_html: function(a, rid, w, h, html, stop, a_type, css, no_report_extra)
	{	this.add_to_queue(rid, a);
		for (var html_id in this.containers){
			var c = this.containers[html_id];
			if (c && ((c.tp) & 1) && c.uc > 0){
				if (c.__w === undefined) {c.__w = c.w; c.__h = c.h;}
				var a_ids = c.ac;
				var vert = c.ud == 'bt' || c.ud == 'tb';
				var erase_cont = !c.html;
				var html_cont =
				{	attach: function(elem)
					{	_S_T.block_action(a, true);
												var subelem = document.createElement(vert ? 'div' : 'span');
						if (html.cloneNode)
						{	subelem.appendChild(html);
						}
						else
						{	subelem.innerHTML = html;
						}
						var f = function()
						{	// personal click reporting for each action inside container
							_S_T.occured(html_id, a, 3, 1, -rid, 1);
						};
						if (erase_cont)
						{	if (elem.value != null)
							{	elem.value = '';
							}
							else
							{	while (elem.firstChild)
								{	elem.removeChild(elem.firstChild);
								}
							}
						}
						if (elem.value != null)
						{	elem.value += subelem.innerHTML;
							if (!no_report_extra)
							{	_S_T.add_e(elem, 'onkeypress', function(e) {if (!this.disabled && !this.readOnly && e.charCode) f()});
							}
						}
						else
						{	var elem2=elem, set_css_to=subelem;
							switch (elem2.nodeName.toUpperCase())
							{	case 'TABLE':
									elem2 = _S_T.select_child(elem2, 'TBODY', true);
								case 'TBODY':
									elem2 = _S_T.select_child(elem2, 'TR', true);
								case 'TR':
									elem2 = _S_T.select_child(elem2, 'TD', true);
									set_css_to = elem2;
								break;
							}
							elem2.appendChild(subelem);
							try
							{	_S_T.add_css(set_css_to, css);
							}
							catch (e)
							{	window.console && console.error(e);
							}
							if (!no_report_extra)
							{	subelem.onclick = f;
							}
						}
						_S_T.unblock_action(a);
					}
				};
				for (var i=0; i<a_ids.length; ++i){
					if (a_ids[i]==a) {
						var hasnt = 1;
						if (c.a) {
							for (var k=c.a.length;k>=0;--k) {
								if (c.a[k]==a) {hasnt=0;break;}
							}
						}
						if (hasnt && (vert ? (c.h < 0 || h <= 0 || h <= c.h) : (c.w < 0 || w <= 0 || w <= c.w))) {
							if (!c.html) c.html = [];
							c.html.push(html_cont);
							if (!c.a) c.a = []; c.a.push(a);
							if (!c.wh) c.wh = []; c.wh.push([w,h]);
							if (vert) {
								if (c.h >= 0 && h > 0) {
									c.h -= h;
									if (c.h < 0) c.h = 0;
								}
							} else {
								if (c.w >= 0 && w > 0) {
									c.w -= w;
									if (c.w < 0) c.w = 0;
								}
							}
							c.rid = rid;
							--c.uc;
							delete c._stop;
							var at = parseInt(stop);
							if (!isNaN(at) && at) setTimeout(function() {_S_T.del_html.call(_S_T, a, a_type);}, at*1000);
							this.remove_from_queue(rid, a);
							_S_T.containers[html_id].inited &= ~1;
							_S_T.init_containers();
							return 1;
						}
					}
				}
			}
		}
		_S_T.unblock_action(a);
		this.action_no_place(a);
	},
	del_html: function(a, a_type) {
		var cc = this.containers, found=0;
		for (var html_id in cc){
			var c = cc[html_id];
			if (c && ((c.tp) & 1) && c.a && c.a.splice && c.html && c.html.splice && c.wh && c.wh.splice) {
				for (var i=c.a.length-1; i>=0; --i) {
					if (c.a[i] == a) {
						c.a.splice(i, 1);
						c.html.splice(i, 1);
						c.wh.splice(i, 1);
						++c.uc;
						this.recalc_c_wh(c);
						delete c._stop;
						this.init_container(html_id, c, this.id(html_id), 1);
						found=1;
					}
				}
			}
		}
		if (found) _S_T.a_closed(a, a_type);
	},
	recalc_c_wh: function(c) {
		var vert = c.ud == 'bt' || c.ud == 'tb';
		var wh = 'w', j = 0;
		if (vert) {
			var wh = 'h', j = 1;
		}
		c.w = c.__w; c.h = c.__h;
		for (var k=0, kk=c.wh.length; k<kk; ++k) {
			if (c[wh] >= 0 && c.wh[k][j] > 0) {
				c[wh] -= c.wh[k][j];
				if (c[wh] < 0) c[wh] = 0;
			}
		}
	},
	action_no_place: function(a)
	{
	},
	custom_event: function(html_id, value)
	{	this.occured(html_id, value||'', 0, 1024, 0, 0);
	},
	occured: function(html_id, value, replace_add, container_mask, rid, mode) { // if rid is specified then report about occupied container (negative rid means personal report for single action inside shared container), otherwise initiate event
		if (!this.get_visit_id()) // before we got response from iframe (ld=1)
		{	_S_T.occured_queue.push([html_id, value, replace_add, container_mask, rid, mode]);
			return;
		}
		if (html_id==-1 || ((container_mask) & 1))
		{	var aids = (''+value).split(/,/);
			for (var n=aids.length-1; n>=0; n--)
			{	_S_T.filter_a[aids[n]] = true;
			}
		}
		if (('|'+this.session_cookie_props.join('|')+'|').indexOf('|'+html_id+'|') != -1)
		{	throw new Error('Text input used by Stat Track cannot be named: '+this.session_cookie_props.join(', '));
		}
		if (container_mask & 6)
		{	if (value == this.html_input_state[html_id]||'') return; // value isn't changed
		}
		this.flush_events();
		rid = parseInt(rid) || ('e'+_S_T.get_visit_id());
		var m = _S_T.cookie_obj('_stat_track_s_id');
		var reset = 1;
		// if rid < 0 then replace_add must be 3, and value must be single integer
		if (replace_add)
		{	for (var i in m)
			{	var prefix = '_'+container_mask+'_'+rid+'_';
				var prefix_neg = '_'+container_mask+'_'+(-rid)+'_';
				if ((''+i).substring((''+i).lastIndexOf(prefix)+prefix.length) == html_id)
				{	// found
					if (replace_add == -1)
					{	if (m[i] == value) reset = 0;
					}
					if (replace_add == 2)
					{	value = (value-0) + (m[i]-0);
					}
					if (replace_add == 3)
					{	var a1 = m[i].split(',').concat((value+'').split(',')), a2=[], old;
						a1.sort(function(a, b) {return a-b});
						for (var j=a1.length; j>=0; --j)
						{	if (old != a1[j])
							{	old = a1[j];
								a2.push(old);
							}
						}
						m[i] = a2.join();
						_S_T.cookie_obj('_stat_track_s_id', m, 1);
						reset = 0;
					}
					if (reset) delete m[i];
				}
				if (rid<0 && (''+i).substring((''+i).lastIndexOf(prefix_neg)+prefix_neg.length)==html_id)
				{	// if personal report is to be sent, so no need to send also shared report
					m[i] = (','+m[i]+',').replace(','+value+',', ',').substring(1).replace(/,$/, '');
					if (!m[i]) delete m[i];
					_S_T.cookie_obj('_stat_track_s_id', m, 1);
				}
			}
		}
		if (reset) {
			m[(this.secs() - m._sid + (replace_add?0:1))+'_'+container_mask+'_'+rid+'_'+html_id] = value; // make "replace events" be earlier
			_S_T.cookie_obj('_stat_track_s_id', m, 1);
		}
		// mode == 0: no send, only save to cookie
		if (mode == 1)
		{	_S_T.iframe_delayed(); // send with delay
		}
		else if (mode == 2)
		{	_S_T.iframe_delayed(1, 0); // send immediately
		}
		else if (mode == 3)
		{	_S_T.iframe_delayed(1, 1); // send immediately + use javascript instead of iframe
		}
	},
	events_to_str: function(obj) {
		var n_html_ids = [];
		for (var n_html_id in obj) n_html_ids[n_html_ids.length] = n_html_id;
		try {n_html_ids.sort()} catch (e) {}
		var str='', delim='', internal_id='';
		// event format: "{$session_time}_{$record_id}_{$container_id}_{$container_mask}_{$value}"
		var c = this.containers;
		for (var i=0; i<n_html_ids.length; i++)
		{	// m[1]: time offset since session start; m[2]: container_mask; m[3]: rid (record id); m[4]: html_id
			var m = n_html_ids[i].match(/^(\d+)_(\d+)_(e?-?\d*)_(.*)/);
			if (m[2] & 6)
			{	this.html_input_state[m[4]] = obj[n_html_ids[i]];
			}
			if
			(	m
				&&
				(	c[m[4]] ||
					m[4]==-1 ||
					m[4]==-2 ||
					m[4]==-3 ||
					m[4]==-4 ||
					m[4]==-5 ||
					m[4]==-6 ||
					m[4]==-7 ||
					m[4]==-8 ||
					m[4]==-9 ||
					m[4]==-10				)
				// filter empty "text input", "text input search", "grab static html", "grab html", "grab volatile html", "grab cookie", "grab url"
				&&
				!(c[m[4]] && ((c[m[4]].tp) & 78278) && !(obj[n_html_ids[i]]+'').match(/\S/))
			)
			{	/* {$session_time}_{$record_id}_{$container_id}_{$container_mask}_{$value} */
				var _cid = c[m[4]] && c[m[4]].tp && c[m[4]].id || m[4];
				str += delim+m[1]+'_'+m[3]+'_'+_cid+'_'+m[2]+'_'+encodeURIComponent(obj[n_html_ids[i]]);
				delim = '&';
				if (c[m[4]] && ((c[m[4]].tp) & 16384))
				{	internal_id = (''+obj[n_html_ids[i]]).replace(/^\s*/, '').replace(/\s*$/, '');
				}
			}
		}
		return {str:str, internal_id:internal_id};
	},
	iframe_delayed: function(immed, as_script)
	{	if (as_script)
		{	return _S_T.iframe(0, 1);
		}
		// delay to give to events chance to accumulate, so we do less queries to the remote server
		if (this.busy == 1) clearTimeout(this.timer);
		if (this.busy <= 1)
		{	this.busy = 1;
			if (immed)
			{	_S_T.iframe(0, 0);
			}
			else
			{	this.timer = setTimeout('_S_T.iframe(0, 0)', 6000);
			}
		}
	},
	iframe: function(is_load, as_script) {
		var props = this.get_props(0, is_load);
		if (!props || !is_load && !props.ev) return;
		var params='', delim='?';
		for (var i in props)
		{	params += delim+i+'='+encodeURIComponent(props[i]);
			delim = '&';
		}
		if (is_load && !this.async)
		{	document.write('<script src="'+'//counter.personyze.com/stat-track-log-visit.js.php'+params+'"></script>');
			this.busy = 0;
			this.iframe_delayed(); // if there are events pending, so call them; otherwise just do nothing
		}
		else if (!is_load && as_script)
		{	this.script_load('//counter.personyze.com/stat-track-log-visit.js.php'+params);
		}
		else
		{	var src = '//counter.personyze.com/stat-track-log-visit.js.php'+params;
			src = '<body onload="setTimeout(function() {parent._S_T.loaded()}, 1)"><script>var src = '+this.json_encode_str_arr(src)+'; document.write("<script src=\\""+parent._S_T.htmlspecialchars(src)+"\\"></"+"script>")</script></body>';
			src = "javascript:"+this.json_encode_str_arr(src);
			var html = as_script ? '<script src="'+'//counter.personyze.com/stat-track-log-visit.js.php'+params+'"></script>' : '<iframe width="0" height="0" frameborder="0" src="'+encodeURI(src)+'"></iframe>';
			this.busy = 2;
			this.iframe_html(html);
		}
	},
	get_loader_elem: function(id)
	{	var elem = document.getElementById(id);
		if (!elem)
		{	elem = document.createElement('div');
			elem.id = id;
			elem.style.position = 'absolute';
			elem.style.display = 'none';
			(document.body || document.documentElement).appendChild(elem);
		}
		return elem;
	},
	script_load: function(src)
	{	if (this.script_load_asked[src])
		{	return;
		}
		this.script_load_asked[src] = true;
		this.reg_onready
		(	function()
			{	var script = document.createElement('script');
				script.type = "text/javascript";
				script.src = src;
				var elem = _S_T.get_loader_elem('-ST-IF-S');
				while (elem.childNodes.length > 8)
				{	elem.removeChild(elem.firstChild);
				}
				elem.appendChild(script);
			}
		);
	},
	iframe_html: function(html)
	{	_S_T.reg_onready
		(	function()
			{	_S_T.get_loader_elem('-ST-IF').innerHTML = html;
			}
		);
	},
	loaded: function()
	{	this.iframe_html('');
		this.busy = 0;
		this.iframe_delayed(); // if there are events pending, so call them; otherwise just do nothing
	},
	secs: function(time) // client's local time offset
	{	return Math.floor(((time || new Date()).getTime() - new Date(1970, 0, 1).getTime()) / 1000);
	},
	hash: function(str)
	{	var h = 0;
		for (var i=0; i<str.length; i++)
		{	var x = str.charCodeAt(i) & 0xFFFFFFFF;
			x = ((h >> 7) ^ x) & 0xFF;
			x ^= x >> 4;
			h = (h << 8) & 0xFFFFFFFF;
			h ^= ((x << 12) & 0xFFFFFFFF) ^ ((x << 5) & 0xFFFFFFFF) ^ x;
		}
		return h;
	},
	get_props: function(is_short, is_load)
	{	var d=document, s=screen, n=navigator;
		var make_id = function(is_load)
		{				var gen_uid = function()
			{	var uid;
				do
				{	uid = (Math.random()+'').substring(2) & 0xFFFFFFFF;
				}
				while (uid>=0 && uid<500000000);
				return uid;
			};
			var uid=_S_T.cookie_obj('stat_track_u_id'), sid=_S_T.cookie_obj('_stat_track_s_id'), f=uid.f, st=uid.st||0, sy=uid.sy, uls=uid.ls||_S_T.secs(), li=uid.li||'', off=uid.off||'', ls=sid._ls, noacts=uid.noacts;
			sid = uid.uid && parseInt(sid._la)+1800>_S_T.secs() && parseInt(sid._sid)+5400>_S_T.secs() ? [sid._sid, sid._inew*2] : [_S_T.secs(), 1];
			uid = uid.uid ? [uid.uid, 0] : [gen_uid(), 1];
			if (sid[1] == 1)
			{	if (!is_load) return null; // request that came before page load (maybe false request that is noticed in FF) or that came after user erased his cookies but before he refreshed the page
				_S_T.cookie_obj('_stat_track_s_id', {_sid: sid[0], _inew: uid[1], _ls:uls, _lurl:'', _lrfr:'', _so:'', _li:''}, 1);
				st++; // session counter (how many times i have been started a new session)
				ls = uls; // last session time (when i had been ended a session last time)
			}
			_S_T.cookie_obj('stat_track_u_id', {uid:uid[0], f:f, st:st, sy:sy, ls:ls, li:li, off:off, noacts:noacts}, 1);
			var ev=_S_T.cookie_obj('_stat_track_s_id'), lurl=ev._lurl, lrfr=ev._lrfr, is_refresh=0, ev2={};
			for (var i=0; i<_S_T.session_cookie_props.length; i++)
			{	var p = _S_T.session_cookie_props[i];
				ev2[p] = ev[p] || '';
				delete ev[p];
			}
			ev2._la = _S_T.secs();
			if (is_load)
			{	var curl=_S_T.hash(location.href), crfr=_S_T.hash(d.referrer);
				if (lurl==curl && lrfr==crfr)
				{	is_refresh = 1;
				}
				ev2._lurl = curl;
				ev2._lrfr = crfr;
			}
			_S_T.cookie_obj('_stat_track_s_id', ev2, 1);
			if (sid[1] == 1)
			{	sy = new _S_T.SessCnt('sy').set(0, 1);
				new _S_T.SessCnt('noacts').set(0, 1);
			}
			return {
				id: uid[0], // user_id
				ss: sid[0], // session_id
				li: li, // login_id_type + login_id
				nw: (sid[1] + uid[1]*2) & 3, // is_new: is_new&1 means new session, is_new&2 means new user
				st: st, // session_counter
				ls: ls, // last_session_time
				rs: is_refresh, // is_refresh
				sy: sy, // sticky conditions
				rf: d.referrer, // referrer
				events: ev // events
			};
		};

		var grab_metas = function()
		{	var metaObj = document.getElementsByTagName('meta');
			var j = metaObj.length;
			var value = '';
			for (var html_id in _S_T.containers) {
				if(((_S_T.containers[html_id].tp) & 65536)) {
					for(var i=0; i < j; i++) {
						if(metaObj[i].name == html_id) {
							var val = _S_T.apply_ghm(metaObj[i].content, _S_T.containers[html_id].ghm).substr(0, 150);
							if(val) value += ',{"value":'+_S_T.json_encode_str_arr(val)+', "id":'+_S_T.containers[html_id].id+'}';
							break;
						}
					}
				}
			}
			return '[' + value.substring(1) + ']'; // _S_T.secs() - _S_T.cookie_obj('_stat_track_s_id')._sid
		};

		var grab_cookies = function()
		{	var metaObj = document.getElementsByTagName('meta');
			var j = metaObj.length;
			var value = '';
			for (var html_id in _S_T.containers) {
				if(((_S_T.containers[html_id].tp) & 4096)) {
					var val = _S_T.apply_ghm(_S_T.get_cookie(html_id), _S_T.containers[html_id].ghm).substr(0, 150);
					if(val) value += ',{"value":'+_S_T.json_encode_str_arr(val)+', "id":'+_S_T.containers[html_id].id+'}';
				}
			}
			return '[' + value.substring(1) + ']'; // _S_T.secs() - _S_T.cookie_obj('_stat_track_s_id')._sid
		};

		// props
		var lo = 0; // login operation
		var id = make_id(is_load);
		if (!id) return null;
		var events = this.events_to_str(id.events);
		if (events.internal_id)
		{	this.want_login_as(events.internal_id, 'IN');
		}
		var w_login = this.get_wanted_login_as();
		if (is_load && w_login && w_login!=id.li)
		{	if (id.li)
			{	// start new session
				_S_T.cookie_obj('_stat_track_s_id', {}, 1);
				id = make_id(1);
				if (!id) return null;
			}
			id.li = w_login;
			_S_T.cookie_obj('stat_track_u_id', {li:id.li});
			lo = 1;
		}
		this.uid = id.id;
		var props = {
			fr: this.get_f(),
			sr: this.server_id,
			ld: is_load?1:0,
			ur: location.href,
			rf: id.rf,
			id: id.id,
			ss: id.ss,
			li: id.li,
			nw: id.nw,
			st: id.st,
			ls: id.ls,
			rs: id.rs,
			sy: id.sy,
			lo: lo,
			ev: events.str,
			tm: this.secs(),
			pl: n.platform + (n.cpuClass && n.platform.indexOf(n.cpuClass)==-1 ? ' '+n.cpuClass : ''), // important to send platform regardless to is_short
			sc: s.width+'x'+s.height+'x'+s.colorDepth,
			th: this.hash(d.title),
			ck: '?',
			aj: '?',
			jv: '?',
			fl: -1,
			sl: -1,
			mp: -1,
			cn: '?',
			vl: -1,
			qt: -1,
			mt: is_load ? grab_metas() : '',
			co: is_load ? grab_cookies() : ''
		};
		var get_versions = function() {
			var a = {
				"QuickTime": {
					progID: ["QuickTime.QuickTime", "QuickTimeCheckObject.QuickTimeCheck.1"],
					classID: "02BF25D5-8C17-4B23-BC80-D3488ABDDC6B",
					getAXVInfo: function(obj) {
						var v = (obj && obj.QuickTimeVersion) ? obj.QuickTimeVersion.toString(16) : -1;
						return v == -1 ? -1 : v.substring(0,1);
					}
				},
				"VLC": {
					progID: [],//["VideoLAN.VLCPlugin"], popup alert in IE>=7 - do not use!
					classID: ""
				},
				"Windows Media": {
					progID: ["WMPlayer.OCX", "MediaPlayer.MediaPlayer.1"],
					classID: "22D6f312-B0F6-11D0-94AB-0080C74C7E95", // WMP6 -> semms to work a lot better, don't know why
					getAXVInfo: function(obj) {
						var v = (obj && obj.versionInfo) ? obj.versionInfo : "";
						v = parseInt(v);
						return isNaN(v) ? -1 : v;
					}
				},
				"Silverlight": {
					progID: ["AgControl.AgControl"],
					classID: ""
				},
				"Flash": {
					progID: ["ShockwaveFlash.ShockwaveFlash"],
					classID: "D27CDB6E-AE6D-11CF-96B8-444553540000"
				}
			};
			var f=a["Flash"].progID;
			var f0=f[0];
			for(var i=15;i>2;--i) {
				f[15-i]=f0+'.'+i;
			}

			var getInfo = function(name) {
				var version = -1;
				var getVersionFromPlugin = function(plugin) {
					if (!plugin.name) plugin = { name: plugin, description: name };
					var matches = /[\d][\d\.]*/.exec(plugin.name);
					if (matches && plugin.name.indexOf("Java") == -1) return matches[0];
					matches = /[\d\.]+/.exec(plugin.description);
					return matches ? matches[0] : "";
				};
				if (navigator.plugins && navigator.plugins.length) {
					for(var i=0;i<navigator.plugins.length;++i) {
						try
						{	var plugin = navigator.plugins[i];
							if (plugin.name.indexOf(name) != -1) {
								version = parseInt(getVersionFromPlugin(plugin));
								if (isNaN(version)) version = -1;
								break;
							}
						}
						catch (e)
						{
						}
					}
				} else {
					var getProgIdForAX = function(progID) {
						if (!progID) return null;
						for (var i=0; i<progID.length; i++) {
							try {
								var obj = new ActiveXObject(progID[i]);
								return [progID[i], obj];
							}
							catch(e) {}
						}
						return null;
					};
					var progID_obj = getProgIdForAX(a[name] && a[name].progID);
					if (progID_obj) {
						if (a[name].getAXVInfo) {
							version = a[name].getAXVInfo(progID_obj[1]);
						} else {
							version = getVersionFromPlugin(progID_obj[0]);
						}
					} else {
						version = -1;
					}
				}
				return version;
			};
			var names = ['QuickTime', 'VLC', 'Windows Media', 'Silverlight', 'Flash'];
			var res = [];
			for(var i=0; i<names.length; ++i) {
				res[i] = getInfo(names[i]);
			}
			return res;
		};
		var ajax_enabled = function()
		{	return window.XMLHttpRequest ? 'y' : 'n';
		}
		var has_canvas = function()
		{	return !!document.createElement('canvas').getContext;
		};
		var yn = function(v) {return v===false ? 'n' : v===true ? 'y' : '?'};
		if (!is_short) {
			var vv = get_versions();
			var props_ex = {
				ck: yn(n.cookieEnabled),
				aj: ajax_enabled(),
				jv: typeof(n.javaEnabled)!='function' ? '?' : yn(n.javaEnabled()),
				fl: vv[4],
				sl: vv[3],
				mp: vv[2],
				cn: yn(has_canvas()),
				vl: vv[1],
				qt: vv[0]
			};
			for (var i in props_ex) props[i] = props_ex[i];
		}
		return props;
	},
	is_url_in: function(u) {
		if (u.charAt(0) == '#') return true;
		u = u.toLowerCase();
		var mailto = 'mailto:';
		var javascript = 'javascript:';
		if (u.substr(0, javascript.length) == javascript) return true;
		if (u.substr(0, mailto.length) == mailto) return true;
		var m = u.match(/^(?:(?:(?:http|ftp)s?\:)?\/\/)?(?:www.)?([^/]+)/);
		if (m) {
			var h = m[1];
			var a = h.split(/\:/);
			if (a.length>1 && a[1] == '80') h = a[0];
			if (!(h in _S_T.domains)) return false;
		}
		return true;
	},
	raise_event_focus: function(immed)
	{	var rid = _S_T.get_visit_id();
		var secs = _S_T.secs();
		if (rid && (_S_T.focus_last_call || 0) < secs-1)
		{	_S_T.focus_last_call = secs;
			_S_T.occured(-2, Math.floor(_S_T.t_on_p_focused/1000)+'/'+Math.floor(_S_T.t_on_p_total/1000), 1, 0, rid, immed ? 3 : 0);
		}
	},
	install_focus: function() {
		this.start_time = new Date().getTime(); // presicion of 1 sec is not enough; 1.9+1.9+1.9 sec != 3 sec
		var curr = new Date().getTime();
		var focused = 1;
		_S_T.add_e(window, 'onfocus', function() {
			if (!focused) {
				focused = 1;
				curr = new Date().getTime();
			}
		});
		var blurf = function() {
			if (focused) {
				focused = 0;
				_S_T.t_on_p_focused += new Date().getTime() - curr;
				_S_T.t_on_p_total = new Date().getTime() - _S_T.start_time;
			}
		};
		_S_T.add_e(window, 'onblur', blurf);
		_S_T.add_e(window, 'onbeforeunload', function() {blurf(); _S_T.raise_event_focus()});
		_S_T.flush_events = function()
		{	_S_T.t_on_p_total = new Date().getTime() - _S_T.start_time;
			if (focused)
			{	_S_T.t_on_p_focused += new Date().getTime() - curr;
				curr = new Date().getTime();
			}
			var tmp = _S_T.flush_events;
			_S_T.flush_events = function() {};
			_S_T.raise_event_focus();
			_S_T.flush_events = tmp;
		};
	},
	flush_events: function()
	{
	},
	set_conts: function(containers, domains) {
		// cleanup previous
		clearTimeout(_S_T.conts_timer);
		var _e = _S_T._containers_e;
		if (_e) {
			for (var i=_e.length-1;i>=0;--i) {//"_e[i]=[e, html_id, handler]"
				var elem=_e[i][1]!=null ? _S_T.id(_e[i][1]) : _S_T.get_win_4_evt(_e[i][0]);
				if (elem) _S_T.remove_e(elem, 'on'+_e[i][0], _e[i][2]);
			}
			_e.length=0;
		}
		// set
		_S_T.containers = containers;
		if (domains == '') {
			domains = location.host.toLowerCase();
			if (domains.substr(0,4) == 'www.') domains = domains.substr(4);
		}
		domains = domains.split(/\s+/);
		var ds = {};
		for (var i=domains.length-1; i>=0; --i) {
			ds[domains[i]] = 1;
		}
		_S_T.domains = ds;
	},
	set_client_cookie: function(session_counter, last_session_time, sticky_conds)
	{	if (parseInt(session_counter) && parseInt(last_session_time) && (''+sticky_conds).match(/^(\d+:-?\d+)?(,\d+:-?\d+)*$/))
		{	_S_T.cookie_obj('stat_track_u_id', {ls:session_counter, st:last_session_time, sy:(''+sticky_conds)});
		}
	},
	set_user_data: function(user_data)
	{	for (var i in user_data) this.user_data[i] = user_data[i];
	},
	subst_user_data: function(format, acc, const_data)
	{	var props=null, props_all=null;
		var f = function(all, prop, fmt)
		{	var v;
			if (const_data && const_data[prop])
			{	v = const_data[prop];
			}
			else if (prop == '_')
			{	v = acc || '';
			}
			else if (prop == 'tm')
			{	v = Math.floor(new Date().getTime() / 1000) + '';
			}
			else if (prop == 'vid')
			{	v = _S_T.get_visit_id();
			}
			else if (prop == 'id_short')
			{	var v = (parseInt(_S_T.uid)+2147483647) + '';
				while (v.length < 10) v = '0' + v;
				v = v.substr(0, 6);
			}
			else
			{	v = _S_T.user_data[prop];
			}
			if (v == null)
			{	if (!props) props = _S_T.get_props(1);
				v = props[prop];
			}
			if (v == null)
			{	if (!props_all) props_all = _S_T.get_props();
				v = props_all[prop];
			}
			if (v == null) v = '';
			v = ''+v;
			fmt = fmt.split(':');
			for (var i=1; i<fmt.length; i++)
			{	var args=[], pos=fmt[i].indexOf('(');
				if (pos != -1)
				{	args = fmt[i].substring(pos+1, fmt[i].length-1).split(/\s*,\s*/);
					fmt[i] = fmt[i].substr(0, pos);
				}
				switch (fmt[i])
				{	case 'json':
						v = '"'+v.replace(/\\/g, '\\\\').replace(/"/g, '\\"').replace(/'/g, '\\u0027').replace(/</g, '\\u003C').replace(/>/g, '\\u003E').replace(/&/g, '\\u0026').replace(/%/g, '\\u0025')+'"';
					break;
					case 'pas':
						v = "'"+v.replace(/'/g, "''")+"'";
					break;
					case 'html':
						v = _S_T.htmlspecialchars(v);
					break;
					case 'url':
						v = encodeURIComponent(v);
					break;
					case 'time':
					case 'time_short':
					case 'date':
					case 'date_short':
					case 'datetime':
					case 'datetime_short':
						v = _S_T.strftime(_S_T.get_time_format(fmt[i]), v);
					break;
					case 'strftime':
						v = _S_T.strftime(args[0], v);
					break;
					case 'trim':
						v = v.replace(/^\s+/, '').replace(/\s+$/, '');
					break;
					case 'substr':
						v = v.substr(args[0]>=0 ? args[0] : v.length+parseInt(args[0]), args[1]>=0 ? args[1] : v.length+parseInt(args[1]));
					break;
					case 'substring':
						v = v.substring(args[0]>=0 ? args[0] : v.length+parseInt(args[0]), args[1]>=0 ? args[1] : v.length+parseInt(args[1]));
					break;
					case 'uc':
						v = v.toUpperCase();
					break;
					case 'lc':
						v = v.toLowerCase();
					break;
					case 'nth-word':
						v = _S_T.nth_word(v, args[0] || '');
					break;
					case 'param':
						v = _S_T.get_param(args[0] || '');
					break;
					case 'default':
						v = (''+v)!='' ? v : args[0];
					break;
				}
			}
			return v;
		};
		return (format+'').replace(/\$\{([\w\d\-]*)((?::[\w\d\-]+(?:\([^\(\)]*\))?)*)\}/g, f);
	},
	get_time_format: function(format_name)
	{	return _S_T.time_formats[format_name] || '%c';
	},
	set_time_format: function(format_name, format_str)
	{	_S_T.time_formats[format_name] = format_str;
	},
	strftime: function(fmt, time)
	{	var LocaleDetails = function()
		{	var d = new Date(0);
			this.time_zone = d.getHours()*60*60*1000 + d.getMinutes()*60*1000 - (d.getFullYear()==1970 ? 0 : 24*60*60*1000);
			var cycles=[], words=null;
			for (var i=3; i<365; i+=15) // start from 3th Jan 1970, because it's Sunday, then skip 1 week plus 1 day
			{	var w = new Date(i*24*60*60*1000 - this.time_zone).toLocaleString().replace(/[^\sA-Za-z\x7F-\xFF\u007F-\uFFFF]/g, '').split(/\s+/);
				if (!words) words = w;
				for (var j=0; j<words.length; j++)
				{	if (words[j] != w[j])
					{	if (!cycles[j]) cycles[j] = [words[j]];
						if ((' '+cycles[j].join(' ')+' ').indexOf(' '+w[j]+' ') == -1)
						{	cycles[j].push(w[j]);
						}
					}
				}
			}
			this.wdays = ['Sun','Mon','Tue','Wed','Thu','Fri','Sat']; // default
			this.months = ['Jan','Feb','Mar','Apr','May','Jun','Jul','Aug','Sep','Oct','Nov','Dec']; // default
			for (var i=0; i<cycles.length; i++)
			{	if (cycles[i] && cycles[i].length == 7) this.wdays = cycles[i];
				else if (cycles[i] && cycles[i].length == 12) this.months = cycles[i];
			}
		};
		if (!_S_T.__locale_details)
		{	_S_T.__locale_details = new LocaleDetails;
		}
		var locale_details = _S_T.__locale_details;
		var zero_pad = function(d) {return d<10 ? '0'+d : d};
		time = time==null ? new Date() : (time instanceof Date) ? time : new Date(time*1000);
		var callback = function(all, f)
		{	if (f == 'j')
			{	var d = new Date(time.getTime());
				d.setMonth(0);
				d.setDate(1);
				return (time.getTime() - d.getTime()) / (24*60*60*1000);
			}
			if (f == 'Z')
			{	var tz = locale_details.time_zone/60000, atz=Math.abs(tz), m=atz%60, h=(atz-m)/60, gmt=tz>=0 ? 'GMT+' : 'GMT-';
				return gmt + zero_pad(h) + ':' + zero_pad(m);
			}
			return f=='A' || f=='a' ? locale_details.wdays[time.getDay()] :
				f=='B' || f=='b' ? locale_details.months[time.getMonth()] :
				f=='c' ? time.toLocaleString() :
				f=='d' ? time.getDate() :
				f=='H' ? time.getHours() :
				f=='I' ? (time.getHours() % 12) || 12 :
				f=='m' ? time.getMonth()+1 :
				f=='M' ? zero_pad(time.getMinutes()) :
				f=='p' ? (time.getHours()<12 ? 'AM' : 'PM') :
				f=='S' ? zero_pad(time.getSeconds()) :
				f=='x' ? time.toString() :
				f=='X' ? time.toTimeString() :
				f=='y' ? time.getYear() % 100 :
				f=='Y' ? time.getFullYear() :
				f;
		};
		return (fmt || '%c').replace(/%(.)/g, callback);
	},
	nth_word: function(str, expr)
	{	var arr=str.split(/\s+/), arr2=[], arr3=[];
		expr = expr.replace(/[^\d\+\-\*\/Nn]/g, '').replace(/(\d)[Nn]/g, '$1*n').replace(/[Nn](\d)/g, 'n*$1').substr(0, 64);
		try
		{	for (var n=0; n<arr.length*2; n++)
			{	var res = eval(expr.replace(/[Nn]/g, n));
				if (res>0 && res<=arr.length) arr2[res-1] = true;
			}
			for (n=0; n<arr.length; n++) if (arr2[n]) arr3.push(arr[n]);
			str = arr3.join(' ');
		}
		catch (e)
		{
		}
		return str;
	},
	/*get_html_ids: function(container_ids)
	{	var html_ids = [];
		for (var i=0; i<container_ids.length; i++)
		{	for (var html_id in this.containers)
			{	if (container_ids[i] == this.containers[html_id].id)
				{	html_ids[html_ids.length] = html_id;
				}
			}
		}
		return html_ids;

	},*/
	get_html_ids_of_action: function(action_id)
	{	var html_ids = [];
		for (var html_id in this.containers)
		{	var c = this.containers[html_id];
			for (var i=0; i<c.ac.length; i++)
			{	if (c.ac[i] == action_id)
				{	html_ids[html_ids.length] = html_id;
					break;
				}
			}
		}
		return html_ids;

	},
	get_elems_of_action: function(action_id, default_to_body)
	{	var ids = _S_T.get_html_ids_of_action(action_id);
		if (ids.length == 0)
		{	return default_to_body ? [document.body || document.documentElement] : [];
		}
		return _S_T.id(ids.join(','), true);
	},
	compose_url: function(url_parts)
	{	var href = url_parts.href;
		if (!href)
		{	var getParam = function(param, ensurePrefix) {
				var part = url_parts[param];

				if (!part) {
					return location[param];
				}

				if (ensurePrefix && part.charAt(0)!=ensurePrefix) {
					part = ensurePrefix + part;
				}

				return part;
			};

			href = getParam('protocol') + '//' + getParam('host') + getParam('pathname', '/') + getParam('search', '?') + getParam('hash', '#');
		}
		return href;
	},
	redirect: function(a, rid, url_parts, throw_error)
	{	var href = this.compose_url(url_parts);
		if (location.href != href) {
			_S_T.occured(-1, a, 3, 0, rid, 3);
			location.href = href;
			return true;
		}
		if (throw_error) throw new Error("Tried to redirect to same URL: "+href);
		return false;
	},
	get_f: function()
	{	return this.cookie_obj('stat_track_u_id').f || 0;
	},
	set_f: function(f)
	{	var old_f = this.get_f();
		this.cookie_obj('stat_track_u_id', {f:Math.max(f, old_f)}); // 2 sites with 2 different server_ids that reside on the same 2nd-level domain can steal cookie from each other including factor. This can cause to eternal _S_T.load_libs('index')
		setTimeout // let the new cookie be applied
		(	function()
			{	if (old_f && old_f<f)
				{	_S_T.filter_a = {};
					_S_T.act_params = {};
					_S_T.load_libs('index'); // this will call _S_T.install() to set new containers and other stuff
				}
			},
			1000 // safer value in case of eternal loop
		);
	},
	set_rid: function(rid) {
		_S_T._rid = rid;
	},
	get_visit_id: function() {
		return _S_T._rid || 0;
	},
	set_page_groups: function(gs)
	{	_S_T.page_groups = gs;
	},
	page_in_group: function(g)
	{	for (var i=0; i<_S_T.page_groups.length; i++) if (_S_T.page_groups[i] == g) return true;
		return false;
	},
	SessCnt: function(cookie_prop) // sessions countdown
	{	this.get = function()
		{	var str = _S_T.cookie_obj('stat_track_u_id')[cookie_prop] || '';
			var obj = {};
			str.replace(/(\d+):([\+\-]?\d+)/g, function($0, $1, $2) {obj[$1] = {remain_sessions:parseInt($2), match_again:$2.charAt(0)=='+'}});
			return obj;
		};
		this.set = function(obj, dec) // dec - decrement all counters (practical when starting a new session)
		{	if (!obj) obj = this.get();
			var str = '';
			for (var i in obj)
			{	if (dec && obj[i].remain_sessions!=0 && --obj[i].remain_sessions<=0) // nonzero counter reached zero
				{	if (!obj[i].match_again)
					{	obj[i].remain_sessions = -1; // -1 indicates "cannot be matched in future"
					}
					else
					{	continue;
					}
				}
				if (parseInt(i) == i) str += i+':'+(obj[i].match_again ? '+' : '')+obj[i].remain_sessions+',';
			}
			str = str.substr(0, str.length-1);
			var set_cookie = {};
			set_cookie[cookie_prop] = str;
			_S_T.cookie_obj('stat_track_u_id', set_cookie);
			return str;
		};
		this.clear = function(arr)
		{	var obj = this.get();
			for (var i=0, j=arr.length; i<j; i++)
			{	delete obj[arr[i]];
			}
			this.set(obj);
		};
		this.add = function(obj, override)
		{	var cur_obj = this.get();
			for (var i in obj)
			{	if (override || !(i in cur_obj))
				{	cur_obj[i] = obj[i];
				}
			}
			this.set(cur_obj);
		};
	},
	set_meaningful_conds: function(conds)
	{	this.conds = conds;
		// add sticky conditions
		var obj = {};
		for (var i in conds)
		{	if (conds[i]) // if is sticky
			{	obj[i.substring(1)] = {remain_sessions:conds[i][0], match_again:conds[i][2]};
			}
		}
		new this.SessCnt('sy').add(obj);
	},
	get_conditions: function() // function that other scripts on page can call; returns occured condition IDs - not all, but only that for which there is a container that depends on them, or a page refresh interval, or for which send_to_client is set to true
	{	var conds = [];
		for (var i in this.conds)
		{	conds.push(parseInt(i.substring(1)));
		}
		return conds;
	},
	session_disable_action: function(action_id)
	{	_S_T.disable_action(action_id);
	},
	disable_action: function(action_id, for_n_sessions)
	{	action_id = parseInt(action_id);
		if (action_id > 0)
		{	if ((for_n_sessions || 0) <= 1) // assert(true <= 1); assert(!(undefined <= 1));
			{	for_n_sessions = 1;
			}
			var set_cookie = {};
			set_cookie[action_id] = {remain_sessions:for_n_sessions, match_again:1};
			new this.SessCnt('noacts').add(set_cookie, 1);
		}
	},
	system:
	{	is_on: function()
		{	return _S_T.cookie_obj('stat_track_u_id').off != '1';
		},

		_set: function(on, ondone)
		{	_S_T.load_libs
			(	'index', function()
				{	_S_T.cookie_obj('stat_track_u_id', {off:on ? '' : 1});
					ondone && ondone();
				}
			);
		},

		on: function(ondone)
		{	this._set(1, ondone);
		},

		off: function(ondone)
		{	this._set(0, ondone);
		}
	},
	set_period: function(p)
	{	clearInterval(_S_T._period_timer);
		_S_T._period = p * 1000;
		if (p > 0) _S_T._period_timer = setInterval(function() {_S_T.occured('-3', '', 0, 0, '', 2);}, _S_T._period);
	},
	set_atimes: function(atimes) {
		_S_T._atimes = atimes;
	},
	get_atime: function(a) {
		var _at = this._atimes;
		if (_at) {
			for (var i=_at.length-1; i>=0; --i) {
				if (_at[i][0] == a) return _at[i][1];
			}
		}
		return 0;
	},
	a_closed: function(a, a_type) {
		if (a_type=='image' || a_type=='html') {
			setTimeout(function() {_S_T.retry_html_from_queue.call(_S_T)}, 10);
		}
	},
	retry_html_from_queue: function() {
		var _a = [];
		for (var i=0,len=_S_T._queue.length;i<len;++i) {
			_a[i] = [_S_T._queue[i][0],_S_T._queue[i][1]];
		}
		_S_T.fire_actions(_a, 1);
	},
	add_script: function(scr, srv, tps) {
		_S_T.__scr = scr;
		_S_T.__srv = srv;
		_S_T.__tps = tps;
		var s = document.createElement('script');
		s.src = scr + '?' + Math.random();
		var head = document.getElementsByTagName('head')[0];
		head.appendChild(s);
	},
	want_login_as: function(login_id, login_id_type)
	{	if (login_id && typeof(login_id_type)=='string' && login_id_type.length==2) // e.g. 'IN' - internal, 'FB' - facebook, etc.
		{	if (login_id_type+login_id != _S_T.cookie_obj('stat_track_u_id').li)
			{	_S_T.cookie_obj('_stat_track_s_id', {_li:login_id_type+login_id});
			}
		}
	},
	get_wanted_login_as: function()
	{	return _S_T.cookie_obj('_stat_track_s_id')._li;
	},
	need_query_social: function(login_id_type)
	{	return (','+_S_T.cookie_obj('_stat_track_s_id')._so+',').indexOf(','+login_id_type+',') == -1;
	},
	no_need_query_social: function(login_id_type)
	{	var sid = _S_T.cookie_obj('_stat_track_s_id');
		var so_arr=[login_id_type], so_obj={};
		so_obj[login_id_type] = null;
		(sid._so || '').replace(/\b\w\w\b/g, function($0) {if (!($0 in so_obj)) {so_arr.push($0); so_obj[$0]=null}});
		if (so_arr.length < 20) _S_T.cookie_obj('_stat_track_s_id', {_so:so_arr.join(',')});
	},
	social: function(login_id_type, data)
	{	if (login_id_type=='IN' || this.need_query_social(login_id_type))
		{	if (login_id_type != 'IN')
			{	this.no_need_query_social(login_id_type);
			}
			data.login_id_type = login_id_type;
			var data_arr=[], data_len=0;
			for (var i in data)
			{	if (typeof(data[i])=='number' || typeof(data[i])=='string')
				{	var item = (data[i]+'').substr(0, 200);
					if (item)
					{	item = i+'='+encodeURIComponent(item);
						data_len += item.length;
						if (item.replace(/\W/g, ' ').match(/\bid\b/i))
						{	this.want_login_as(item, login_id_type);
						}
						if (data_len > 2500) break;
						data_arr.push(item);
					}
				}
			}
			_S_T.occured('-4', data_arr.join('&'), 1, 0, 0, 2);
		}
	},
	agent: function()
	{	if (this.isIE) return 'msie';
		if (navigator.userAgent.indexOf('Gecko')!=-1 || navigator.userAgent.indexOf('Firefox')!=-1) return 'moz';
		if (navigator.userAgent.indexOf('WebKit')!=-1 || navigator.userAgent.indexOf('Safari')!=-1) return 'webkit';
		return 'default';
	},
	get_js_url: function(js_filename)
	{	if (js_filename == 'index')
		{	js_filename = this.agent()+'/'+js_filename;
		}
		var factor = this.get_f();
		var url = '//d34v2lkyplcbk7.cloudfront.net/js';
		if (!factor)
		{	factor = 1000000+Math.floor(Math.random()*1000000);
							url = '//counter.personyze.com/js';
					}
					return url+'/'+this.server_id+'/'+js_filename+'-'+factor+'.js';
			},
	get_action_url: function(js_filename)
	{				return '//d34v2lkyplcbk7.cloudfront.net/actions'+'/'+this.agent()+'/'+js_filename+'-'+this.get_f()+'.js';
			},
	load_libs: function(js_filenames, onload, onerror, niter)
	{	var to_load = [];
		if (js_filenames)
		{	if (!js_filenames.join)
			{	js_filenames = [js_filenames];
			}
			for (var i=0; i<js_filenames.length; i++)
			{	if (js_filenames[i] == 'index')
				{	if (!_S_T.domains)
					{	to_load[to_load.length] = js_filenames[i];
					}
				}
				else
				{	if (!_S_T[js_filenames[i]>0 ? 'act_params' : 'act'][js_filenames[i]])
					{	to_load[to_load.length] = js_filenames[i];
					}
				}
			}
		}
		if (to_load.length == 0)
		{	onload && onload();
		}
		else
		{	if (!niter)
			{	for (var i=0; i<to_load.length; i++)
				{	_S_T.script_load(_S_T[to_load[i]>0 || to_load[i]=='index' ? 'get_js_url' : 'get_action_url'](to_load[i]));
				}
				niter = 0;
			}
			if (niter < 3000)
			{	setTimeout
				(	function()
					{	_S_T.load_libs(to_load, onload, onerror, niter+1);
					},
					20
				);
			}
			else
			{	window.console && console.log('load_libs: files couldn\'t be loaded: '+to_load.join(', '));
				onerror && onerror();
			}
		}
	},
	setup: function(server_id)
	{	if (!this.server_id)
		{	this.server_id = server_id;
			if (this.system.is_on())
			{	for (var i=document.styleSheets.length-1; i>=0; i--)
				{	if (document.styleSheets[i].title == '-S-T-L')
					{	// async load
						this.async = true;
						break;
					}
				}
				if (this.async)
				{	this.load_libs('index');
					return;
				}
				document.write('<script type="text/javascript" src="', this.get_js_url('index'), '"><\/script>');
			}
		}
	},
	block_action: function(action_id, is_attached)
	{			if (this.blocks)
		{	this.blocks[action_id] = is_attached ? 2 : 1;
		}
	},
	unblock_action: function(action_id)
	{			if (this.blocks)
		{	delete this.blocks[action_id];
		}
	},
	unblock_all: function(force)
	{			if (force || this.blocks && !this.keys(this.blocks).length)
		{	for (var i=0; i<document.styleSheets.length; i++)
			{	try
				{	var style = document.styleSheets[i];
					var rules = style.cssRules || style.rules;
					if (rules && rules[0].selectorText)
					{	var selectorText = rules[0].selectorText.toUpperCase();
						if (selectorText.indexOf('#-S-T-H') == 0)
						{	document.styleSheets[i].disabled = true;
							this.blocks = null;
							return;
						}
					}
				}
				catch (e)
				{
				}
			}
			if (force)
			{	setTimeout('_S_T.unblock_all(1)', 5000);
			}
		}
	},
	pre_init_containers: function(actions_qelem_ids)
	{	/* hide initial content of containers and try to set style before containers become visible on page */
		var stylesheet='', stylesheet_hide='';
		for (var html_id in this.containers)
		{	var c = this.containers[html_id];
			if (((c.tp) & 1))
			{	var style = c.a==null ? c.em : c.oc;
				if (html_id.charAt(0)!='#' && html_id.charAt(0)!='.') html_id = '#' + html_id;
				for (var s in style)
				{	if (typeof(style[s]) != 'function')
					{	stylesheet += html_id+' {'+s+':'+style[s]+'}\n';
					}
				}
				stylesheet_hide += ', ' + html_id;
			}
		}
		// actions_qelem_ids
		for (var i=0; i<actions_qelem_ids.length; i++)
		{	stylesheet_hide += ', ' + this.qelem_id_to_css(actions_qelem_ids[i]);
		}
		// write
		document.write('<style>'+stylesheet+'</style><style>#-S-T-H'+stylesheet_hide+' {display:none !important}</style>');
	},
	reg_unblock: function()
	{	_S_T.reg_onready
		(	function()
			{					if (_S_T.blocks)
				{	for (var action_id in _S_T.blocks)
					{	if (_S_T.blocks[action_id] != 2)
						{	delete _S_T.blocks[action_id];
						}
					}
					_S_T.unblock_all();
				}
			}
		);
	},
	reg_static_script: function(url, content)
	{	if (!this.async)
		{	if (url)
			{	document.write('<script src="'+_S_T.htmlspecialchars(url)+'"></script>'); // this blocks rendering (good)
			}
			if (content)
			{	if (typeof(content) != 'function')
				{	document.write('<script>'+content+'</script>');
				}
				else
				{	var func_id = ''+Math.random();
					_S_T.temp_funcs[func_id] = content;
					document.write('<script>_S_T.temp_funcs["'+func_id+'"](); delete _S_T.temp_funcs["'+func_id+'"]</script>');
				}
			}
		}
		else
		{	if (url)
			{	_S_T.script_load(url);
			}
			if (content)
			{	if (typeof(content) != 'function')
				{	eval(content);
				}
				else
				{	content();
				}
			}
		}
	},
	install: function(new_f, is_immediate, containers, domains, actions_pagegroups, embedded_act_params, actions_qelem_ids)
	{	this.set_conts(containers, domains);
		var post_set_factor = this.cookie_obj('stat_track_u_id').f;
		if (post_set_factor && new_f!=post_set_factor)
		{	is_immediate = 1;
		}
		if (this.async)
		{	is_immediate = 0;
		}
		for (var i in embedded_act_params)
		{	this.act_params[i] = embedded_act_params[i];
		}
		if (new_f) this.set_f(new_f); // this operation sets cookie, so must come after domains are set
		this.actions_pagegroups = actions_pagegroups;
		if (!this.ready)
		{	this.install_focus();
			this.iframe(1, is_immediate);
			if (is_immediate)
			{	this.pre_init_containers(actions_qelem_ids);
				document.write('<script>_S_T.isIE ? _S_T.reg_unblock() : _S_T.unblock_all()</script>'); // _S_T.iframe(1) emitted <script src="stat-track-log-visit.js.php?..."></script>. That script calls _S_T.log_visit(), which calls _S_T.fire_actions(), which puts data to containers. Right after he's finished i want to execute _S_T.unblock_all().
				setTimeout('_S_T.unblock_all(1)', 5000);
			}
		}
	},
	log_visit: function(new_f, rid, user_data, period, page_groups, conds, actions, action_times, client_cookie, clear_conds)
	{			// override actions and conditions
		var override = this.get_param("_S_T");
		if (window._S_T_ACTIONS_DISABLED)
		{	actions = [];
		}
		else if (override)
		{	var override_actions = [rid];
			var arr = override.split(',');
			for (var i=0; i<arr.length; i++)
			{	var what = arr[i].charAt(0);
				var data = arr[i].substring(1);
				if (what == 'a')
				{	override_actions.push(data);
				}
			}
			// add overrided
			if (override_actions.length > 1)
			{	actions.push(override_actions);
			}
		}
		// process received data
		for (var i=0; i<this.occured_queue.length; i++)
		{	var q = this.occured_queue[i];
			this.occured.apply(this, q);
		}
		this.occured_queue = [];
		this.set_f(new_f);
		if (rid) this.set_rid(rid);
		this.set_user_data(user_data);
		if (period != null) this.set_period(period);
		if (page_groups) this.set_page_groups(page_groups);
		if (conds) this.set_meaningful_conds(conds);
		if (client_cookie) this.set_client_cookie(client_cookie.st, client_cookie.ls, client_cookie.sy);
		if (clear_conds && clear_conds.length) new this.SessCnt('sy').clear(clear_conds);
		if (action_times != null) this.set_atimes(action_times);
		if (!this.block_queue)
		{	this.block_queue = new _S_T.Queue;
		}
		this.fire_actions(actions, 0, this.block_queue.add());
				this.block_queue.wait(_S_T.reg_unblock);
		this.init_page_events();
		this.reg_onready(function(){_S_T.init_containers()});
		if (!this.ready)
		{	for (var s=document.styleSheets, i=s.length-1; i>=0 && s[i].title!='-S-T-L'; i--);
			if (i >= 0)
			{	this.reg_onready(function(){s[i].disabled = true});
			}
			this.ready = true;
			this.async = true;
		}
	},
	error_response: function(msg)
	{	window.console && console.log('Stat Track: '+msg);
	}
}

