


function WebcoreUtils()
{
}

/**
 * Stop propagation of event to other containers and push it to the root document for further processing.
 * @param event
 */
WebcoreUtils.pushEventToDocument = function( event )
{
    if( !event )
        event = window.event;

    event.cancelBubble = true;
    if( event.stopPropagation )
        event.stopPropagation();

    //trigger document event handlers to close overlays for example.
    if ( event.type )
        $( document ).trigger( { type: event.type, target: event.target } );
};

/**
 * Deprecated. Use retrieveFocus()
 * @param elemId
 */
WebcoreUtils.setFocus = function( elemId )
{
    var elem = document.getElementById(elemId);
    if (elem)
        elem.focus();
};

WebcoreUtils.popupWindows = {};

/*
 * Opens a popup windows using given parameters and return it
 */
WebcoreUtils.openPopup = function (url, windowName, width, height) {
    var screenReaderInfoElement = $("#webcore_id_window_opened_info");
    if ( screenReaderInfoElement != undefined )
    {
        screenReaderInfoElement.show();
        setTimeout( function()
        {
            screenReaderInfoElement.hide();
        }, 2000 );
    }

    windowManagement.removeWindowId();
    var popupWindow = width == undefined || (windowName && windowName == "_blank") ? window.open(url, windowName) : window.open(url, windowName, "resizable=yes, scrollbars=yes, status=yes, toolbar=no, width=" + width + ", height=" + height);
    if (!popupWindow) // in case of Popup is blocked, return to prevent further errors
        return null;

    try {
        if (width != undefined)
            popupWindow.resizeTo(width, height);
    }
    catch (exception) {
        // the IE blocks resizing of the given popup is already open!
    }

    try {
       popupWindow.focus();
    }
    catch (exception) {
    }

    WebcoreUtils.popupWindows[windowName] = popupWindow;
    windowManagement.restoreWindowId();

    return popupWindow;
};

WebcoreUtils.closePopup = function (windowName) {
    var window = WebcoreUtils.popupWindows[windowName];
    if (window) {
        try {
            window.close();
        }
        catch (exception) {
        }

        delete WebcoreUtils.popupWindows[windowName];
    }
};

WebcoreUtils.replacePopupUrl = function (url, windowName) {
  var window = WebcoreUtils.popupWindows[windowName];
  if (window) {
    try {
      window.location.href = url;
      return true;
    }
    catch (exception) {
    }

    return false;
  }
};

WebcoreUtils.removeElement = function (id) {
    var elem = document.getElementById(id);
    if (elem) {
        elem.parentNode.removeChild(elem);
    }
};

WebcoreUtils.scrollToElement = function( elem, position, force, additionalDistance, speed )
{
    if ( !$(elem).is(":visible") )
        return;
    var windowScrollTop = $( window ).scrollTop();
    var windowHeight = $( window ).height();
    var elemOffset = $( elem ).offset();
    var elemHeight = $( elem ).height();

    if ( !elemOffset || typeof elemHeight == 'undefined' )
        return;

    if ( speed == undefined )
        speed=1000;

    if ( additionalDistance != undefined )
        elemHeight = elemHeight + additionalDistance;

    //isn't before && isn't after
    var isVisible = !force && windowScrollTop < elemOffset.top &&
        (windowScrollTop + windowHeight) > (elemOffset.top + elemHeight);

    //if it isn't visible scroll to ensure visibility
    if( !isVisible || position == "TOP" )
    {
        var scrollToPos;
        if ( position == "TOP" ) {
            scrollToPos = elemOffset.top;
            if (additionalDistance != undefined)
                scrollToPos -= additionalDistance;
        }
        else if ( position == "BOTTOM" )
            scrollToPos = elemOffset.top + elemHeight -windowHeight;
        else
            scrollToPos = elemOffset.top - (windowHeight / 2.0);
        $ ('html, body').animate ({scrollTop: scrollToPos }, speed);
    }
};

