jquery插件:将函数转换为插件?

Posted

技术标签:

【中文标题】jquery插件:将函数转换为插件?【英文标题】:jquery plugin: converting functions into a plugin? 【发布时间】:2011-07-28 06:04:14 【问题描述】:

我想学写jquery插件,所以我觉得如果把我的函数转换成插件来学习会更容易理解,比如:

这些是我的正常功能,

this.delete_uploaded = function()  

    $(".delete-uploaded").click(function()

        // remove the popup.
        $('#popup_result').remove();

        // same as: var target_delete = $(this).parent().parent().parent();
        var target_delete = $(this).parents('.item-uploaded'); // the item for deletion, such as item held in li 
        var parent_delete = $(this).parents('.items-uploaded'); // the parent that hold delete item, such as ul > li
        var wrapper_parent = $(this).parents('.upload'); // the wrapper that hold the parent, such as div > ul > li
        var target_loadin = $(this).parent();
        var target_html = $(this).parent().html();
        var path_load = $(this).attr('href');

        // make a gif loader.
        target_loadin.html('<img src="'+http_root+rp_image_global+img_loader+'" style="float:none;"/> loading');

        // load the delete form.
        target_loadin.load( path_load, function()

            // when the yes button is triggered.
            $("input[type=submit][name=yes]").click(function()

                // get the path from attribute of action in the form.
                var path_post = $(this).parent('form').attr('action');
                //alert(path_post);

                // make a gif loader.
                target_loadin.html('<div class="ajaxloader"><img src="'+http_root+rp_image_global+img_loader+'" style="float:none;"/> loading</div>');

                // post the form.
                $.post(path_post, $(this).serialize(), function(xml)

                    // procees the form output.
                    process_delete_uploaded(xml);
                );

                // slide up the deleted target.
                target_delete.slideUp('fast', function() 

                    // remove its divs completely
                    target_delete.remove();
                    //alert($('li',parent_delete).length);

                    // count how many items are left behind         
                    if($('li',parent_delete).length == 0)
                    
                        $('.binder-row',wrapper_parent).css(
                            borderBottom: '0px solid #999', 
                            padding: '0px 0px 0px 0px'
                        );
                    

                );

                return false;
            );

            // when the no/cancel button is triggered.
            $("input[type=button][name=no]").click(function()

                // return the html
                target_loadin.html(target_html);

                // reload the delete function
                delete_uploaded();

                return false;
            );

        );

    return false;
    );


// callback function for proccesing the deleted item.
this.process_delete_uploaded = function(xml)

    // append a popup div.
    $(document.body).append("<div id=\"popup_result\" class=\"popup\"></div>");

    var popup = $('#popup_result');
    var width = 400;
    var top = 220;
    var scrollTop = $(window).scrollTop();
    var scrollLeft = $(window).scrollLeft();
    var marginLeft = "-"+ ((scrollLeft + width)/2);

    popup.css(
        top:(scrollTop + top) + "px", 
        left:"50%",
        marginLeft:marginLeft + "px",
        width:width + "px",
        zIndex:"11",
        display:"none"
    );

    // proccess the result and load the result page and display the result messages on the result page.
    popup.load(http_root+rp_cms+"result.php", , function()

        // loop for any error messages.
        $("error", xml).each(function()
            var elementid = $(this).attr('elementid');
            var message = $(this).attr('message');
            $("#"+elementid+"_label").addClass('error');
            $("#"+elementid+"_img").css(visibility:'visible');
            $(".result").append("<img src='"+http_root+rp_image_global+"attention.png' /> <b>" + message + "</b> <br />");
            popup.fadeIn('slow', function()    
                closePopup(popup);
            ); 
        );

        // loop for any positive results.
        $("result", xml).each(function()

            // store the result node.
            var message = $(this).attr('message');
            //alert(message);

            // append the positive messages in the result class.
            $(".result").append("<img src='"+http_root+rp_image_global+"info.png' /> <b>" + message + "</b> <br />");

            // display the messages by fading them in.
            popup.fadeIn('fast', function()

                // set the timeout to 1 minute to remove the popup
                setTimeout(function()
                    popup.fadeOut("slow",function()
                        popup.remove();
                    ); 
                ,1000);    

                // attach closePopup function.
                closePopup(popup);      
            );

        );
    );

我想把它转换成一个插件,这样我就可以像这样实例化它,

