sự kiện trao đổi html <input type = “text” /> không hoạt động


88

Tôi đang cố gắng làm một số thử nghiệm. Điều tôi muốn xảy ra là mỗi khi người dùng nhập một thứ gì đó vào hộp văn bản, nó sẽ được hiển thị trong một hộp thoại. Tôi đã sử dụng thuộc tính onchangesự kiện để làm cho nó xảy ra nhưng nó không hoạt động. Tôi vẫn cần nhấn nút gửi để làm cho nó hoạt động. Tôi đã đọc về AJAX và tôi đang suy nghĩ để tìm hiểu về điều này. Tôi vẫn cần AJAX để làm cho nó hoạt động hay là JavaScript đủ đơn giản? Xin vui lòng giúp đỡ.

index.php

<script type="text/javascript" src="javascript.js"> </script>

<form action="index.php" method="get">
 Integer 1: <input type="text" id="num1" name="num1" onchange="checkInput('num1');" /> <br />
 Integer 2: <input type="text" id="num2" name="num2" onchange="checkInput('num2');" /> <br />
 <input type="submit" value="Compute" />
</form>

javascript.js

function checkInput(textbox) {
 var textInput = document.getElementById(textbox).value;

 alert(textInput); 
}

4
bạn có thể gửi "này" thay vì id, vì vậy bạn không cần phải gọi getElementById
bourgarel remi

Ừ ... nhờ tôi đã làm những gì Ash Burlaczenko nói với tôi ...
Newbie Coder

Với JQuery, giải pháp tuyệt vời được đề xuất tại đây: stackoverflow.com/a/8167009/2065594
Cyril Jacquart

Câu trả lời:


127

onchangechỉ được kích hoạt khi điều khiển bị mờ. Hãy thử onkeypressthay thế.


19
Không hoạt động để phát hiện sự thay đổi sau khi bột nhão dùng từ clipboard
Juozas Kontvainis

19
Điều đó chỉ khắc phục sự cố của tôi. Tôi thích onkeyupmặc dù, cho nó được các giá trị mới vào input( 'element.value')
stealthjong

4
Tôi cũng nhận thấy "phím bấm" không tăng lên sau khi nhấn phím xóa lùi, ít nhất là khi sử dụng jquery. "keyup" sẽ được nâng lên sau khi nhấn và thả phím xóa lùi. "input" giải quyết vấn đề này và cũng hoạt động để sao chép-dán và tôi nghĩ đây là giải pháp thích hợp ở đây (như người dùng "99 Vấn đề - Cú pháp không phải là một" chỉ ra bên dưới).
Patrick Finnigan

4
'onkeypres', 'onkeyup', v.v. không phải là giải pháp khi người ta muốn gọi một hàm chỉ khi văn bản đã thay đổi ! Các sự kiện chính tạo ra một lưu lượng truy cập không cần thiết trong trường hợp này. (Rất lạ là câu trả lời này đã được chọn làm giải pháp, đặc biệt là với số phiếu bình chọn rất hấp dẫn !! Tôi không phản đối nó, bởi vì tôi không thích chỉ phản đối câu trả lời. Tôi thích đưa ra (các) lý do tại sao nó không ổn - Nó hữu ích hơn!)
Apostolos

Đối với HTML ≥5 hoặc jQuery ≥1.7, có các giải pháp khác bên dưới, cũng xử lý việc dán từ khay nhớ tạm.
user202729

41