WebcoreUtils.installOverlayMessage = function ( parentId, message )
{
    var $e = $( "#" + parentId );
    var overlayId = parentId + "Overlay";
    var parent = document.getElementById( parentId );

    var FuncObj = function ()
    {
        var timerId = null;

        function showFunc ()
        {
            if ( !timerId )
                timerId = WebcoreUtils._showOverlayMessage( parent, overlayId, message, 0 );
            return false;
        }

        function showFuncDelayed()
        {
            if ( !timerId )
                timerId = WebcoreUtils._showOverlayMessage( parent, overlayId, message, 1000 );
            return false;
        }

        function removeFunc()
        {
            WebcoreUtils.removeElement( overlayId );
            if ( timerId )
                window.clearTimeout( timerId );
            timerId = null;
        }

        return {
            showFunc: showFunc,
            showFuncDelayed: showFuncDelayed,
            removeFunc: removeFunc
        }
    };

    var f = new FuncObj();

    $e.bind( "mouseover." + overlayId + ".show", function ()
    {
        f.showFuncDelayed();
    } );
    $e.bind( "click." + overlayId + ".show", function ()
    {
        f.showFunc();
    } );
    $e.bind( "mouseleave." + overlayId + ".close", function ()
    {
        f.removeFunc();
    } );
    $( document ).bind( "click." + overlayId + ".close", function ()
    {
        f.removeFunc();
    } );
};

WebcoreUtils._showOverlayMessage = function( parent, id, message, delay )
{
    var overlayDiv = document.createElement( "div" );
    overlayDiv.setAttribute( "id", id );
    overlayDiv.style.zIndex = "10000"; // make sure that the div is in front of the other elements
    overlayDiv.className = "wc-OverlayMessage";
    overlayDiv.innerHTML=message;
    parent.appendChild( overlayDiv );
    return window.setTimeout( "WebcoreUtils._showOverlayMessageImmediately('" + id + "')", delay );
};

WebcoreUtils._showOverlayMessageImmediately = function( id )
{
    var elem = document.getElementById( id );
    if ( elem )
        elem.style.display = "block";
};

/**
 * Removes hidden field from form of the child.
 */
WebcoreUtils.removeHiddenField = function(childElement, fieldName)
{
    var $childElement = $(childElement);
    var $form = $childElement.is("form") ? $childElement : $(childElement).parents('form:first');
    $form.find("input[name=\'" + fieldName + "\']").remove();
};

/*
 * Add a hidden field to the form.
 */
WebcoreUtils.addHiddenField = function(childElement, fieldName, fieldValue)
{
    var $childElement = $(childElement);
    var $form = $childElement.is("form") ? $childElement : $(childElement).parents('form:first');
    $('<input/>', {type: 'hidden', name: fieldName, value: fieldValue}).appendTo($form);
};

WebcoreUtils.checkCookies = function(msg)
{
    $(document).bind("ready.checkCookies", function() {
        if (!navigator.cookieEnabled)
            alert(msg);
        $(document).unbind("ready.checkCookies");
    } );
};

WebcoreUtils.showMessage = function( messageType, messageKey )
{
    ajaxEngine.sendServerCommand("getMessageDialog",{type:messageType, messageKey: messageKey });
};

WebcoreUtils.showErrorMessage = function( messageKey )
{
    WebcoreUtils.showMessage( "Error", messageKey );
};

WebcoreUtils.retrieveFocus = function (id, position) {
    var elem = $("#" + id);
    if (elem.length == 1 && elem.is(':visible')) {
        var initialTabIndex = elem.attr( "tabindex" );
        elem.attr( "tabindex", "0" );
        WebcoreUtils.scrollToElement(elem, position);
        elem.focus ();
        if ( initialTabIndex == undefined )
            elem.removeAttr( "tabindex" );
        else
            elem.attr( "tabindex", initialTabIndex );
    }
};

WebcoreUtils.isTouchDevice = function() {
    return (('ontouchstart' in window)
        || (navigator.MaxTouchPoints > 0)
        || (navigator.msMaxTouchPoints > 0));
};

WebcoreUtils.getDeviceDetails = function()
{
    var deviceDetails = {};
    deviceDetails.windowWidth = $(window).width();
    deviceDetails.windowHeight = $(window).height();
    deviceDetails.screenWidth = window.screen.width;
    deviceDetails.screenHeight = window.screen.height;
    deviceDetails.userAgent = navigator.userAgent;
    deviceDetails.browserName = $.browser.name;
    deviceDetails.browserVersion = $.browser.version;
    deviceDetails.platform = navigator.platform;
    deviceDetails.touchDevice = WebcoreUtils.isTouchDevice();
    deviceDetails.pdfSupport = WebcoreUtils.isPdfSupport();

    return deviceDetails;
};

WebcoreUtils.getTiming = function( startTime )
{
    if ( startTime == undefined )
        startTime = 0;

    return new Date().getTime() - startTime;
};

WebcoreUtils.formatAmount = function (value, fractionalDigits) {
    if (value != undefined && value != null) {
        value = value.toFixed(fractionalDigits).replace(/(\d)(?=(\d{3})+(?!\d))/g, "$1,"); // beautify
        // now we have something like this: 1,000,765.77
        value = WebcoreUtils.replaceAll(value, ",", "#");
        value = WebcoreUtils.replaceAll(value, ".", webcore.getSettings().locale.decimal);
        value = WebcoreUtils.replaceAll(value, "#", webcore.getSettings().locale.thousand);
    }

    return value;
};