$(".delete-uploaded").delete_uploaded(
  target_delete: '.item-uploaded', 
  parent_delete: '.items-uploaded',
  wrapper_parent:'.upload'
)

等等,

 $(".delete-listed").delete_uploaded(
    target_delete: '.item-listed', 
    parent_delete: '.items-listed',
    wrapper_parent:'.upload'
 )

有可能吗?

谢谢。

编辑:

到目前为止,我的尝试非常好......

// You need an anonymous function to wrap around your function to avoid conflict
(function($)

    // Attach this new method to jQuery
    $.fn.extend( 

        // This is where you write your plugin's name
        pluginname: function(options) 

            //Set the default values, use comma to separate the settings, example:
            var defaults = 
                deleteTarget:   '.item-listed', 
                deleteParent:   '.items-listed',
                wrapperParent:  '.upload',
            

            var options =  $.extend(defaults, options);

            return this.click(function()
                var o = options;

                var target_delete = $(this).parents(o.deleteTarget); // The item for deletion, such as item held in li 
                var parent_delete = $(this).parents(o.deleteParent); // The parent that hold delete item, such as ul > li
                var wrapper_parent = $(this).parents(o.wrapperParent); // The wrapper that hold the parent, such as div > ul > li
                var target_loadin = $(this).parent();
                var target_html = $(this).parent().html();
                var path_load = $(this).attr('href');

                // Make a gif loader.
                target_loadin.html('<img src="'+http_root+rp_image_global+img_loader+'" style="float:none;"/> loading');
                //alert(target_html);

                // Load the delete form.
                target_loadin.load( path_load, function()

                    // When the yes button is triggered.
                    $("input[type=submit][name=yes]").click(function()

                        // Get the path from attribute of action in the form.
                        var path_post = $(this).parent('form').attr('action');
                        //alert(path_post);

                        // Make a gif loader.
                        target_loadin.html('<div class="ajaxloader"><img src="'+http_root+rp_image_global+img_loader+'" style="float:none;"/> loading</div>');

                        // Post the form.
                        $.post(path_post, $(this).serialize(), function(xml)

                            // Procees the form output.
                            process_delete_uploaded(xml);
                        );

                        // Slide up the deleted target.
                        target_delete.slideUp('fast', function() 

                            // Remove its divs completely
                            target_delete.remove();
                            //alert($('li',parent_delete).length);

                            // Count how many items are left behind         
                            if($('li',parent_delete).length == 0)
                            
                                $('.binder-row',wrapper_parent).css(
                                    borderBottom: '0px solid #999', 
                                    padding: '0px 0px 0px 0px'
                                );
                            

                        );

                        return false;
                    );
                );

                return false;

            );

        
    );

//pass jQuery to the function, 
//So that we will able to use any valid javascript variable name 
//to replace "$" SIGN. But, we'll stick to $ (I like dollar sign: ) )       
)(jQuery);

我已按照here 的教程进行操作。即使我不太明白为什么我必须使用 jquery.extend(),它也能很好地工作...

【问题讨论】:

【参考方案1】:

这是一个不完整的示例,应该可以帮助您继续前进:

$.fn.delete_uploaded = function(settings) 
    /* Define defaults for each of the settings: */
    var target_delete = settings.target_delete || '.item-uploaded';
    var parent_delete = settings.parent_delete || '.items-uploaded';
    var wrapper_parent = settings.wrapper_parent || '.upload';

    /* "this" is already a jQuery object: */
    this.click(function()  ... );
;

Here 是编写 jQuery 插件的文档。希望有帮助! jQueryUI source code 也很有用。

编辑:您不必使用extend,但是根据您的情况使用它可能更方便。 Here 是处理 $.fn.extend 的好答案。

【讨论】:

非常感谢这位安德鲁!我已经研究过了 - 看看我上面的编辑。谢谢:-) @lauthiamkok:很高兴为您提供帮助!您不必使用.fn.extend,它只是另一种做事方式。

以上是关于jquery插件:将函数转换为插件?的主要内容,如果未能解决你的问题,请参考以下文章

《锋利的jQuery》插件的使用和写法

无法将 jQuery 脚本转换为插件

将 jQuery 插件转换为 Kentico Web 部件

使用 jquery 插件时,TypeError $(...) 不是函数

jQuery插件3种类型

将此自定义 JQuery 工具提示脚本转换为 Jquery 插件