/**
 * Pluginy jQuery uzywane w MP
 * @author  Krzysztof Kotowicz <kkotowicz at mp dot pl>
 * @version $Id$
 */

(function($){
 $.mpProcessFormResults = function (json, options) {

    /* Default settings */
    var settings = {
       result: '.result',
       error_class: 'inline_error',
       form: 'form'
    };

    /* Processing settings */
    settings = jQuery.extend(settings, options || {});

    if (json._redirect) {
        window.location = json._redirect;
        return;
    }

    $(settings.result).mpShowResult(json.msg, json.error);
    $(settings.form).mpShowErrors(json.form_errors || {}, settings);
 };

 $.unserialize = function (url) {
    if (url.match(/\?(.+)$/)) {
        // in case it is a full query string with ?, only take everything after the ?
        url = RegExp.$1;
    }

    // split the params
    var pArray = url.split("&");
    // hash to store result
    var pHash = {};
    // parse each param in the array and put it in the hash
    for (var i=0; i < pArray.length; i++) {
        var temp = pArray[i].split("=");
        pHash[temp[0]] = unescape(temp[1]);
    }
    return pHash;
 };
})(jQuery);

jQuery.fn.mpShowErrors = function(errors, options) {
    /* Default settings */
    var settings = {
       error_class: 'inline_error'
    };

    /* Processing settings */
    settings = jQuery.extend(settings, options || {});

    return this.each(function() {
        // remove previous errors
        $(this).find('.'+settings.error_class).add('br.removeme').remove();

        var self = this;

        $.each(errors, function(key, values) {
            var error_message = '';

            $.map(values, function(value) { error_message += value + "<br />"});

            $(':input[name="' + key + '"]', self).after('<br class="removeme" /><span id="' + key + '_error" class="' + settings.error_class + '">' + error_message + "</span>");
        });
    });

};

jQuery.fn.mpShowResult = function (text, isError, options) {
    /* Default settings */
    var settings = {
    };

    /* Processing settings */
    settings = jQuery.extend(settings, options || {});

    if (isError == undefined)
       isError = false;

    return this.each(function() {
        if (isError) {
            jQuery(this).hide().text(text).addClass('errormsg').removeClass('okmsg').show();
        } else {
            jQuery(this).hide().text(text).removeClass('errormsg').addClass('okmsg').show();
        }
    });
};

/**
 * Przypina do podanych <a href=""> event wysylajacy AJAXem POSTa na podany adres
 * Po uzyskaniu z serwera odpowiedzi w formacie JSON wyswietla sie komunikat
 * oraz opcjonalnie zostaje wykonana funkcja ok_callback
 */
jQuery.fn.mpConvertToAjaxPost = function (options) {

    var settings = {
        'confirm': "Na pewno?",
        'result': '#result',
        'ajax_in_progress_class': 'ajax_processing', // class to add/remove from anchors while ajax call is in progress
        'ok_callback': false, // function(json, anchor) {}
        'before_callback': false // function() { // this == anchor }
    };

    /* Processing settings */
    settings = jQuery.extend(settings, options || {});

    return this.click(function() {

        // send delete link through post
        if (!settings.confirm || confirm(settings.confirm)) {
            var anchor = this;
            // wysylamy posta na adres this.href, z danymi w POSTcie takimi, jak w URLu
            // serwer powinien zwrocic json w formacie mpShowResult()

            var post_callback = function(json) {

                if (json._redirect) {
                    window.location = json._redirect;
                    return;
                }

                $(settings.result).mpShowResult(json.msg, json.error);

                if (settings.ajax_in_progress_class) {
                    $(anchor).removeClass(settings.ajax_in_progress_class);
                }

                if (!json.error && settings.ok_callback) {
                    // wywolaj ok_callback dajac za parametry json oraz achor
                    settings.ok_callback.apply(this, [json, anchor]);
                }
            };

            if (settings.before_callback) {
                settings.before_callback.apply(this);
            }

            if (settings.ajax_in_progress_class) {
                $(this).addClass(settings.ajax_in_progress_class);
            }

            $.post(this.href, $.unserialize(this.href), post_callback, 'json');
        }

        return false;
    });
};

