如何将事件处理程序附加到extJS中的面板?

Edw*_*uay 7 events extjs event-handling

我想要做的就是处理extJS面板上的点击.

我已经尝试了关于这个问题的所有建议以及我在其他地方找到的所有建议,但是每个建议都以下面描述的方式失败了.

将click事件处理程序添加到extJS面板的正确语法是什么?

[ 编辑:为了以后可能会发现这个问题的其他人,我会在内联添加一些注释,以便更容易解读 - @ bmoeskau]

不执行处理程序:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem',
    listeners: {
        click: function() {
            alert('ok');
        }
    }
}); 
Run Code Online (Sandbox Code Playgroud)

[Ed:click不是小组活动]

不执行处理程序:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem',
    listeners: {
        render: function(c) {
            c.body.on('click', function() {
                alert('ok');
            });
        }
    }
}); 
Run Code Online (Sandbox Code Playgroud)

[Ed:面板永远不会被渲染 - 添加renderTo配置.接下来,您将遇到一个空错误,告诉您这c不是一个有效的变量.你的意思是menuItem1吗?]

不执行处理程序:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem'
}); 
Ext.getCmp('panelStart').on('click', function() {
    alert('ok');
});
Run Code Online (Sandbox Code Playgroud)

[Ed:click不是小组活动.此外,Panel尚未呈现,因此如果您将回调切换为元素而不是Component,则会出现null错误.

获取错误:Ext.get('panelStart')为null:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem'
}); 
Ext.get('panelStart').on('click', function() {
    alert('ok');
});
Run Code Online (Sandbox Code Playgroud)

[Ed:它没有渲染,见上文.从切换getCmpget意味着您正在从引用Component(确实存在,但没有click事件)切换到引用Element(它确实有click事件,但尚未呈现/有效).

使面板消失:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem',
    listeners: {
        'render': {
            fn: function() {
                this.body.on('click', this.handleClick, this);
            },
            scope: content,
            single: true
        }
    },
    handleClick: function(e, t){
        alert('ok');
    }        
}); 
Run Code Online (Sandbox Code Playgroud)

[Ed:传递给callback(content)的作用域不是此代码中的有效引用(这是从另一个示例中错误地复制粘贴).由于Panel var是创建的,menuItem1并且回调旨在在面板的作用域中运行,因此范围var应该是menuItem1.此外,此小组从未呈现,请参阅上一条评论.]

给出错误"Ext.fly(menuItem1.id)为null":

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem'
}); 
Ext.fly(menuItem1.id).addListener('click', Ext.getCmp(menuItem1.id) , this);
Run Code Online (Sandbox Code Playgroud)

[编辑:面板未渲染,见上文]

...放在外面Ext.onReady()...得到错误:Ext.getCmp('panelStart')为空

Ext.getCmp('panelStart').on('click', function() {
    alert('okoutside');
});
Run Code Online (Sandbox Code Playgroud)

[Ed:Panel可能在此代码运行时未呈现.此外,click不是Panel事件.]

...放在外面Ext.onReady()...得到错误:Ext.get('panelStart')为空

Ext.get('panelStart').on('click', function() {
    alert('okoutside');
});
Run Code Online (Sandbox Code Playgroud)

[编辑:见上文]

...放在外面Ext.onReady()...得到错误:Ext.fly('panelStart')为空

Ext.fly('panelStart').on('click', function() {
    alert('okoutside');
});
Run Code Online (Sandbox Code Playgroud)

[编辑:见上文]

对于最后三个,我检查了Firebug并<div id="startPanel">存在:

替代文字

它适用于JQuery:

所以使用JQuery我只需要这样做它可以工作:

$('body').delegate(('#panelStart'), 'click', function(){
    alert('ok with jquery');
});
Run Code Online (Sandbox Code Playgroud)

[艾德:这不是一个好方法.它只是延迟了处理程序的附加,直到后来,当元素实际显示在DOM中时(也可以通过Ext btw完成,但仍然不是正确的方法).我在下面的回答中列出了正确的方法.OP的尝试都非常接近,但每个都缺少一两个关键部分.

如何使用extJS附加这样的单击处理程序?

Ger*_*rat 7

试试这个:

var menuItem1 = new Ext.Panel({
    id: 'panelStart',
    title: 'Start',
    html: 'This is the start page.',
    cls:'menuItem',
    listeners: {
        afterrender: function (comp) {
            var element = comp.getEl();
            element.on('click', function() {
                alert('ok')
            });
        }
    }
}); 


Bri*_*kau 6

[对于其他读这篇文章的人,我已经在这里对此进行了相当详尽的解释.]

您缺少一些关键概念:

click不是一个有效的小组活动,因此增加一个面板上单击处理程序不会做任何事情(这是问题的最上面你贴的代码).

在这段代码中:

var menuItem1 = new Ext.Panel({
   ...
}); 
content.body
Run Code Online (Sandbox Code Playgroud)

您从另一个答案复制粘贴,但不正确. content在其他代码中引用了创建的Panel - 它是一个变量.在这段代码中你创建了Panel,menuItem1但是后来试图引用它content

请重新阅读我之前关于渲染如何在我给你的另一个答案中工作的解释.您必须将Panel添加到呈现它的容器中,或者直接呈现它(通过renderTo配置).如果您不这样做,小组将不会出现.

使用jQuery的委托函数不是 Ext JS组件的正确方法.