0

在大量使用 Java 和 C++ 经验之后,我第一次使用 JS 和 jQuery。我喜欢 jQuery 的想法$(document).on('click', 'btn-selector', react),但对于更复杂的小部件,我发现自己一遍又一遍地陷入同样的​​困境:在每个react处理程序中,我必须将小部件作为一个整体进行查找并重建我对它的所有知识。

例如,我正在用<input>s 制作一个简单的小部件,用户可以使用它来制作评分等级:90 个映射到 A,80 个映射到 B,等等。当其中一个输入发生变化时,我想检查一下确保输入仍然正常(例如,您的秤不能达到 90、70、80)。

所以,我有类似的东西

实际的

$(document).on('click', '.scale-input', function() {
    var widget = $(this).closest('.scale-widget-container');
    ensureLevelsAreInOrder(widget);
});

几乎每个处理程序都必须有第一行才能找到它的上下文。我宁愿有这样的代码:

首选

$(document).on('click', '.scale-input', ensureLevelsAreInOrder);

问题在于,在这种形式中,ensureLevelsAreInOrder只有对更改的输入的引用,而不是更大的上下文。

在 Java 或 C++ 中,我会在小部件上调用构造函数,并且每个输入都会有一个处理程序,其中包含通过成员变量烘焙的上下文。我可以做类似的事情

$(function() {
    $('.scale-widget-container').scaleWidget();
});

通过scaleWidget()设置上下文处理程序,但是我正在使用的页面使用 ajax 加载了很多它的 html,并且我没有可靠的时间来运行该初始化。

如果我们不想在 HTML 中使用 JS,这是我们必须处理的常见问题,还是有我还没有遇到的解决方案?

4

1 回答 1

0

不知道你到底在追求什么,但是当谈到 JS 时,你似乎没有触及两个非常重要的概念:event对象和闭包。这两个都对您开放以获得您需要的东西:

事件对象:
回调函数被传递一个参数,描述事件本身,并引用受该事件影响的元素,这不是 jQ 独有的(只是 google addEventListener),但它非常方便:

$(document).on('click', '.scale-input', function(e)//<-- e is our event
{
    console.log(e);//check console
});

其中,在香草 JS 中看起来像这样:

document.addEventListener('click', function(e)
{
    if (!e.className.test(/\bscale\-input\b/))
    {
        return e;
    }
    console.log(e);
}, false);

您可能要考虑的另一件事是在 IIFE 的范围内包含对您需要的任何内容的引用:

(function()
{
    var containers = $('.scale-widget-container'),
    localBool = false,
    asMany = 'varsAs you need',
    previousScales = [],
    inputs = $('.scale-input');//references to all DOM nodes you mention
    $(document).on('click','.scale-input',function(e)
    {
        console.log($(this));
        console.log(containers);
        previousScales.push(this.value);//or something
        console.log(previousScales);
        //and so on.
    });
}());

希望这有帮助

更新:
如果 IE 不是您不太关心的浏览器,您可以使用 DOM 修改事件之一,特别是DOMTreeModified

(function()
{
    var nodes = [];//<-- store current nodes here, if applicable
    nodes.containsNode = function(node)
    {
        var i;
        for (i=0;i<this.length;i++)
        {
            if (this[i] && this[i] === node)
            {//node is set, return its index
                return i;
            }
        }
        //node not found, return -1
        return -1;
    };
    document.body.addEventListener('DOMSubtreeModified',function(e)
    {
        var all = document.getElementsByClassName('scale-input'),
        i;
        for (i=0;i<all.length;i++)
        {
            if (nodes.containsNode(all[i]) === -1)
            {
                nodes.push(all[i]);//add new
            }
        }
    },false);
}());

有关突变事件及其问题的更多信息,请访问 DOM 事件 wiki

于 2013-06-03T13:49:50.083 回答