Sử dụng .on('input'...để theo dõi mọi thay đổi đối với đầu vào (dán, gõ phím, v.v.) từ jQuery 1.7 trở lên.

Đối với đầu vào tĩnh và động:

$(document).on('input', '.my-class', function(){
    alert('Input changed');
});

Chỉ dành cho đầu vào tĩnh:

$('.my-class').on('input', function(){
    alert('Input changed');
});

JSFiddle với ví dụ tĩnh / động: https://jsfiddle.net/op0zqrgy/7/


Điều này làm việc hoàn hảo cho tôi - cảm ơn. Lưu ý cho những người khác - đừng quên thực thi mã trên trong onLoad của bạn hoặc một cái gì đó để nó 'bắt đầu' theo dõi.
Robert Penridge

Quá muộn cho một nhận xét nhưng ... Tại sao bạn đề xuất sử dụng jQuery nếu người dùng trả lời hiển thị JavaScript đơn giản?
Andrés Morales

@ AndrésMorales Đó là một thư viện chung mà nhiều ứng dụng có thể truy cập ngay lập tức và rất đơn giản để thêm vào những ứng dụng không có. Rõ ràng, câu trả lời này không áp dụng cho những ứng dụng không thể (hoặc chọn không) sử dụng jQuery.
rybo111

@ rybo111 Chính xác! jQuery là một thư viện phổ biến và được sử dụng rộng rãi, nhưng nó liên kết trực tiếp trong não tôi đến câu hỏi meme về "tính tổng hai số bằng JavaScript" và câu trả lời được ủng hộ nhiều nhất về việc sử dụng jQuery để làm điều đó. Không phải vậy nhưng nhiều người không thể tách JavaScript và jQuery.
Andrés Morales

@ AndrésMorales Lưu ý rằng câu trả lời của tôi bao gồm "paste, keyup, v.v.". Tôi nhớ lại giải pháp jQuery rất tiện lợi khi tôi trả lời câu hỏi này (7 năm trước!).
rybo111

30

Kiểm tra tổ hợp phím chỉ là giải pháp một phần, vì có thể thay đổi nội dung của trường nhập bằng cách nhấp chuột. Nếu bạn nhấp chuột phải vào trường văn bản, bạn sẽ có các tùy chọn cắt và dán mà bạn có thể sử dụng để thay đổi giá trị mà không cần gõ phím. Tương tự như vậy, nếu tính năng tự động điền được bật thì bạn có thể nhấp chuột trái vào một trường và nhận được danh sách thả xuống của văn bản đã nhập trước đó và bạn có thể chọn trong số các lựa chọn của mình bằng cách nhấp chuột. Tính năng bẫy phím sẽ không phát hiện được một trong hai loại thay đổi này.

Đáng buồn là không có sự kiện "onchange" nào báo cáo các thay đổi ngay lập tức, ít nhất là theo như tôi biết. Nhưng có một giải pháp phù hợp với mọi trường hợp: thiết lập sự kiện định thời bằng cách sử dụng setInterval ().

Giả sử trường nhập của bạn có id và tên là "thành phố":

<input type="text" name="city" id="city" />

Có một biến toàn cục có tên "city":

var city = "";

Thêm cái này vào phần khởi tạo trang của bạn:

setInterval(lookForCityChange, 100);

Sau đó, xác định một hàm lookForCityChange ():

function lookForCityChange()
{
    var newCity = document.getElementById("city").value;
    if (newCity != city) {
        city = newCity;
        doSomething(city);     // do whatever you need to do
    }
}

Trong ví dụ này, giá trị của "thành phố" được kiểm tra cứ sau 100 mili giây, bạn có thể điều chỉnh giá trị này theo nhu cầu của mình. Nếu bạn thích, hãy sử dụng một hàm ẩn danh thay vì xác định lookForCityChange (). Lưu ý rằng mã của bạn hoặc thậm chí trình duyệt có thể cung cấp giá trị ban đầu cho trường đầu vào để bạn có thể được thông báo về "thay đổi" trước khi người dùng thực hiện bất kỳ điều gì; điều chỉnh mã của bạn nếu cần.

Nếu ý tưởng về một sự kiện thời gian xảy ra mỗi phần mười giây có vẻ vô duyên, bạn có thể khởi tạo bộ hẹn giờ khi trường đầu vào nhận được tiêu điểm và kết thúc nó (với clearInterval ()) khi bị mờ. Tôi không nghĩ rằng có thể thay đổi giá trị của trường đầu vào mà nó không nhận tiêu điểm, vì vậy việc bật và tắt bộ hẹn giờ theo cách này sẽ an toàn.


1
Nếu không thể thay đổi giá trị của trường đầu vào mà nó không lấy nét và xảy ra hiện tượng mờ khi một phần tử mất tiêu điểm, tại sao không chỉ tìm kiếm các thay đổi trong onblur?
Pakman

Bạn có muốn thực hiện hành động khi trường đầu vào thay đổi hoặc khi trường mất tiêu điểm sau khi thay đổi không? Nếu bạn muốn hành động ngay lập tức, bạn không thể đợi người bật mí.
Dragonfly

@Pakman Đó là một giải pháp tốt trong một số trường hợp. Nhưng nếu bạn muốn thực hiện tìm kiếm khi bạn nhập - một tính năng rất hay của IMO (tại sao người dùng phải tìm kiếm nội dung khi máy tính có thể làm việc đó nhanh hơn rất nhiều và không bị nhàm chán?) - hoặc bất cứ điều gì khác thực sự như vậy cần phải xảy ra khi văn bản thay đổi, tại sao bạn không thể?
The Dag

Thật buồn khi nói đến điều này.
Chuck Batson

1
@ChuckBatson Câu trả lời này là từ năm 2012. Tôi nhận thấy bạn đã đăng nhận xét của mình vào năm 2016. Hãy xem câu trả lời của tôi nếu bạn đang sử dụng jQuery, bây giờ nó cực kỳ dễ dàng.
rybo111

26

HTML5 xác định một oninputsự kiện để bắt tất cả các thay đổi trực tiếp. nó hoạt động cho tôi.


1
cũng hoạt động với điều khiển spinner type = "number" (onkeypress không hoạt động với).
Bob

13

onchange chỉ xảy ra khi người dùng cam kết thay đổi đối với phần tử đầu vào, hầu hết trường hợp này là khi phần tử mất tiêu điểm.

nếu bạn muốn hàm của mình kích hoạt mỗi khi giá trị phần tử thay đổi, bạn nên sử dụng oninputsự kiện - điều này tốt hơn so với sự kiện phím lên / xuống vì giá trị có thể được thay đổi bằng chuột của người dùng tức là được dán vào hoặc tự động điền, v.v.

Đọc thêm về sự kiện thay đổi tại đây

Đọc thêm về sự kiện đầu vào tại đây


11

sử dụng các sự kiện sau thay vì "onchange"

- onkeyup(event)
- onkeydown(event)
- onkeypress(event)

6

Thứ nhất, điều gì 'không hoạt động'? Bạn không thấy cảnh báo?

Ngoài ra, mã của bạn có thể được đơn giản hóa thành

<input type="text" id="num1" name="num1" onkeydown="checkInput(this);" /> <br />

function checkInput(obj) {
    alert(obj.value); 
}

2

Tôi gặp sự cố trong đó Safari không kích hoạt các sự kiện "onchange" trên trường nhập văn bản. Tôi đã sử dụng sự kiện "thay đổi" jQuery 1.7.2 và nó cũng không hoạt động. Tôi đã sử dụng sự kiện trao đổi văn bản của ZURB. Nó hoạt động với mouseevents và có thể kích hoạt mà không cần rời khỏi trường:
http://www.zurb.com/playground/jquery-text-change-custom-event

$('.inputClassToBind').bind('textchange', function (event, previousText) {
    alert($(this).attr('id'));
});

2

Một số nhận xét rằng IMO rất quan trọng:

  • các phần tử đầu vào không phát ra sự kiện 'thay đổi' cho đến khi người dùng thực hiện hành động ENTER hoặc làm mờ đang chờ đợi là hành vi chính xác .

  • Sự kiện bạn muốn sử dụng là "input"(" oninput "). Đây là minh chứng rõ ràng về sự khác biệt giữa hai: https://javascript.info/events-change-input

  • Hai sự kiện báo hiệu hai cử chỉ / khoảnh khắc khác nhau của người dùng (sự kiện "đầu vào" có nghĩa là người dùng đang viết hoặc điều hướng một tùy chọn danh sách đã chọn, nhưng vẫn không xác nhận thay đổi. "Thay đổi" có nghĩa là người dùng đã thay đổi giá trị (với dấu enter hoặc làm mờ của chúng tôi)

  • Lắng nghe các sự kiện chính như nhiều sự kiện được khuyến nghị ở đây là một cách thực hành không tốt trong trường hợp này. (như mọi người sửa đổi hành vi mặc định của ENTER trên đầu vào) ...

  • jQuery không liên quan gì đến điều này. Đây là tất cả trong tiêu chuẩn HTML.

  • Nếu bạn gặp khó khăn trong việc hiểu TẠI SAO đây là hành vi chính xác, có lẽ hữu ích, như thử nghiệm, hãy sử dụng trình chỉnh sửa văn bản hoặc trình duyệt của bạn mà không cần chuột / pad, chỉ cần bàn phím.

Theo quan điểm của tôi.


1

onkeyup đã làm việc cho tôi. onkeypress không kích hoạt khi nhấn lại khoảng trắng.


những gì khi một giá trị được dán? Tôi cũng sử dụng "onpaste" để kích hoạt sự kiện
Louis

1

Nó là tốt hơn để sử dụng onchange(event)với <select>. Với <input>bạn có thể sử dụng sự kiện dưới đây:

- onkeyup(event)
- onkeydown(event)
- onkeypress(event)

-3

thử onpropertychange. nó chỉ hoạt động cho IE.


6
Tại sao mọi người lại muốn xem xét một thuộc tính chỉ hoạt động trong TRÌNH DUYỆT OBSOLETE đã bị nhà phát triển của nó bỏ rơi? Phản đối.
Sod Almighty,
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.