﻿/*!
 * CDI data functions
 * version 1.90 (12/15/2009)
 * NO license granted to any party.  
 */

/**
 *  Core functions for CDI Foundation based services.
 *  Replaces functions in cdi.data.js (version 2.0 will fully replace)
 *  REQUIRES: jQuery.
 *  Special Thanks to: 
 *      Albion Research Ltd.  (various ideas on coding from postings from Albion)
 *      West-Wind.com  (many ideas on coding from postings from Rick Stahl)
 */
 
 /* *** DEFAULT VALUES *** */

// pwd rule = min len=6, 1 number, 1 character, no <
//  lookahead regx
 var pwdregx = "^.*(?=.{6,})(?=.*[\\d])(?=.*[a-zA-Z])(?!.*[\\s])(?!.*[<]).*$";
 var pwdregxobj = /^.*(?=.{6,})(?=.*[\\d])(?=.*[a-zA-Z])(?!.*[\\s])(?!.*[#])(?!.*[<])(?!.*[%])(?!.*[&]).*$/;

 var _tmplCache = {} 
 var _ls = 0;
 /* *** AJAX JSON FUNCTIONS *** */
 
    function cdiGetJSON(url, data, callback, ondone) {
        $.ajax({
            type: "POST",
            url: url,
            data: data,
            contentType: "application/json; charset=utf-8",
            dataType: "json",
            success: function(rtnmsg) {
                    var _data = rtnmsg.hasOwnProperty("d") ? rtnmsg.d : rtnmsg;
                    if (callback!=null) {callback(_data);}
                },
            error: null,
            complete: function() { if (ondone !=null) {ondone();}}
        });
    } 
    
    function cdiGetJSONOptionList(url, data, valuefield, namefield, showNone) {
        var rtn = "";
        $.ajax({
            type: "POST",
            async: false,
            url: url,
            data: data,
            contentType: "application/json; charset=utf-8",
            dataType: "json",
            success: function(rtnmsg) {
                    var _data = rtnmsg.hasOwnProperty("d") ? rtnmsg.d : rtnmsg;
                    rtn = "";
                    if (showNone) {
                        rtn+="<option value=''>(none)</option>";
                    }
                    switch(_data.substring(0,2)) {
                        case "0.": break;
                        case "1.": break;
                        default:
                            var _rtn = eval(_data);
                            for(j=0; j<_rtn.length; j++) {
                                rtn+="<option value='"+eval(_rtn[j])[valuefield]+"'>"+eval(_rtn[j])[namefield]+"</option>";
                            }
                            break;
                    }   // end switch
                },
            error: null
        });
        return rtn;
    }

    $.fn.extend({
        cdiFloat: function() {
            // we have to append and THEN set css etc. because we have to find rendered width etc.
            $(this).appendTo(document.body);
            var _docw = $(document).width();
            var _doch = $(window).height();
            var _thisw = $(this).width();
            var _thish = $(this).height();
            $(this).css({zIndex: 49, opacity: 0.9, position: "absolute", left: (_docw-_thisw)/2, top: (_doch-_thish)/2});
            return $(this);
        }
    });

    $.fn.extend({
        cdiSetSelectValues: function() {
            jQuery(".cdiui-select", this).each(function(i,_obj) { $(_obj).val($(_obj).attr("selvalue")); });
            return $(this);
        }
    });

    $.fn.extend({
        cdiSetDefaultValues: function() {
            jQuery(":input", this).each(function(i,_obj) { $(_obj).val($(_obj).attr("defaultvalue")); });
            return $(this);
        }
    });

   
    $.fn.extend({
        cdiBindCommand: function(pSelector, pAction, pFunction) {
            jQuery(pSelector, this).each(function(i,_obj) { 
                $(_obj).unbind(pAction).bind(pAction, function() {pFunction(_obj)});
                });
            return $(this);
        }
    });


    function cdiDoCommand(pObj, pReturn, pValidate) {
        var ctrlid = $(pObj).attr("ctrlid");
        if (ctrlid=="") {ctrlid = $(pObj).parent().attr("ctrlid");}
        var cmd = $(pObj).attr("command")
        var svccmd = $("#"+ctrlid).attr("service")+"/"+cmd;
        var datacmd = $(pObj).attr("datamode");
        var data;
        if (pValidate!=null && pValidate!="undefined" && pValidate==true)
        {
            if (!cdiValidationOkForAction("#"+ctrlid+" .databody")) {return false;}
        }
        switch (datacmd) {
            case "serialize":
                var _rgx = new RegExp("'", "g");
                var _rgx2 = new RegExp("%22", "g");
                serialized = $("#"+ctrlid+" .databody :input").serialize().replace(_rgx, "%27");
                //serialized = encodeURIComponent("#"+ctrlid+" .databody :input").serialize();
                serialized = serialized.replace(_rgx2, "%27");
                data = "{inbound: '"+ serialized  +"'}";
                break;
            case "raw":
                data = $(pObj).attr("data");
                break;
            case "inbound":
                data = "{inbound: '"+$(pObj).attr("data")+"'}";
                break;
        }
        $("#"+ctrlid+" .doinprocess").show();
        $("#"+ctrlid+" .doresult").html("");
        var returnmsg = "";
        cdiGetJSON(svccmd, data, 
            function(rtnmsg) {
                returnmsg = rtnmsg;
                if (rtnmsg==null || rtnmsg=="undefined") {
                }
                else {
                    switch(rtnmsg.substring(0,2)) {
                        case "0.":
                            $("#"+ctrlid+" .doresult").html(rtnmsg.substring(2)).addClass("cdiui-result-failure").removeClass("cdiui-result-success");
                            break;
                        case "1.":
                            $("#"+ctrlid+" .doresult").html(rtnmsg.substring(2)).addClass("cdiui-result-success").removeClass("cdiui-result-failure");
                            break;
                        default: 
                            if (rtnmsg.length<12) { // not a dataset
                                $("#"+ctrlid+" .doresult").html((parseInt(rtnmsg)=="NaN") ? "Failed" : "Success");
                            }
                            break;
                    }   // end switch on rtnmsg
                    if (pReturn!=null && pReturn!="undefined") {pReturn(rtnmsg);}
                }// end if rtnmsg=null
            },
            function() {$("#"+ctrlid+" .doinprocess").hide(); }
        );
    }


/* Micro-templating (foundation 1.0 uses different.  Foundation 2.0 uses Micro-templating)
/* credit: west-wind.com
/* thanks Rick Stahl!
*/

this.parseTemplate = function(str, data) {
    /// <summary>
    /// Client side template parser that uses &lt;#= #&gt; and &lt;# code #&gt; expressions.
    /// and # # code blocks for template expansion.
    /// NOTE: chokes on single quotes in the document in some situations
    ///       use &amp;rsquo; for literals in text and avoid any single quote
    ///       attribute delimiters.
    /// </summary>    
    /// <param name="str" type="string">The text of the template to expand</param>    
    /// <param name="data" type="var">
    /// Any data that is to be merged. Pass an object and
    /// that object's properties are visible as variables.
    /// </param>    
    /// <returns type="string" />  
    var err = "";
    try {
        var func = _tmplCache[str];
        if (!func) {
            var strFunc =
            "var p=[],print=function(){p.push.apply(p,arguments);};" +
                        "with(obj){p.push('" +
            str.replace(/[\r\t\n]/g, " ")
               .replace(/'(?=[^#]*#>)/g, "\t")
               .split("'").join("\\'")
               .split("\t").join("'")
               .replace(/<#=(.+?)#>/g, "',$1,'")
               .split("<#").join("');")
               .split("#>").join("p.push('")
               + "');}return p.join('');";
            //alert(strFunc);
            func = new Function("obj", strFunc);
            _tmplCache[str] = func;
        }
        return func(data);
    } catch (e) { err = e.message; }
    return "< # ERROR: " + err + " # >";
}



    function cdiGetRegXParts(pRegEx) {
        var part = new Array();
        $.each(pRegEx.toString().split('(?'),
            function(i, curval) {
                if (curval != "^.*") { // if not first part (which gets split off)
                    part.push({ exp: "^(?" + curval,
                        msg: ((curval.indexOf("6,") > -1)) ? "min length"
                            : (curval.indexOf("\\d") > -1) ? "numbers"
                            : (curval.indexOf("\\W") > -1) ? "symbols"
                            : (curval.indexOf("[a-zA-Z]") > -1) ? "letter"
                            : (curval.indexOf("!.*[\\s]") > -1) ? "no spaces"
                            : (curval.indexOf("!.*[#]") > -1) ? "no #"
                            : (curval.indexOf("!.*[<]") > -1) ? "no <"
                            : (curval.indexOf("!.*[%]") > -1) ? "no %"
                            : (curval.indexOf("!.*[&]") > -1) ? "no &" : "other"
                    });
                } // end if
            } // end func inside split
        );    // end $.each
        return part;
    }

    function cdiLiveValidatePassword(pValue, pCallback, pRegEx) {
        pRegEx = (pRegEx==null || pRegEx=="undefined" || pRegEx=="") ? pwdregx : pRegEx;
        // we first check to see if pass/fail
        var regx = new RegExp(pRegEx);
        this.result = regx.test(pValue);    // set result
        var resultmsg = "";
        if (!this.result) {
            var regxparts = cdiGetRegXParts(pRegEx);
            $.each(regxparts, function(i, curpart) {
                resultmsg += (new RegExp(curpart.exp).test(pValue)) ? "" : curpart.msg + ", ";
            });
        }
        this.resultmsg = resultmsg;
        pCallback(this);
    }

    function cdiGetValidationRegEx(pValidator) {
        switch(pValidator) {
            case "ssn":
                return /^\d{3}-?\d{2}-?\d{4}$/;
                break;
            case "email":
                return /^[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\.)+(?:[A-Z]{2}|com|org|net|edu|gov|mil|biz|info|mobi|name|aero|asia|jobs|museum)$/;
                break;
            case "phone":
                return /^\(?(\d{3})\)?[- ]?(\d{3})[- ]?(\d{4})$/;
                break;
            case "password":    
                return pwdregx;
                break;
            case "money":
                return /^[-+]?\$?[1-9]\d{0,2}(,\d{3})*(\.\d{0,2})?$/;
                break;
            case "decimal":
                return /^[-+]?\d+(\.\d+)?$/;
                break;
            default:
                return pValidator;
                break;
             
        }
        
    }
    function cdiValidate(pThis) {
        var _validator = $(pThis).attr("validator");
        if (_validator==null || _validator=="undefined") {return;}
        // validator can be a regex expression OR a built-in value (from cdiFNGetValidationRegEx)
        var _curval = $(pThis).val();
        var _rslt= false;
        var _param = "";
        if (_validator.substring(0,6)=="length") {_param=_validator.substring(6); _validator="length";}
        switch(_validator) {
            case "emptyphone":
                if (cdiFNIsNullOrEmpty(_curval)) {_rslt=true;}
                else {
                    var _rgx = new RegExp(cdiGetValidationRegEx("phone"));
                    _rslt = _rgx.test(_curval);
                }
                break;
            case "non-empty":
                _rslt = !cdiFNIsNullOrEmpty(_curval);
                break;
            case "length":
                if ( cdiFNIsNullOrEmpty(_curval)) {_rslt = false;}
                else {
                    var _minlen = _param.split("-")[0]; var _maxlen = _param.split("-")[1];
                    _rslt = (_curval.length >= _minlen) && (_curval.length <= _maxlen);
                }
                break;
            default:
                var _rgx = new RegExp(cdiGetValidationRegEx(_validator));
                _rslt = _rgx.test(_curval);
                break;
        }
        if (_rslt) {$(pThis).removeClass("cdiui-validation-failure").addClass("cdiui-validation-success");}
        else {$(pThis).removeClass("cdiui-validation-success").addClass("cdiui-validation-failure"); }
        return _rslt;
    }
    
    function cdiValidationOkForAction(pSelector, callback) { // tests each item in the selector selection for validation failure.
        // we are using a for loop because the $.each loop DOES loop BUT the line immediately following it...
        //  return _result;   is called immediately.
        var _result = true; var _done = false;
        var _ary = $("#"+pSelector+ " .cdiui-validate");
        for (_i = 0; _i<_ary.length; _i++) {
            if (!cdiValidate(_ary[_i])) {_result = false;}
        }
        return _result;
    }


function stringIntersection(string1, string2) {
    var _rtn = "";
    var _shortstring = (string1.length > string2.length) ? string2 : string1;
    var _longstring =  (string1.length > string2.length) ? string1 : string2;
    for(corecounter=0; corecounter < _shortstring.length; corecounter++) {
        _rtn += (_longstring.indexOf(_shortstring.substring(corecounter,corecounter+1))>-1) ? _shortstring.substring(corecounter,corecounter+1) : "";
    }
    return _rtn;
}

function stringContainsAllOf(string1, string2) {
    var _rtn = true; if (string2.length==0) {_rtn=false;}
    for(corecounter=0; corecounter < string1.length; corecounter++) {
        if (string2.indexOf(string1.substring(corecounter,corecounter+1))<0) {_rtn = false;break;}
    }
    return _rtn;
}

function stringContainsOneOf(string1, string2) {
    var _rtn = false;
    for(corecounter=0; corecounter < string1.length; corecounter++) {
        if (string2.indexOf(string1.substring(corecounter,corecounter+1))>-1) {_rtn = true;break;}
    }
    return _rtn;
}



function ShowMoreInfo(pPage) {
    if (pPage=="pgRecreation.html") {
        MagicGo();
    }
    else {
        $("<div class='ui-corner-all cdiui-event' />").load("content_pages/"+pPage+"?x="+(new Date().getTime()))
            .dialog({title: "More Info", width: "600px", position: "top"});
    }
}

function MagicGo() {
    $("#cdiContent").fadeOut(400, function() {
        $("#cdiContent").empty().load("pageCalendar.aspx"
            ,null,               
            function(rt,ts,rqst) {
                $("#Ctab1").tabs("select",3);
                //if (pObj.path.indexOf("#")>-1) {
                //    var _tab = pObj.path.split("#")[1].split("-")[1];
                //    $("#Ctab1").tabs("select",_tab);
                //}
            }
        ).show();
    });
    return false;
}

function MagicGoMap() {
    $("#cdiContent").fadeOut(400, function() {
        $("#cdiContent").empty().load("pagePreserve.aspx"
            ,null, null 
        ).show();
    });
    return false;
}

function cdiRegisterForClass(pObj) {
        var ctrlid = $(pObj).attr("ctrlid");
        if (ctrlid=="") {ctrlid = $(pObj).parent().attr("ctrlid").substring(1);}
        var cmd = $(pObj).attr("command")
        var svccmd = $("#"+ctrlid).attr("service")+"/"+cmd;
        var datacmd = $(pObj).attr("datamode");
        var data;
        switch (datacmd) {
            case "serialize":
                data = "{inbound: '"+ $("#"+ctrlid+" .databody :input").serialize() +"'}";
                break;
            case "raw":
                data = $(pObj).attr("data");
                break;
            case "inbound":
                data = "{inbound: '"+$(pObj).attr("data")+"'}";
                break;
        }
        $("#"+ctrlid+" .doinprocess").show();
        $("#"+ctrlid+" .doresult").html("");
        alert('register for class: '+data);
}


/* *** Feature Handling *** */
/*
    f=family, b=biking, h=hiking, q=equestrian, e=education, p=photography, c=climbing
    1=parking, 2=equestrian parking, w=water avail, w=shelter, m=map board
    r=restrooms, *=highlight 
*/
var cdiVARFeatureList = [{c:"1",t:"Shade"}, {c:"2",t:"Equestrian parking"}, {c:"3", t:"Wheelchair access"},
                            {c: "4",t:"No Bikes"}, {c: "5",t:"No Horses"}, {c: "6",t:"No Dogs"},
                            {c: "7", t: "Benches"},
                            {c: "a",t:"Rocky Surface"}, {c:"b",t:"Biking"}, {c:"c",t:"Climbing"}, {c: "d", t:"Dog"},
                            {c: "e",t:"Sandy Surface"}, {c:"f",t:"Family"}, 
                            {c: "g",t:"Slope <5"},
                            {c:"h",t:"Hiking"}, {c:"i",t:"Information"},
                             {c: "j",t:"Slope >5"}, 
                            {c: "k",t:"Pinch Point"}, {c: "l",t:"Smooth Surface"}, 
                            {c:"m",t:"Map Board"}, 
                            {c: "n",t:"Cross Slope <5"}, {c: "o",t:"Cross Slope >5"}, 
                            {c:"q",t:"Equestrian"}, {c:"r",t:"Restrooms"}, {c:"s",t:"Shelter"}, 
                            {c:"x", t:"Trash"},{c:"w",t:"Water"} 
                            ];
function cdiGetFeatureList(pString, pWithText, pImgSize) {
    flist = "";
    for(jc1=0; jc1<cdiVARFeatureList.length; jc1++) {
        if (cdiContainsFeature(pString, cdiVARFeatureList[jc1].c)) {
            if (pImgSize>0) {
                flist+="<div class='cdiui-feature cdiui-selectablerow' featurecode='"+cdiVARFeatureList[jc1].c+"' style='width:40px;'>";
            }
            else {
                flist+="<div class='cdiui-feature cdiui-selectablerow' featurecode='"+cdiVARFeatureList[jc1].c+"'>";}
            if (pImgSize>0) {
                flist += "<img class='cdiui-feature-img' width="+pImgSize+" height="+pImgSize+ " src='images/icon_feature_"+cdiVARFeatureList[jc1].c+".png'/>";
            }
            else {
                flist += "<img class='cdiui-feature-img'  src='images/icon_feature_"+cdiVARFeatureList[jc1].c+".png'/>";
            }
            if (pWithText) {flist+="<span class='cdiui-feature-text'>"+cdiVARFeatureList[jc1].t+"</span>";}
            flist+="</div>";
        }
    }
    return flist;
}
function cdiGetFeatureListAll(pWithText, pImgSize) {
    var rtn="<div><table><tr>";
    var rowcounter = 0;
    for(jc2=0;jc2<cdiVARFeatureList.length;jc2++) {
        rtn += "<td width='33%' class='cdiui-selectablerow' featurecode='"+cdiVARFeatureList[jc2].c+"'>";
        if (pWithText) {rtn += "<span class='cdiui-feature-text'>"+cdiVARFeatureList[jc2].t+"</span>";}
        rtn += (pImgSize>0) ? "<img style='cdiui-feature-img' width='"+pImgSize+"' src='images/icon_feature_"+cdiVARFeatureList[jc2].c+".png' width='90%' style='margin:3px;' />" 
            : "<img style='cdiui-feature-img' src='images/icon_feature_"+cdiVARFeatureList[jc2].c+".png' width='90%' style='margin:3px;' />";
        rtn += "</td>";
        rowcounter++;
        if (rowcounter>2) {rowcounter=0; rtn+="</tr><tr>";}
    }
    if (rtn.substring(rtn.length-5)!="</tr>") {rtn+="</tr>";}
    rtn+="</table></div>";
    return rtn;
}

function cdiAddFeature(pCurFeatures, pNewFeature) {
    return (pCurFeatures.indexOf(pNewFeature)>-1) ? pCurFeatures : pCurFeatures+pNewFeature;
}

function cdiRemoveFeature(pCurFeatures, pNewFeature) {
    return pCurFeatures.replace(pNewFeature, "");
}


function cdiContainsFeature(pString, pFeature) {
    return stringContainsOneOf(pFeature,pString);
}
/* *** END  Feature Handling *** */


function cdiOpenPage(pTarget, pPage, pInject, pShadow) {
    if (pInject) {
        $("<div/>").appendTo($(pTarget).parent()).load("content_pages/"+pPage+"?x="+(new Date().getTime()), function() {if (pShadow) {(pTarget).parent().parent().parent().parent().removeShadow().dropShadow();}} )}
    else {
        $(pTarget).load("content_pages/"+pPage+"?x="+(new Date().getTime()), 
            function() {if (pShadow) {(pTarget).parent().parent().parent().parent().removeShadow().dropShadow();}}
        );}
}



/*
* Print Element Plugin 1.1
*
* Copyright (c) 2010 Erik Zaadi
*
* Inspired by PrintArea (http://plugins.jquery.com/project/PrintArea) and
* http://stackoverflow.com/questions/472951/how-do-i-print-an-iframe-from-javascript-in-safari-chrome
*
*  jQuery plugin page : http://plugins.jquery.com/project/printElement 
*  Wiki : http://wiki.github.com/erikzaadi/jQueryPlugins/jqueryprintelement 
*  Home Page : http://erikzaadi.github.com/jQueryPlugins/jQuery.printElement 
*  
*  Thanks to David B (http://github.com/ungenio) and icgJohn (http://www.blogger.com/profile/11881116857076484100)
*  For their great contributions!
* 
* Dual licensed under the MIT and GPL licenses:
*   http://www.opensource.org/licenses/mit-license.php
*   http://www.gnu.org/licenses/gpl.html
*   
*   Note, Iframe Printing is not supported in Opera and Chrome 3.0, a popup window will be shown instead
*/
;
(function($){
    $.fn.printElement = function(options){
        var mainOptions = $.extend({}, $.fn.printElement.defaults, options);
        //iframe mode is not supported for opera and chrome 3.0 (it prints the entire page).
        //http://www.google.com/support/forum/p/Webmasters/thread?tid=2cb0f08dce8821c3&hl=en
        if (mainOptions.printMode == 'iframe') {
            if ($.browser.opera || (/chrome/.test(navigator.userAgent.toLowerCase()))) 
                mainOptions.printMode = 'popup';
        }
        //Remove previously printed iframe if exists
        $("[id^='printElement_']").remove();
        
        return this.each(function(){
            //Support Metadata Plug-in if available
            var opts = $.meta ? $.extend({}, mainOptions, $this.data()) : mainOptions;
            _printElement($(this), opts);
        });
    };
    $.fn.printElement.defaults = {
        printMode: 'iframe', //Usage : iframe / popup
        pageTitle: '', //Print Page Title
        overrideElementCSS: null,
        /* Can be one of the following 3 options:
         * 1 : boolean (pass true for stripping all css linked)
         * 2 : array of $.fn.printElement.cssElement (s)
         * 3 : array of strings with paths to alternate css files (optimized for print)
         */
        printBodyOptions: {
            styleToAdd: 'padding:10px;margin:10px;', //style attributes to add to the body of print document
            classNameToAdd: '' //css class to add to the body of print document
        },
        leaveOpen: false, // in case of popup, leave the print page open or not
        iframeElementOptions: {
            styleToAdd: 'border:none;position:absolute;width:0px;height:0px;bottom:0px;left:0px;', //style attributes to add to the iframe element
            classNameToAdd: '' //css class to add to the iframe element
        }
    };
    $.fn.printElement.cssElement = {
        href: '',
        media: ''
    };
    function _printElement(element, opts){
        //Create markup to be printed
        var html = _getMarkup(element, opts);
        var popupOrIframe = null;
        var documentToWriteTo = null;
        if (opts.printMode.toLowerCase() == 'popup') {
            popupOrIframe = window.open('about:blank', 'printElementWindow', 'width=650,height=440,scrollbars=yes');
            documentToWriteTo = popupOrIframe.document;
        }
        else {
            //The random ID is to overcome a safari bug http://www.cjboco.com.sharedcopy.com/post.cfm/442dc92cd1c0ca10a5c35210b8166882.html
            var printElementID = "printElement_" + (Math.round(Math.random() * 99999)).toString();
            //Native creation of the element is faster..
            var iframe = document.createElement('IFRAME');
            $(iframe).attr({
                style: opts.iframeElementOptions.styleToAdd,
                id: printElementID,
                className: opts.iframeElementOptions.classNameToAdd,
                frameBorder: 0,
                scrolling: 'no',
                src: 'about:blank'
            });
            document.body.appendChild(iframe);
            documentToWriteTo = (iframe.contentWindow || iframe.contentDocument);
            if (documentToWriteTo.document) 
                documentToWriteTo = documentToWriteTo.document;
            iframe = document.frames ? document.frames[printElementID] : document.getElementById(printElementID);
            popupOrIframe = iframe.contentWindow || iframe;
        }
        focus();
        documentToWriteTo.open();
        documentToWriteTo.write(html);
        documentToWriteTo.close();
        _callPrint(popupOrIframe);
    };
    
    function _callPrint(element){
        if (element && element.printPage) 
            element.printPage();
        else 
            setTimeout(function(){
                _callPrint(element);
            }, 50);
    }
    
    function _getElementHTMLIncludingFormElements(element){
        var $element = $(element);
        //Radiobuttons and checkboxes
        $(":checked", $element).each(function(){
            this.setAttribute('checked', 'checked');
        });
        //simple text inputs
        $("input[type='text']", $element).each(function(){
            this.setAttribute('value', $(this).val());
        });
        $("select", $element).each(function(){
            var $select = $(this);
            $("option", $select).each(function(){
                if ($select.val() == $(this).val()) 
                    this.setAttribute('selected', 'selected');
            });
        });
        $("textarea", $element).each(function(){
            //Thanks http://blog.ekini.net/2009/02/24/jquery-getting-the-latest-textvalue-inside-a-textarea/
            var value = $(this).attr('value');
            if ($.browser.mozilla) 
                this.firstChild.textContent = value;
            else 
                this.innerHTML = value;
        });
        //http://dbj.org/dbj/?p=91
        var elementHtml = $('<div></div>').append($element.clone()).html();
        return elementHtml;
    }
    
	//http://github.com/erikzaadi/jQueryPlugins/issues#issue/3
    function _getBaseHref(){
		return window.location.protocol + "//" + window.location.hostname + (window.location.port ? ":" + window.location.port : "") + window.location.pathname;
	}
    
        
    function _getMarkup(element, opts){
        var $element = $(element);
        var elementHtml = _getElementHTMLIncludingFormElements(element);
        
        var html = new Array();
        html.push('<html><head><title>' + opts.pageTitle + '</title>');
        if (opts.overrideElementCSS) {
            if (opts.overrideElementCSS.length > 0) {
                for (var x = 0; x < opts.overrideElementCSS.length; x++) {
                    var current = opts.overrideElementCSS[x];
                    if (typeof(current) == 'string') 
                        html.push('<link type="text/css" rel="stylesheet" href="' + current + '" >');
                    else 
                        html.push('<link type="text/css" rel="stylesheet" href="' + current.href + '" media="' + current.media + '" >');
                }
            }
        }
        else {
            $(document).find("link").filter(function(){
                return $(this).attr("rel").toLowerCase() == "stylesheet";
            }).each(function(){
                html.push('<link type="text/css" rel="stylesheet" href="' + $(this).attr("href") + '" media="' + $(this).attr('media') + '" >');
            });
        }
        //Ensure that relative links work
        html.push('<base href="' + _getBaseHref() + '" />');
        html.push('</head><body style="' + opts.printBodyOptions.styleToAdd + '" class="' + opts.printBodyOptions.classNameToAdd + '">');
        html.push('<div class="' + $element.attr('class') + '">' + elementHtml + '</div>');
        html.push('<script type="text/javascript">function printPage(){focus();print();' + ((!$.browser.opera && !opts.leaveOpen && opts.printMode.toLowerCase() == 'popup') ? 'close();' : '') + '}</script>');
        html.push('</body></html>');
        
        return html.join('');
    };
    })(jQuery);