jQuery.fn.showAndEnable = function() {
    return this.find(':input').attr('disabled','').end().show();
}

jQuery.fn.hideAndDisable = function() {
    return this.hide().find(':input').attr('disabled','disabled').end();
}

/**
 * @author Klaus Hartl
 * @author modified by Krzysztof Kotowicz <koto at webworkers dot pl>
 * @see http://groups.google.com/group/jquery-ui/browse_thread/thread/c728b8464f669674/711a7b0dd4236190?lnk=gst&q=tabs+links+ajax#711a7b0dd4236190
 * @param fun function to always call after hijacking (will be run in the same context as hijack())
 */
jQuery.fn.hijack = function(fun) {
    var target = this;

    return this
        .find('a:not(.nohijack)').click(function(event) {

           if (event.isDefaultPrevented())
               return false;

           $(target).load(this.href, function() {
               $(this).hijack(fun);
               if (jQuery.isFunction(fun)) {
                 fun.call(this);
               }

           });

           return false;
        })
        .end()
        .find('form:not(.nohijack)')
            .hijackForm(target, fun)
        .end();
};

jQuery.fn.hijackForm = function(target, afterLoadFunction) {

    if (!jQuery.fn.ajaxForm) {
        return this;
    }

    return $(this).ajaxForm({
            target: target,
            beforeSubmit: function(fdata, jqForm, options) {
                if (jqForm.data('skip')) { // some submit handler (validation method?) told us to stop
                    jqForm.data('skip', false); // clear
                    return false;
                }
            },
            success: function() {
                var $target = $(target);
                $target.hijack(afterLoadFunction);

                if (jQuery.isFunction(afterLoadFunction)) {
                    afterLoadFunction.call($target);
                }
            }
    });
};

jQuery.fn.showAjaxDialog = function(dialog_opts) {
    return this.each(function() {
        var self = this;
        // try url passed in options
        var url = dialog_opts && dialog_opts.url ? dialog_opts.url : undefined;

        // try object's href
        if (!url)
            url = self.href ? self.href : undefined;

        // if object is inside form, try its action
        if (!url) {
            // object to serialize = myself or my form
            var serial = self.action ? self : (self.form ? self.form : undefined);
            if (serial) {
                url = serial.action ? (serial.action + (serial.action.indexOf("?") == -1 ? "?" : "&" ) + $(serial).serialize()) : undefined;
            }

        }
        $('#ajax-action').remove();
        $("<div id='ajax-action'>").hide().appendTo('body');
        $('#ajax-action').load(url,
            function(response, status, xhr) {
                if (status == "error") {
                    var msg = "Wystąpił błąd podczas ładowania " + url;
                    if (xhr.status) {
                        msg += "\n"+xhr.status + " " + xhr.statusText;
                    }
                    alert(msg);
                } else {
                    $(this).hijack();
                    $(this).dialog(dialog_opts);
                }
            }
        );
    });
}

jQuery.fn.showAction = function(onhide) {

  return this.each(function() {
      var $div = $('<div class="jqmWindow">Loading...</div>')
        .appendTo('body')
        .jqm({

             // will load initial form via GET
             ajax: this.href ? this.href : (this.action + (this.action.indexOf("?") == -1 ? "?" : "&" ) + $(this).serialize()),
             ajaxMethod: this.method,
             modal: true,
             toTop: true,
             onLoad: function() {
                 $(this).hijack( // passing additional function to hijack()

                     function() { // function reassigns close dialog buttons on jqModal subsequent requests
                         var $self = $(this);
                         $(this).find('.jqmClose').click( function() {
                             $self.jqmHide();
                         });

                     }
                 );
             },
             onHide: function(hash) {
                 hash.o.remove(); // remove overlay
                 hash.w.remove(); // remove jqModal object (will not be reused)
                 if (jQuery.isFunction(onhide)) {
                     onhide.call(hash);
                 }
             }
        })
        .jqmShow(); // show dialog at once
  });
};


