jQuery:学习制作插件:基本手风琴插件

时间:2012-03-11 16:15:12

标签: jquery plugins accordion

再次感谢所有花费一点时间帮助我理解jQuery的人,非常感谢。

我正在努力,慢慢地推动我的jQuery。所以我在stackoverflow中一直非常活跃地向我面临的问题提出问题......很多时候“为什么”...我对jQuery很满意并且每天都使用它。然而,我的知识总是需要学习和填补空白。所以我决定尝试创建一个jQuery插件 - 这个非常简单,我可以作为一个个人项目进行扩展,这样我就可以学会做一些事情。

所以,我选择制作一个非常简单的手风琴插件jsFiddle of the current accordion

(function($){
//The current script for the plugin..
    $.fn.simpleAccordion = function() { 
        $("li a").live("click", function(e){
            e.preventDefault();
            $("li div").slideUp(200);
            $(this).next(':hidden').slideDown(200);
        });
    };
})(jQuery);

第一个问题:我一直在阅读jQuery文档Plugins/Authoring。 我在文档中遇到的第一个问题是状态$(this)通常使用不正确..应该是“this.fadeIn('normal',function(){...” -

 $(this).next(':hidden').slideDown(200);

我是否在上述行中的正确背景下使用“this”? 目前我明白“this”是引用插件被调用的选择器..所以ul#accordion ..那么为什么没有$(“”)它没有工作..

$(document).ready(function(){
    $("ul#accordion").simpleAccordion();
}); 

第二个问题: 我想我自己找到了一个解决方案(见下文) 我正在测试我已经拥有的东西并意识到如果我在手风琴的内容体中放置了一个ancor标签/链接,这个链接也将打开并关闭面板..我试图将选择器更改为点击功能

$("li a:first-child").live("click",.. 

确保只有第一个ancor标签继续点击的链接附加了一个事件..但没有运气......我不希望li中的每一个标签都触发幻灯片功能我希望它们离开单独..所以最好给出一个类名或使用更具体的选择器? :P

我认为我找到了第二个问题的正确解决方案(下面)

$("li > a:first-of-type").live("click", function(e){

再次感谢,我知道这有点罗嗦!

jsFiddle of the current accordion

2 个答案:

答案 0 :(得分:1)

第一个问题: 这在事件的上下文中 - 回调始终是触发事件的元素。 要使用所有jQuery魔法,这个元素必须通过$(this)进行扩展。只有这样它才是一个jQuery-Object。 在你的插件中,你不应该使用$("li div"),因为这将在你的整个页面上为你提供所有div。您只需要当前上下文中的那些。 因此,使用$(this)然后使用parents(),find()等在DOM中上下移动。

在你的插件上: 请继续阅读插件教程。您必须更改代码才能使其成为真正的插件。在这种状态下,你正在破坏链条。 类似$('.element).simpleAccordion().data('foo','bar')之类的东西将无效,因为您不会再次返回该对象。

并且:不要使用已弃用的live()。请查看文档中的.on()http://api.jquery.com/on/

希望有所帮助

答案 1 :(得分:1)

让我试着指导你一点。

首先,当你这样做时:

$.fn.foo = function () {
    // some code
}

这可以让你这样做:

$('div').foo();

这里的关键是,在foo内,this变量将等同于函数所作用的选择。在这种情况下,

this === $('div')

因此,我没有看到在插件函数中选择完全不同的选择(即$('li a'))。

你可能是这样的意思:

$.fn.simpleAccordion = function () {
    var stuff = this.find('li a');
    // use your stuff
    return this; // for chaining
};

其次(完全不在问题上下文中),停止使用.live()。它不仅没有意义(你正在使你的插件功能对看起来应该已经存在的东西起作用),这可能是不好的做法。请改用.on(),或者使用jQuery 1.7之前的.delegate()。但首先要确保它不是你真正想要的.bind()(我非常怀疑)。

要回答你的第二个问题,这真的有点模糊。但是根据经验,几乎总有一种方法可以选择(并因此修改/使用)DOM 中的HTML元素,而不必使用装饰器类标记它们,就像您用来识别/标记它们一样。

如果:first-child在比你想要的更多元素上启动动画,我怀疑你要么使用错误的选择器,要么你没有足够的限制你的jQuery方法调用(比如如果您在插件功能中误用this或选择 - 请参阅上面的第1点。

如果没有HTML标记,我无法指出您应该改进的内容。

我不知道它对你有多大帮助,但我之前写了一篇关于插件创作的快速文章。 You might want to take a look