WebcoreUtils.replaceAll = function (str, find, replace) {
    // Regular expressions contain special (meta) characters, and as such it is dangerous to blindly pass an argument 
    // in the find function above without pre-processing it to escape those characters. 
    find = find.replace(/([.*+?^=!:${}()|\[\]\/\\])/g, "\\$1");
    return str.replace(new RegExp(find, 'g'), replace);
};

WebcoreUtils.parseAmount = function (value) {
    if (value != undefined && value != null) {
        value = WebcoreUtils.replaceAll(value, webcore.getSettings().locale.thousand, "");
        value = WebcoreUtils.replaceAll(value, webcore.getSettings().locale.decimal, ".");
        value = parseFloat(value);
    }

    return value;
};

WebcoreUtils.isNumber = function(val)
{
    return !isNaN( val - 0 ) && val !== null && $.trim( val ) !== "" && val !== false;
};

WebcoreUtils.formatDate = function (timeMillis, pattern) {
    if (timeMillis != null && pattern != null) {
        var date = new Date(timeMillis);

        return pattern.replace(/dd|d|MMMM|MMM|MM|M|yyyy|yy|HH|H|mm|m|ss|s/g, function (s) {
            if (s == 'dd') {
                var day = date.getDate();
                return day < 10 ? '0' + day : day;
            }
            if (s == 'd')
                return date.getDate();
            if (s == 'MM') {
                var month = date.getMonth() + 1;
                return month < 10 ? '0' + month : month;
            }
            if (s == 'M')
                return date.getMonth() + 1;
            if (s == 'yyyy')
                return date.getFullYear();
            if (s == 'yy')
                return date.getFullYear().toString().substr(2, 2);
            if (s == 'HH') {
                var hours = date.getHours();
                return hours < 10 ? '0' + hours : hours;
            }
            if (s == 'H')
                return date.getHours();
            if (s == 'mm') {
                var minutes = date.getMinutes();
                return minutes < 10 ? '0' + minutes : minutes;
            }
            if (s == 'm')
                return date.getMinutes();
            if (s == 'ss') {
                var seconds = date.getSeconds();
                return seconds < 10 ? '0' + seconds : seconds;
            }
            if (s == 's')
                return date.getSeconds();
        });
    }
};

WebcoreUtils.createActiveXObject = function (type) {
    try {
        return new ActiveXObject(type);
    } catch (e) {
        // do nothing
    }
    return null;
};

WebcoreUtils.isIE = function () {
    return !!(window.ActiveXObject || "ActiveXObject" in window);
};

WebcoreUtils.isIOS = function () {
    return /iphone|ipad|ipod/i.test(navigator.userAgent.toLowerCase());
};


WebcoreUtils.isPdfSupport = function () {
    if (typeof window === "undefined" || typeof navigator === "undefined")
        return false;

    var supportsPdfMimeType = typeof navigator.mimeTypes['application/pdf'] !== "undefined";

    // If either ActiveX support for "AcroPDF.PDF" or "PDF.PdfCtrl" are found, return true
    var supportsPdfActiveX = function () {
        return WebcoreUtils.createActiveXObject("AcroPDF.PDF") != null || WebcoreUtils.createActiveXObject("PDF.PdfCtrl") != null;
    };

    return supportsPdfMimeType || WebcoreUtils.isIOS() || (WebcoreUtils.isIE() && supportsPdfActiveX());
};

WebcoreUtils.executeUrl = function(url)
{
    var xmlHttpReq = false;
    if (window.XMLHttpRequest)
    {
        xmlHttpReq = new XMLHttpRequest ();
        if (xmlHttpReq.overrideMimeType)
            xmlHttpReq.overrideMimeType ('text/xml');
    }
    else if (WebcoreUtils.isIE()) // IE
    {
        xmlHttpReq = WebcoreUtils.createActiveXObject("Msxml2.XMLHTTP");
        if (xmlHttpReq == null)
            xmlHttpReq = WebcoreUtils.createActiveXObject("Microsoft.XMLHTTP");
    }

    xmlHttpReq.open ("GET", url, false);
    xmlHttpReq.send ("");
};

WebcoreUtils.setWindowUrl = function(url)
{
    window.location= url;
};

