我正在动态添加select元素,如下面的HTML。我不确定为什么.on('更改'...)不能用于动态选择。我错过了什么?
我正在使用Chrome 24.0.1312.57 + jquery 1.8.3。
<script type="text/javascript">
$(document).ready(function() {
$('#x select').on('change', function () { alert('helo'); })
$('#y select').on('change', function () { alert('helo'); })
$('#x').html($('#y').html());
});
</script>
<div id="x"></div>
<div id="y">
<select>
<option>O1</option>
<option>O2</option>
</select>
</div>
答案 0 :(得分:31)
您的代码:
$('#x select').on('change', function () { alert('helo'); })
将一个事件处理程序附加到#x元素内的select。
你想要的东西(根据我所理解的)是符合以下内容的:
$("#y").on('change','select',function () { alert('helo'); });
这将事件处理程序附加到#y元素,该元素被委托给其子元素的“select”元素
.on()方法将事件处理程序附加到jQuery对象中当前选定的元素集。
答案 1 :(得分:8)
事件绑定到初始页面加载时不在DOM中的元素将不起作用。您需要绑定到存在的DOM上方的元素,以允许事件向下流动。这通常是我采取的方法:
$(document).on({
change: function() {
alert('helo');
}
}, '#x select');
$(document).on({
change: function() {
alert('helo');
}
}, '#y select');
我更喜欢它,因为您可以轻松添加后续事件。
$(document).on({
change: function() {
alert('helo');
},
blur: function() {
alert('helo');
}
}, '#x select');
答案 2 :(得分:3)
您的事件绑定设置在$(document).ready()上。但是,如果您稍后动态添加它们(例如通过jQuery.appendTo()等),则新添加的组件需要绑定,因为它们不是$(document).ready()中发生的初始组件的一部分。 ,只在加载页面并且最初完成DOM时才运行一次。
答案 3 :(得分:1)
正确的语法:
$('#x').on(
'change',
'select',
function () {
alert('helo');
}
);
因此动态元素on()
的语法似乎是:
$(staticParent).on( eventName, target, handler);
答案 4 :(得分:1)
.on()的重点是,您可以将事件绑定到文档以外的其他内容。这就是现在折旧的.live()所做的事情,在大多数情况下都是低效的。您可以将事件绑定到最不会动态更改的父元素。
据我所知,这是正确的语法:
$('#x').on('change', 'select', function(){
alert('hello');
});
如果要更改#x或#y,请将它们包装在元素上并将事件绑定到该元素。
答案 5 :(得分:1)
这很容易。无论您的目标是什么类别或ID,都要尝试更精确,但不需要包含超级父母。
错误方式的例子:
$('#tablecontent').on('change', '#tablecontent > table.CampaignGrid > tbody > tr > td', function(e) {
console.log('IN TABLE CONTENT CHANGE');
var value = e.target.value;
$('button#updateLuck').prop('disabled', false).css({'color': '#000', 'font-weight': 600});
//alert($(ele[0]).html());
});
正确的方式:
$('#tablecontent').on('change', 'table.CampaignGrid > tbody > tr > td', function(e) {
console.log('IN TABLE CONTENT CHANGE');
var value = e.target.value;
$('button#updateLuck').prop('disabled', false).css({'color': '#000', 'font-weight': 600});
//alert($(ele[0]).html());
});
注意我放弃了超级父母:'#tablecontent'
关于清晰度。
答案 6 :(得分:1)
/**
* Source: http://stackoverflow.com/a/33841999/1402846
*
* This function is (almost) equivalent to array_column() in PHP (http://php.net/manual/function.array-column.php).
*
* Differences between this function and PHP's array_column():
* <ul>
* <li>If <code>indexKey</code> is not found in an element of the input array, the behaviour of this function is undefined.
* In PHP's array_column(), the element will be put into the end of the array. It is possible in PHP because PHP does not
* distinguish between arrays and dictionaries, but it is not possible in JavaScript because Arrays and Objects are different.
*
* <li>Associative arrays (dictionaries) in PHP are ordered, JavaScript objects are not (http://stackoverflow.com/a/5525820/14028460.
* Do not make assumptions on the ordering of the keys in JavaScript objects.
*
* <li>If the value of an element at <code>inputKey</code> is not a string, the result of this function and the PHP function
* doesn't make much sense. For example, in PHP,
* <code>
* $records = array(
* array('id' => true, 'last_name' => 'Doe')
* );
* array_column($records, 'last_name', 'id');
* </code>
* gives <code>Array([1] => Doe)</code>, or maybe <code>Array([0] => Doe)</code> due to a bug ({@link https://bugs.php.net/bug.php?id=68553}). But, in JavaScript,
* <code>
* var records = [
* {id: true, last_name: 'Doe'},
* ];
* arrayColumn(records, 'last_name', 'id');
* </code>
* gives <code>{true: "Doe"}</code>. Therefore, it is strongly advised to make sure that the value at <code>indexKey</code> of
* each input element is a string.
* </ul>
*
* @param {Array|Object} inputArray The input array, it must either contain objects only or arrays only.
* If it is an object instead of an array, it would be converted to an array first.
* @param {int|string|null} columnKey If the input array contains objects, this parameter is the key in each object.
* If the input array contains arrays, this parameter is the index in each array.
* If the key or index is not valid, this element is skipped.
* This parameter may also be <code>null</code>.
* @param {int|string|null} [indexKey=null] If the input array contains objects, this parameter must be a valid key in each object.
* If the input array contains arrays, this parameter must be a valid index in each array.
* If it is not a valid key or index, the behaviour is undefined.
* This parameter may also be <code>null</code>.
* @returns {Array|Object} If <code>indexKey</code> is <code>null</code>, this function returns an array which is parallel
* to the input array. For each element <code>elem</code> in the input array, the element in the
* output array would be <code>elem[columnKey]</code>, or just <code>elem</code> if <code>columnKey</code>
* is <code>null</code>.
* If <code>indexKey</code> is <b>not</b> <code>null</code>, this function returns an object.
* For each element <code>elem</code> in the input array, the output object would contain an
* element <code>elem[columnKey]</code>, or just <code>elem</code> if <code>columnKey</code>
* is <code>null</code>, at the key <code>elem[indexKey]</code>. If the value of <code>elem[indexKey]</code>
* of some elements in the input array are duplicated, the element in the return object would
* correspond to the element nearest to the end of the input array.
* @example
* var records = [
* {id: 2135, first_name: 'John', last_name: 'Doe'},
* {id: 3245, first_name: 'Sally', last_name: 'Smith'},
* {id: 5342, first_name: 'Jane', last_name: 'Jones'},
* {id: 5623, first_name: 'Peter', last_name: 'Doe'}
* ];
* var first_names = arrayColumn(records, 'first_name');
* >> ["John", "Sally", "Jane", "Peter"]
* var last_names = arrayColumn(records, 'last_name', 'id');
* >> {2135: "Doe", 3245: "Smith", 5342: "Jones", 5623: "Doe"}
* var persons = arrayColumn(records, null, 'id');
* >> {
* 2135: {id: 2135, first_name: 'John', last_name: 'Doe'},
* 3245: {id: 3245, first_name: 'Sally', last_name: 'Smith'},
* 5342: {id: 5342, first_name: 'Jane', last_name: 'Jones'},
* 5623: {id: 5623, first_name: 'Peter', last_name: 'Doe'}
* }
*/
function arrayColumn(inputArray, columnKey, indexKey)
{
function isArray(inputValue)
{
return Object.prototype.toString.call(inputValue) === '[object Array]';
}
// If input array is an object instead of an array,
// convert it to an array.
if(!isArray(inputArray))
{
var newArray = [];
for(var key in inputArray)
{
if(!inputArray.hasOwnProperty(key))
{
continue;
}
newArray.push(inputArray[key]);
}
inputArray = newArray;
}
// Process the input array.
var isReturnArray = (typeof indexKey === 'undefined' || indexKey === null);
var outputArray = [];
var outputObject = {};
for(var inputIndex = 0; inputIndex < inputArray.length; inputIndex++)
{
var inputElement = inputArray[inputIndex];
var outputElement;
if(columnKey === null)
{
outputElement = inputElement;
}
else
{
if(isArray(inputElement))
{
if(columnKey < 0 || columnKey >= inputElement.length)
{
continue;
}
}
else
{
if(!inputElement.hasOwnProperty(columnKey))
{
continue;
}
}
outputElement = inputElement[columnKey];
}
if(isReturnArray)
{
outputArray.push(outputElement);
}
else
{
outputObject[inputElement[indexKey]] = outputElement;
}
}
return (isReturnArray ? outputArray : outputObject);
}
$('#tablecontent').on('change', '#tablecontent > table.CampaignGrid > tbody > tr > td', function(e) {
console.log('IN TABLE CONTENT CHANGE');
var value = e.target.value;
$('button#updateLuck').prop('disabled', false).css({'color': '#000', 'font-weight': 600});
//alert($(ele[0]).html());
});
$('#tablecontent').on('change', '#tablecontent > table.CampaignGrid > tbody > tr > td', function(e) {
console.log('IN TABLE CONTENT CHANGE');
var value = e.target.value;
$('button#updateLuck').prop('disabled', false).css({'color': '#000', 'font-weight': 600});
//alert($(ele[0]).html());
});
$('#tablecontent').on('change', 'table.CampaignGrid > tbody > tr > td', function(e) {
console.log('IN TABLE CONTENT CHANGE');
var value = e.target.value;
$('button#updateLuck').prop('disabled', false).css({'color': '#000', 'font-weight': 600});
//alert($(ele[0]).html());
});
答案 7 :(得分:1)
方括号中的单词是alt文本,如果浏览器无法显示图像,则会显示该文本。请务必为屏幕阅读软件添加有意义的替代文字。
答案 8 :(得分:0)
不要使用.live()
/ .bind()
/ .delegate()
。你应该使用。on()
。
用于静态和动态选择更改
$(document).on('change', 'select', function (e) {
// do something
});
答案 9 :(得分:0)
对此有点误解,因为我无法从动态ID的ajax帖子中返回动态创建的选择来触发事件。
$(document).on('change', 'select', function (e) {
$("#theDiv select").on("change",function(){ post("SelectChanged");} );
});
直到我先进行一些更改,然后我添加
$("#theDiv select").on("change",function(){ post("SelectChanged");} );
但这并不意味着在更改之后,所有其他更改都会触发两次。 这可能不是很好的做法。 但是我要做的是放入一个在ajax的开始和每次返回时调用的函数。
`function myFuncs(){
$('#theDiv select').unbind('change');
$('#theDiv select').on('change' function(){ post('selectChanged'); });
}`
但是必须在每个函数调用开始时取消绑定,否则每次都会使函数加倍。 我确信必须有适当的方法来做到这一点,我只是还没有找到它。 感谢您提出问题。