// deletes all cookies with the given name
WebcoreUtils.deleteCookieByName = function (name) {
  var cookies = document.cookie.split("; ");
  for (var c = 0; c < cookies.length; c++) {
    var cookieName = cookies[c].split(";")[0].split("=")[0];
    if (cookieName != name)
      continue;

    // first without domain
    var cookieBaseWithoutDomain = encodeURIComponent(cookieName) + '=; expires=Thu, 01-Jan-1970 00:00:01 GMT';
    document.cookie = cookieBaseWithoutDomain;
    document.cookie = cookieBaseWithoutDomain + ' ;path=/';
    var paths = location.pathname.split('/');
    while (paths.length > 0) {
      document.cookie = cookieBaseWithoutDomain + ' ;path=' + paths.join('/');
      paths.pop();
    }
    
    var domains = window.location.hostname.split(".");
    while (domains.length > 0) {
      var cookieBaseWithDomain = cookieBaseWithoutDomain + '; domain=' + domains.join('.');
      document.cookie = cookieBaseWithDomain;
      document.cookie = cookieBaseWithDomain + ' ;path=/';
      paths = location.pathname.split('/');              
      while (paths.length > 0) {
        document.cookie = cookieBaseWithDomain + ' ;path=' + paths.join('/');
        paths.pop();
      }
      domains.shift();
    }
  }
};

WebcoreUtils.disableScrolling = function () {
  // lock scroll position, but retain settings for later
  var scrollPosition = [
    self.pageXOffset || document.documentElement.scrollLeft || document.body.scrollLeft,
    self.pageYOffset || document.documentElement.scrollTop || document.body.scrollTop
  ];
  var html = $('html'); // it would make more sense to apply this to body, but IE7 won't have that
  html.data('scroll-position', scrollPosition);
  html.data('previous-overflow', html.css('overflow'));
  html.css('overflow', 'hidden');
  window.scrollTo(scrollPosition[0], scrollPosition[1]);
};

WebcoreUtils.enableScrolling = function () {
  // un-lock scroll position
  var html = $('html');
  var scrollPosition = html.data('scroll-position');
  html.css('overflow', html.data('previous-overflow'));
  window.scrollTo(scrollPosition[0], scrollPosition[1]);
};

// get the value of the first cookie withe given name
WebcoreUtils.getCookieValue = function (name) {
  var cookies = document.cookie.split("; ");
  for (var c = 0; c < cookies.length; c++) {
    var cookie = cookies[c];
    var cookieNameAndValue = cookie.split(";")[0];
    var cookieName = cookieNameAndValue.split("=")[0];
    var cookieValue = cookieNameAndValue.split("=")[1];

    if (cookieName == name)
      return cookieValue;
  }

  return null;
};

WebcoreUtils.getPopupWidth = function (min, preffered) {
  var screenWidth = WebcoreUtils.getDeviceDetails().screenWidth;
  if ( screenWidth < min )
    return min;
  else // screenWidth >= min
  {
    if ( screenWidth >= min ) {
      if ( screenWidth < preffered )
        return screenWidth;
      else
        return preffered;
    }
  }
};

WebcoreUtils.getPopupHeight = function (min, preffered) {
  var screenHeight = WebcoreUtils.getDeviceDetails().screenHeight;
  if ( screenHeight < min )
    return min;
  else // screenWidth >= min
  {
    if ( screenHeight >= min ) {
      if ( screenHeight < preffered )
        return screenHeight;
      else
        return preffered;
    }
  }
};

$.fn.setCursorPosition = function(position){
    if(this.length == 0) return this;
    return $(this).setSelection(position, position);
};

$.fn.setSelection = function(selectionStart, selectionEnd) {
    if(this.length == 0) return this;
    var input = this[0];

    if (input.createTextRange) {
        var range = input.createTextRange();
        range.collapse(true);
        range.moveEnd('character', selectionEnd);
        range.moveStart('character', selectionStart);
        range.select();
    } else if (input.setSelectionRange) {
        input.focus();
        input.setSelectionRange(selectionStart, selectionEnd);
    }

    return this;
};

$.fn.focusEnd = function(){
    if (!this.val())
      return this;
    this.setCursorPosition(this.val().length);
    return this;
};

$.fn.focusStart = function(){
    this.setCursorPosition(0);
    return this;
};

$(document).ready(function () {
  var body = $("body");

  body.removeClass("TouchDevice");
  body.removeClass("NonTouchDevice");
  if (WebcoreUtils.isTouchDevice())
    body.addClass("TouchDevice");
  else
    body.addClass("NonTouchDevice");

  body.removeClass("WithPDFSupport");
  body.removeClass("WithoutPDFSupport");
  if (WebcoreUtils.isPdfSupport())
    body.addClass("WithPDFSupport");
  else
    body.addClass("WithoutPDFSupport");
});