ตรวจจับการป้อนอัตโนมัติของเบราว์เซอร์


165

คุณจะบอกได้อย่างไรว่าเบราว์เซอร์เติมข้อความอัตโนมัติหรือไม่ โดยเฉพาะอย่างยิ่งกับกล่องชื่อผู้ใช้และรหัสผ่านที่ป้อนอัตโนมัติเมื่อมีการโหลดหน้าเว็บ

คำถามแรกของฉันคือสิ่งนี้เกิดขึ้นในลำดับการโหลดหน้า? ก่อนหรือหลังเอกสารเสร็จไหม

ประการที่สองฉันจะใช้ตรรกะเพื่อค้นหาว่าสิ่งนี้เกิดขึ้นได้อย่างไร ไม่ใช่ว่าฉันต้องการที่จะหยุดสิ่งนี้ไม่ให้เกิดขึ้นเพียงขอเข้าร่วมในเหตุการณ์ โดยเฉพาะอย่างยิ่งสิ่งนี้:

if (autoFilled == true) {

} else {

}

ถ้าเป็นไปได้ฉันชอบที่จะเห็น jsfiddle แสดงคำตอบของคุณ

ข้อมูลซ้ำที่เป็นไปได้

เหตุการณ์ DOM สำหรับป้อนรหัสผ่านเบราว์เซอร์อัตโนมัติหรือไม่

Autofill ของเบราว์เซอร์และ Javascript เรียกใช้เหตุการณ์

- ทั้งคำถามเหล่านี้ไม่ได้อธิบายสิ่งที่เรียกเหตุการณ์พวกเขาเพียงตรวจสอบกล่องข้อความอย่างต่อเนื่อง (ไม่ดีสำหรับประสิทธิภาพ!)


1
การตรวจสอบใช้เวลาบางไมโครวินาทีในขณะที่ช่วงเวลาจะทำการตรวจสอบทุกๆ 100 มิลลิวินาทีหรือมากกว่านั้น ... มันจะส่งผลต่อประสิทธิภาพการทำงานอย่างไร? หากมีเหตุการณ์เกิดขึ้นจากเบราว์เซอร์ฉันแน่ใจว่าพวกเขาจะใช้มัน
Esailija

ฉันเห็นสิ่งที่คุณหมายถึง แต่มันก็ขึ้นอยู่กับส่วนแรกของคำถามของฉันไม่ว่า JavaScript จะตระหนักถึงการเปลี่ยนแปลงที่เกิดขึ้น (เช่นก่อน document.ready)
ไม่ได้กำหนด

1
ทางออกที่ดีที่สุดสำหรับ Chrome / WebKit คือการใช้ตัวเลือก DOM: document.querySelectorAll ('อินพุต: -webkit-autofill'); หลังจาก setTimeout ล่าช้าเล็กน้อย (... รหัสที่นี่ ... 250);
ChrisN

โดยทั่วไปฉันต้องการผู้ใช้เข้าสู่ระบบอัตโนมัติถ้ามันถูกป้อนอัตโนมัติ, ot ot ที่น่ารำคาญบ้าเข้าสู่ระบบอีกครั้งเมื่อมันออกจากระบบโดยอัตโนมัติ
มูฮัมหมัดอูเมอร์

@ChrisN ความคิดเห็นของคุณคือสิ่งที่ทำให้ฉันมีวิธีการแก้ปัญหา (ง่าย) ฉันไม่เห็นว่ามันเป็นคำตอบ แต่! โพสต์เป็นหนึ่งและ ping ฉันดังนั้นฉันสามารถ upvote ได้ขอบคุณ
Ethan Kaminski

คำตอบ:


123

ปัญหาคือการป้อนอัตโนมัติถูกจัดการแตกต่างกันโดยเบราว์เซอร์ที่แตกต่างกัน บางคนส่งเหตุการณ์การเปลี่ยนแปลงบางคนไม่ทำ ดังนั้นจึงแทบเป็นไปไม่ได้เลยที่จะเชื่อมโยงเหตุการณ์ที่เกิดขึ้นเมื่อเบราว์เซอร์เติมข้อมูลในฟิลด์ป้อนข้อมูลอัตโนมัติ

  • เปลี่ยนทริกเกอร์เหตุการณ์สำหรับเบราว์เซอร์ต่างๆ:

    • สำหรับฟิลด์ชื่อผู้ใช้ / รหัสผ่าน:

      1. Firefox 4, IE 7 และ IE 8 จะไม่ส่งเหตุการณ์การเปลี่ยนแปลง
      2. Safari 5 และ Chrome 9 ส่งเหตุการณ์การเปลี่ยนแปลง
    • สำหรับฟิลด์แบบฟอร์มอื่น:

      1. IE 7 และ IE 8 จะไม่ส่งเหตุการณ์การเปลี่ยนแปลง
      2. Firefox 4 จะส่งเหตุการณ์การเปลี่ยนแปลงเมื่อผู้ใช้เลือกค่าจากรายการคำแนะนำและแท็บนอกเขตข้อมูล
      3. Chrome 9 ไม่ส่งเหตุการณ์การเปลี่ยนแปลง
      4. Safari 5 ส่งเหตุการณ์การเปลี่ยนแปลง

ตัวเลือกที่ดีที่สุดคือการปิดใช้งานการเติมข้อความอัตโนมัติสำหรับแบบฟอร์มที่ใช้autocomplete="off"ในแบบฟอร์มหรือแบบสำรวจของคุณในช่วงเวลาปกติเพื่อดูว่าแบบฟอร์มนั้นกรอกหรือไม่

สำหรับคำถามของคุณเกี่ยวกับการกรอกข้อมูลในหรือก่อนหน้าเอกสารอีกครั้งมันจะแตกต่างกันไปจากเบราว์เซอร์เบราว์เซอร์และแม้แต่เวอร์ชันต่อเวอร์ชัน สำหรับฟิลด์ชื่อผู้ใช้ / รหัสผ่านเฉพาะเมื่อคุณเลือกฟิลด์รหัสผ่านชื่อผู้ใช้เต็มแล้ว ดังนั้นโดยรวมคุณจะมีรหัสยุ่งมากหากคุณพยายามแนบกับเหตุการณ์ใด ๆ

คุณสามารถอ่านได้ดีที่นี่


26
โปรดทราบว่าการเติมข้อความอัตโนมัติกับการป้อนอัตโนมัติมีความแตกต่าง OP หมายถึงเบราว์เซอร์ที่กรอกรายละเอียดการเข้าสู่ระบบที่บันทึกไว้ในการโหลดหน้าเว็บโดยเฉพาะ
Robbert

2
การแฮ็คตามปกติเป็นผู้วางเมาส์ในส่วนสำคัญของหน้า เหตุการณ์ได้รับการทริกเกอร์เป็นหัวเมาส์ของผู้ใช้สำหรับปุ่มหรือบางอย่าง
ไบรซ์

1
@Bryce โดยส่วนตัวฉันจะไปกับเหตุการณ์ 'เบลอ' เนื่องจากการป้อนอัตโนมัติเป็นสิ่งที่เกิดขึ้นหลังจากคุณเข้าสู่พื้นที่ป้อนข้อมูล เห็นได้ชัดว่ามันไม่เหมาะ แต่เป็นทางเลือกสำหรับเบราว์เซอร์ดังกล่าวข้างต้นมันจะมีประโยชน์มาก
JakeJ

อย่าลืมinputเหตุการณ์ นั่นคือสิ่งที่ Chrome ใช้กับการเติมข้อความอัตโนมัติ (และอาจป้อนอัตโนมัติเช่นกันหาก Chrome มีสิ่งนั้นฉันปิดสิ่งนี้ทุกครั้ง)
TJ Crowder

ดูคำตอบหนึ่งบรรทัดของฉันหากคุณต้องการทราบว่าค่าในกล่องข้อความนั้นถูกเติมด้วยการเติมข้อความอัตโนมัติของ Google Chrome หรือไม่
ThdK

71

โซลูชั่นสำหรับเบราว์เซอร์ WebKit

จาก MDN docs สำหรับ: -webkit-autofill CSS pseudo-class:

: -webkit-autofill CSS pseudo-class ตรงกันเมื่อองค์ประกอบมีค่าป้อนอัตโนมัติโดยเบราว์เซอร์

เราสามารถกำหนดกฎการเปลี่ยนแปลงโมฆะcss ใน<input>องค์ประกอบที่ต้องการได้เมื่อมีการ:-webkit-autofillแก้ไข จากนั้น JS จะสามารถขอเข้าร่วมanimationstartกิจกรรมได้

มอบเครดิตให้กับทีมKlarna UI ดูการใช้งานที่ดีของพวกเขาที่นี่:


1
นี่คือทางออกที่ดีที่สุด! ขอชื่นชมที่นี่สำหรับเรื่องนี้ ขอบคุณที่แบ่งปันวิธีการแก้ปัญหาของ Klarna UI ... ไม่มีอะไรได้ผลสำหรับฉันจนกว่าฉันจะพบสิ่งนี้ ช่วยชีวิต!
Braden Rockwell Napier

1
เช่นเดียวกับ CSS กฎคีย์เฟรมที่นี่github.com/klarna/ui/blob/v4.10.0/Field/styles.scss#L181-L189ก็มีความจำเป็น
1069816

สิ่งนี้ใช้ได้อย่างไร้ที่ติสำหรับฉัน! จำเป็นต้องเล่นรอบกับมันเล็กน้อยเพื่อคิดออกวิธีที่แน่นอน ขอบคุณทีม Klarna
pritesh

18

สิ่งนี้ใช้ได้กับฉันใน Firefox, Chrome และ Edge ล่าสุด:

$('#email').on('blur input', function() {
    ....
});

6
'input'! นี่เป็นวิธีที่ง่ายที่สุดสำหรับฉัน แต่ฉันทดสอบการเติมข้อความอัตโนมัติเท่านั้นไม่ใช่ป้อนอัตโนมัติ
GreenRaccoon23 23

เบลอไม่ทำงานสำหรับฉันด้วยโปรแกรมเสริมบางตัวที่สมบูรณ์แบบอัตโนมัติ
ผู้เบิกทาง

อินพุตจะทริกเกอร์ในทุกการกดปุ่ม หากคุณโทรเซิร์ฟเวอร์อาจทำให้เกิดบ่อยครั้ง
RiZKiT

สุดยอดทางออก! การรวมกันของเหตุการณ์นี้แก้ปัญหาด้วยการเติมตามผู้ใช้และป้อนอัตโนมัติโดยเบราว์เซอร์
Petr Hladík

17

สำหรับการเติมข้อความอัตโนมัติของ Google Chrome สิ่งนี้ใช้ได้กับฉัน:

if ($("#textbox").is(":-webkit-autofill")) 
{    
    // the value in the input field of the form was filled in with google chrome autocomplete
}

มันก็ใช้ได้สำหรับฉันเช่นกัน ฉันลองใช้วิธีการแก้ปัญหาหลายร้อยและไม่มีใครทำงาน ขอบคุณมากบันทึกวันของฉันและทุกครั้งที่ฉันค้นหาวิธีแก้ปัญหา
perozzo

4
วิธีนี้ทำให้เกิดข้อผิดพลาด: "ข้อผิดพลาดทางไวยากรณ์, การแสดงออกที่ไม่รู้จัก: หลอกไม่สนับสนุน: -webkit-autofill" บนเบราว์เซอร์อื่น (ฉันลองใช้ Firefox)
anvita surapaneni

1
ไม่ทำงานกับโครเมี่ยมและในปี 2020 แต่ยังโยนข้อผิดพลาดที่ไม่รู้จัก: หลอกไม่สนับสนุน: -webkit-autofill
Leo

15

ในกรณีที่มีใครบางคนกำลังมองหาวิธีการแก้ปัญหา (เช่นเดียวกับฉันในวันนี้) เพื่อฟังการเปลี่ยนแปลงการป้อนอัตโนมัติของเบราว์เซอร์นี่เป็นวิธีการ jquery แบบกำหนดเองที่ฉันสร้างขึ้นเพื่อลดความยุ่งยากในการประมวลผลเมื่อเพิ่มผู้ฟังการเปลี่ยนแปลง

    $.fn.allchange = function (callback) {
        var me = this;
        var last = "";
        var infunc = function () {
            var text = $(me).val();
            if (text != last) {
                last = text;
                callback();
            }
            setTimeout(infunc, 100);
        }
        setTimeout(infunc, 100);
    };

คุณสามารถโทรแบบนี้:

$("#myInput").allchange(function () {
    alert("change!");
});

1
ด้วยเหตุผลบางอย่างสำหรับฉันรหัสนี้ไม่ทำงานในการเปลี่ยนเส้นทางหน้า (เมื่อฉันออกจากระบบของแอพลิเคชันและได้รับการเปลี่ยนเส้นทางไปยังหน้าเข้าสู่ระบบที่มีการป้อนอัตโนมัติเกิดขึ้น) แม้ว่ามันจะทำงานในการรีเฟรชหน้า
VishwaKumar

1
ที่ดูเหมือนว่าอุปกรณ์ชาร์จแบตเตอรี่มือถือ: /
Stefan Fisk

@StefanFisk - ไม่จริงไม่ได้ การตั้งค่าตัวจับเวลาซ้ำ ๆ อย่างง่าย ๆ ที่ระดับ JS ของหน้าเบราว์เซอร์นั้นไม่เพียงพอที่จะส่งผลกระทบต่อแบตเตอรี่ของคุณเนื่องจากมีเกิดขึ้นมากมายในหน้าเว็บส่วนใหญ่ .... คุณคิดว่าgoogle.comไม่มีการตั้งเวลาซ้ำหรือไม่? ช่างเป็นข้อบกพร่องด้านการจัดการพลังงานถ้าฉันสามารถตั้งโปรแกรมง่ายๆด้วย JS หน้าเว็บที่ใช้พลังงานจากแบตเตอรี่ของผู้ใช้ ....
LcSalazar

15

ฉันอ่านเรื่องนี้มากและต้องการให้วิธีการแก้ปัญหาที่รวดเร็วซึ่งช่วยฉันได้

let style = window.getComputedStyle(document.getElementById('email'))
  if (style && style.backgroundColor !== inputBackgroundNormalState) {
    this.inputAutofilledByBrowser = true
  }

โดยที่inputBackgroundNormalStateสำหรับเทมเพลตของฉันคือ 'rgb (255, 255, 255)'

ดังนั้นโดยทั่วไปเมื่อเบราว์เซอร์ใช้การเติมข้อความอัตโนมัติพวกเขามักจะระบุว่าอินพุตถูกป้อนอัตโนมัติโดยใช้สีเหลือง (น่ารำคาญ) ที่แตกต่างกันในอินพุต

แก้ไข: ใช้ได้กับทุกเบราว์เซอร์


คิดดีมาก!
moto

7

น่าเสียดายที่วิธีเดียวที่เชื่อถือได้ฉันได้ตรวจสอบข้ามเบราว์เซอร์นี้คือการสำรวจความคิดเห็นอินพุต เพื่อให้ตอบสนองยังฟังเหตุการณ์ Chrome เริ่มซ่อนค่าเติมอัตโนมัติจาก javascript ซึ่งต้องการแฮ็ก

  • โพลทุกครึ่งถึงสามวินาที (ไม่จำเป็นต้องเป็นทันใจในกรณีส่วนใหญ่)
  • ทริกเกอร์เหตุการณ์การเปลี่ยนแปลงโดยใช้ JQuery จากนั้นทำลอจิกของคุณในฟังก์ชั่นเพื่อรับฟังเหตุการณ์การเปลี่ยนแปลง
  • เพิ่มการแก้ไขค่าป้อนรหัสผ่านอัตโนมัติของ Chrome ที่ซ่อนอยู่

    $(document).ready(function () {
        $('#inputID').change(YOURFUNCTIONNAME);
        $('#inputID').keypress(YOURFUNCTIONNAME);
        $('#inputID').keyup(YOURFUNCTIONNAME);
        $('#inputID').blur(YOURFUNCTIONNAME);
        $('#inputID').focusin(YOURFUNCTIONNAME);
        $('#inputID').focusout(YOURFUNCTIONNAME);
        $('#inputID').on('input', YOURFUNCTIONNAME);
        $('#inputID').on('textInput', YOURFUNCTIONNAME);
        $('#inputID').on('reset', YOURFUNCTIONNAME);
    
        window.setInterval(function() {
            var hasValue = $("#inputID").val().length > 0;//Normal
            if(!hasValue){
                hasValue = $("#inputID:-webkit-autofill").length > 0;//Chrome
            }
    
            if (hasValue) {
                $('#inputID').trigger('change');
            }
        }, 333);
    });

6

มีองค์ประกอบ polyfill ใหม่เพื่อแก้ไขปัญหานี้ใน Github มีลักษณะที่ป้อนอัตโนมัติเหตุการณ์ เพียงต้อง bower ติดตั้งและvoilàป้อนอัตโนมัติทำงานตามที่คาดไว้

bower install autofill-event

สิ่งนี้ใช้ได้ผลดีกับ jQuery Custom Forms ฉันทิ้งไว้และรายการเลือกแบบกำหนดเองของฉันทำงานได้ดีกับการป้อนอัตโนมัติ
Chris Bloom

6

ทางออกของฉัน:

ฟังchangeเหตุการณ์ตามปกติและในการโหลดเนื้อหา DOM ให้ทำดังนี้

setTimeout(function() {
    $('input').each(function() {
        var elem = $(this);
        if (elem.val()) elem.change();
    })
}, 250);

สิ่งนี้จะดำเนินการเหตุการณ์การเปลี่ยนแปลงสำหรับฟิลด์ทั้งหมดที่ไม่ว่างเปล่าก่อนที่ผู้ใช้จะมีโอกาสแก้ไข


สมบูรณ์ ทางออกแรกที่ฉันพบว่าทำงานกับ Chrome!
กำจัด Iculous

3
เป็น @RidIculous จริง ๆ แล้ววิธีแก้ปัญหาบางอย่างง่าย ๆ สามารถทำได้อย่างไร
Camilo Martin

3
แต่ elem.val () ส่งคืนสตริงว่างสำหรับฟิลด์รหัสผ่านที่ป้อนอัตโนมัติใน chrome :(
Hemant_Negi

@Hemant_Negi Chrome ไม่ส่งเหตุการณ์การเปลี่ยนแปลงหรือไม่ ช่วยแก้ให้ด้วยนะถ้าฉันผิด. ฉันใช้ LastPass และขี้เกียจเกินไปที่จะปิดการใช้งานเพื่อดูว่าใช้งานได้หรือไม่
Camilo Martin

1
ใช่เหตุการณ์เปลี่ยนการจัดส่งของ chrome แต่เมื่อฉันพยายามดึงค่ามันจะคืนค่าว่าง
Hemant_Negi

4

ฉันยังประสบปัญหาเดียวกันกับที่ฉลากไม่ได้ตรวจสอบการป้อนอัตโนมัติและภาพเคลื่อนไหวสำหรับการย้ายป้ายกำกับในการเติมข้อความทับซ้อนกันและวิธีนี้ใช้ได้สำหรับฉัน

input:-webkit-autofill ~ label {
    top:-20px;
} 

สิ่งนี้มีประโยชน์
rustyshackleford

สิ่งที่ฉันต้องการ :) :)
Dabrule

4

ฉันกำลังมองหาสิ่งที่คล้ายกัน Chrome เท่านั้น ... ในกรณีของฉัน Div wrapper จำเป็นต้องทราบว่าช่องป้อนข้อมูลถูกเติมอัตโนมัติหรือไม่ ดังนั้นฉันสามารถให้ css พิเศษได้เช่นเดียวกับ Chrome ที่ทำบนฟิลด์อินพุตเมื่อป้อนอัตโนมัติ โดยดูที่คำตอบทั้งหมดข้างต้นโซลูชันที่รวมกันของฉันคือต่อไปนี้:

/* 
 * make a function to use it in multiple places
 */
var checkAutoFill = function(){
    $('input:-webkit-autofill').each(function(){
        $(this).closest('.input-wrapper').addClass('autofilled');
    });
}

/* 
 * Put it on the 'input' event 
 * (happens on every change in an input field)
 */
$('html').on('input', function() {
    $('.input-wrapper').removeClass('autofilled');
    checkAutoFill();
});

/*
 * trigger it also inside a timeOut event 
 * (happens after chrome auto-filled fields on page-load)
 */
setTimeout(function(){ 
    checkAutoFill();
}, 0);

html สำหรับสิ่งนี้ในการทำงานจะเป็น

<div class="input-wrapper">
    <input type="text" name="firstname">
</div>

3

ฉันรู้ว่านี่เป็นเธรดเก่า แต่ฉันสามารถจินตนาการได้ว่าหลายคนมาหาวิธีแก้ไขปัญหานี้ได้ที่นี่

หากต้องการทำสิ่งนี้คุณสามารถตรวจสอบว่าอินพุตมีค่าด้วย:

$(function() {
    setTimeout(function() {
        if ($("#inputID").val().length > 0) {
            // YOUR CODE
        }
    }, 100);
});

ฉันใช้สิ่งนี้เพื่อตรวจสอบค่าในแบบฟอร์มการเข้าสู่ระบบเมื่อโหลดเพื่อเปิดใช้งานปุ่มส่ง รหัสนี้สร้างขึ้นสำหรับ jQuery แต่สามารถเปลี่ยนแปลงได้ง่ายหากจำเป็น


1
รหัสนี้ใช้งานได้ดีสำหรับฉันถ้าคุณอัปเดตบรรทัดที่สามเป็น($("#inputID:-webkit-autofill").val().length > 0) {
Hector

3

นี่เป็นวิธีแก้ปัญหาสำหรับเบราว์เซอร์ที่มีเอ็นจิ้นการสร้างเว็บคิต เมื่อกรอกฟอร์มอัตโนมัติอินพุตจะได้รับคลาสหลอก: -webkit-autofill- (อินพุต fe: -webkit-autofill {... }) ดังนั้นนี่คือตัวระบุสิ่งที่คุณต้องตรวจสอบผ่าน JavaScript

โซลูชันพร้อมแบบฟอร์มทดสอบบางส่วน:

<form action="#" method="POST" class="js-filled_check">

    <fieldset>

        <label for="test_username">Test username:</label>
        <input type="text" id="test_username" name="test_username" value="">

        <label for="test_password">Test password:</label>
        <input type="password" id="test_password" name="test_password" value="">

        <button type="submit" name="test_submit">Test submit</button>

    </fieldset>

</form>

และจาวาสคริปต์:

$(document).ready(function() {

    setTimeout(function() {

        $(".js-filled_check input:not([type=submit])").each(function (i, element) {

            var el = $(this),
                autofilled = (el.is("*:-webkit-autofill")) ? el.addClass('auto_filled') : false;

            console.log("element: " + el.attr("id") + " // " + "autofilled: " + (el.is("*:-webkit-autofill")));

        });

    }, 200);

});

ปัญหาเมื่อเพจโหลดคือค่ารหัสผ่านความยาว นี่เป็นเพราะความปลอดภัยของเบราว์เซอร์ นอกจากนี้การหมดเวลาเป็นเพราะเบราว์เซอร์จะกรอกแบบฟอร์มหลังจากลำดับเวลา

รหัสนี้จะเพิ่มคลาสauto_filledให้กับอินพุตที่กรอก นอกจากนี้ฉันพยายามตรวจสอบค่ารหัสผ่านประเภทอินพุตหรือความยาว แต่มันก็ใช้ได้หลังจากเหตุการณ์บางอย่างบนหน้ากระดาษเกิดขึ้น ดังนั้นฉันจึงพยายามเรียกใช้เหตุการณ์บางอย่าง แต่ไม่ประสบความสำเร็จ สำหรับตอนนี้นี่คือทางออกของฉัน สนุก!


นี่คือคำตอบล่าสุด
Ben Racicot

ฉันลองวิธีนี้และทำงานได้ดีมากสำหรับฉัน ขอบคุณมาก.
Marcus Crisostomo

2

ฉันมีทางออกที่สมบูรณ์แบบสำหรับคำถามนี้ลองใช้โค้ดขนาดสั้นนี้
การสาธิตอยู่ที่นี่

function ModernForm() {
    var modernInputElement = $('.js_modern_input');

    function recheckAllInput() {
        modernInputElement.each(function() {
            if ($(this).val() !== '') {
                $(this).parent().find('label').addClass('focus');
            }
        });
    }

    modernInputElement.on('click', function() {
        $(this).parent().find('label').addClass('focus');
    });
    modernInputElement.on('blur', function() {
        if ($(this).val() === '') {
            $(this).parent().find('label').removeClass('focus');
        } else {
            recheckAllInput();
        }
    });
}

ModernForm();
.form_sec {
  padding: 30px;
}
.form_sec .form_input_wrap {
  position: relative;
}
.form_sec .form_input_wrap label {
  position: absolute;
  top: 25px;
  left: 15px;
  font-size: 16px;
  font-weight: 600;
  z-index: 1;
  color: #333;
  -webkit-transition: all ease-in-out 0.35s;
  -moz-transition: all ease-in-out 0.35s;
  -ms-transition: all ease-in-out 0.35s;
  -o-transition: all ease-in-out 0.35s;
  transition: all ease-in-out 0.35s;
}
.form_sec .form_input_wrap label.focus {
  top: 5px;
  color: #a7a9ab;
  font-weight: 300;
  -webkit-transition: all ease-in-out 0.35s;
  -moz-transition: all ease-in-out 0.35s;
  -ms-transition: all ease-in-out 0.35s;
  -o-transition: all ease-in-out 0.35s;
  transition: all ease-in-out 0.35s;
}
.form_sec .form_input {
  width: 100%;
  font-size: 16px;
  font-weight: 600;
  color: #333;
  border: none;
  border-bottom: 2px solid #d3d4d5;
  padding: 30px 0 5px 0;
  outline: none;
}
.form_sec .form_input.err {
  border-bottom-color: #888;
}
.form_sec .cta_login {
  border: 1px solid #ec1940;
  border-radius: 2px;
  background-color: #ec1940;
  font-size: 14px;
  font-weight: 500;
  text-align: center;
  color: #ffffff;
  padding: 15px 40px;
  margin-top: 30px;
  display: inline-block;
}
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<form class="form_sec">
    <div class="row clearfix">
        <div class="form-group col-lg-6 col-md-6 form_input_wrap">
            <label>
                Full Name
            </label>
            <input type="text" name="name" id="name" class="form_input js_modern_input">
        </div>
    </div>
    <div class="row clearfix">
        <div class="form-group form_input_wrap col-lg-6 col-md-6">
            <label>
                Emaill
            </label>
            <input type="email" name="email" class="form_input js_modern_input">
        </div>
    </div>
    <div class="row clearfix">
        <div class="form-group form_input_wrap col-lg-12 col-md-12">
            <label>
                Address Line 1
            </label>
            <input type="text" name="address" class="form_input js_modern_input">
        </div>
    </div>
    <div class="row clearfix">
        <div class="form-group col-lg-6 col-md-6 form_input_wrap">
            <label>
                City
            </label>
            <input type="text" name="city" class="form_input js_modern_input">
        </div>
        <div class="form-group col-lg-6 col-md-6 form_input_wrap">
            <label>
                State
            </label>
            <input type="text" name="state" class="form_input js_modern_input">
        </div>
    </div>
    <div class="row clearfix">
        <div class="form-group col-lg-6 col-md-6 form_input_wrap">
            <label>
                Country
            </label>
            <input type="text" name="country" class="form_input js_modern_input">
        </div>
        <div class="form-group col-lg-4 col-md-4 form_input_wrap">
            <label>
                Pin
            </label>
            <input type="text" name="pincode" class="form_input js_modern_input">
        </div>
    </div>
    <div class="row cta_sec">
        <div class="col-lg-12">
            <button type="submit" class="cta_login">Submit</button>
        </div>
    </div>
</form>


2

บนโครเมี่ยมคุณสามารถตรวจหาฟิลด์ป้อนอัตโนมัติโดยการตั้งค่ากฎ CSS พิเศษสำหรับองค์ประกอบที่ป้อนอัตโนมัติแล้วตรวจสอบด้วย javascript หากองค์ประกอบมีการใช้กฎนั้น

ตัวอย่าง:

CSS

input:-webkit-autofill {
  -webkit-box-shadow: 0 0 0 30px white inset;
}

JavaScript

  let css = $("#selector").css("box-shadow")
  if (css.match(/inset/))
    console.log("autofilled:", $("#selector"))

2

นี่คือโซลูชัน CSS ที่นำมาจากทีม Klarna UI ดูการใช้งานที่ดีของพวกเขาที่นี่ทรัพยากร

ทำงานได้ดีสำหรับฉัน

input:-webkit-autofill {
  animation-name: onAutoFillStart;
  transition: background-color 50000s ease-in-out 0s;
}
input:not(:-webkit-autofill) {
  animation-name: onAutoFillCancel;
}

1

ฉันใช้วิธีนี้สำหรับปัญหาเดียวกัน

รหัส HTML ควรเปลี่ยนเป็น:

<input type="text" name="username" />
<input type="text" name="password" id="txt_password" />

และรหัส jQuery ควรอยู่ในdocument.ready:

$('#txt_password').focus(function(){
    $(this).attr('type','password');
});

0

ฉันใช้เหตุการณ์เบลอในชื่อผู้ใช้เพื่อตรวจสอบว่าฟิลด์ pwd ถูกป้อนอัตโนมัติ

 $('#userNameTextBox').blur(function () {
        if ($('#userNameTextBox').val() == "") {
            $('#userNameTextBox').val("User Name");
        }
        if ($('#passwordTextBox').val() != "") {
            $('#passwordTextBoxClear').hide(); // textbox with "Password" text in it
            $('#passwordTextBox').show();
        }
    });

สิ่งนี้ใช้ได้กับ IE และควรใช้ได้กับเบราว์เซอร์อื่น ๆ ทั้งหมด (ฉันได้ตรวจสอบเฉพาะ IE เท่านั้น)


@ChrisN ฉันทดสอบโซลูชันของฉันกับ IE แล้วเบราว์เซอร์จัดการกับเหตุการณ์ javascsript แตกต่างกัน โซลูชันของฉันนั้นง่ายและอ่านง่ายและเป็นหนึ่งในเบราว์เซอร์ที่ยากกว่าในการเขียนโค้ด
Bridget Arrington

1
ฉันจบลงด้วยโซลูชันเดียวกัน: blurเหตุการณ์ ฉันใช้ฟังก์ชั่นเดียวกันสำหรับchangeและblurกิจกรรมและมันใช้งานได้ดี ทางออกที่ง่ายโดยไม่ต้องมีห้องสมุดเพิ่มเติม
เปาโลตรวจสอบ

0

ฉันมีปัญหาเดียวกันและฉันได้เขียนวิธีแก้ปัญหานี้

มันเริ่มการสำรวจในทุก ๆ ช่องข้อมูลเมื่อหน้ากำลังโหลด (ฉันได้ตั้ง 10 วินาที แต่คุณสามารถปรับค่านี้)
หลังจากผ่านไป 10 วินาทีมันจะหยุดการสำรวจในทุกช่องสัญญาณเข้าและมันจะเริ่มทำการสำรวจเฉพาะสัญญาณเข้าที่ถูกโฟกัส (ถ้ามี) มันจะหยุดเมื่อคุณพร่ามัวอินพุตและเริ่มต้นอีกครั้งหากคุณโฟกัสที่หนึ่ง

ด้วยวิธีนี้คุณสำรวจความคิดเห็นเมื่อจำเป็นจริงๆและเฉพาะในการป้อนข้อมูลที่ถูกต้อง

// This part of code will detect autofill when the page is loading (username and password inputs for example)
var loading = setInterval(function() {
    $("input").each(function() {
        if ($(this).val() !== $(this).attr("value")) {
            $(this).trigger("change");
        }
    });
}, 100);
// After 10 seconds we are quite sure all the needed inputs are autofilled then we can stop checking them
setTimeout(function() {
    clearInterval(loading);
}, 10000);
// Now we just listen on the focused inputs (because user can select from the autofill dropdown only when the input has focus)
var focused;
$(document)
.on("focus", "input", function() {
    var $this = $(this);
    focused = setInterval(function() {
        if ($this.val() !== $this.attr("value")) {
            $this.trigger("change");
        }
    }, 100);
})
.on("blur", "input", function() {
    clearInterval(focused);
});

มันไม่ทำงานค่อนข้างดีเมื่อคุณมีหลายค่าที่แทรกโดยอัตโนมัติ แต่อาจ tweaked ค้นหาทุกอินพุทในรูปแบบปัจจุบัน

สิ่งที่ต้องการ:

// This part of code will detect autofill when the page is loading (username and password inputs for example)
var loading = setInterval(function() {
    $("input").each(function() {
        if ($(this).val() !== $(this).attr("value")) {
            $(this).trigger("change");
        }
    });
}, 100);
// After 10 seconds we are quite sure all the needed inputs are autofilled then we can stop checking them
setTimeout(function() {
    clearInterval(loading);
}, 10000);
// Now we just listen on inputs of the focused form
var focused;
$(document)
.on("focus", "input", function() {
    var $inputs = $(this).parents("form").find("input");
    focused = setInterval(function() {
        $inputs.each(function() {
            if ($(this).val() !== $(this).attr("value")) {
                $(this).trigger("change");
            }
        });
    }, 100);
})
.on("blur", "input", function() {
    clearInterval(focused);
});

0

หากคุณต้องการตรวจสอบว่ามีการใช้การเติมอัตโนมัติหรือไม่แทนที่จะตรวจสอบว่ามีการใช้การป้อนอัตโนมัติเมื่อใดและที่ใดในฟิลด์อัตโนมัติคุณสามารถเพิ่มองค์ประกอบที่ซ่อนอยู่ซึ่งจะถูกป้อนอัตโนมัติแล้วตรวจสอบว่า มีค่าใด ๆ ฉันเข้าใจว่านี่อาจจะไม่ใช่สิ่งที่หลาย ๆ คนสนใจตั้งค่าฟิลด์อินพุตด้วยแท็บลบดัชนีและด้วยค่าสัมบูรณ์จากหน้าจอ สิ่งสำคัญคืออินพุตเป็นส่วนหนึ่งของรูปแบบเดียวกับส่วนที่เหลือของอินพุต คุณต้องใช้ชื่อที่จะถูกรับโดย Auto-fill (เช่น "secondname")

var autofilldetect = document.createElement('input');
autofilldetect.style.position = 'absolute';
autofilldetect.style.top = '-100em';
autofilldetect.style.left = '-100em';
autofilldetect.type = 'text';
autofilldetect.name = 'secondname';
autofilldetect.tabIndex = '-1';

ผนวกอินพุตนี้กับแบบฟอร์มและตรวจสอบค่าในแบบฟอร์มการส่ง


0

มีไม่ดูเหมือนจะเป็นวิธีแก้ปัญหานี้ไม่ได้ขึ้นอยู่กับการเลือกตั้ง (อย่างน้อยสำหรับ Chrome) มันเกือบจะเป็นแฮ็ค แต่ฉันคิดว่าดีกว่าการสำรวจทั่วโลกเล็กน้อย

พิจารณาสถานการณ์สมมติต่อไปนี้:

  1. ผู้ใช้เริ่มกรอกฟิลด์ 1

  2. ผู้ใช้เลือกคำแนะนำการเติมข้อความอัตโนมัติที่ป้อนอัตโนมัติ field2 และ field3

วิธีการแก้ไข: ลงทะเบียน onblur ในทุกสาขาที่ตรวจสอบว่ามีฟิลด์ที่ป้อนอัตโนมัติผ่าน jQuery snippet $ ต่อไปนี้ (': - webkit-autofill')

สิ่งนี้จะไม่เกิดขึ้นทันทีเนื่องจากมันจะล่าช้าจนกว่าผู้ใช้จะพร่ามัว field1 แต่มันไม่ได้พึ่งพาการสำรวจทั่วโลกดังนั้น IMO จึงเป็นทางออกที่ดีกว่า

ที่กล่าวว่าเนื่องจากการกดปุ่ม Enter สามารถส่งแบบฟอร์มคุณอาจต้องใช้ตัวจัดการที่เกี่ยวข้องสำหรับ onkeypress

คุณสามารถใช้การสำรวจทั่วโลกเพื่อตรวจสอบ $ (': - webkit-autofill')


0

จากประสบการณ์ส่วนตัวของฉันรหัสด้านล่างทำงานได้ดีกับ firefox IE และ safari แต่ทำงานได้ไม่ดีในการเลือกการเติมข้อความอัตโนมัติใน Chrome

function check(){
clearTimeout(timeObj);
 timeObj = setTimeout(function(){
   if($('#email').val()){
    //do something
   }
 },1500);
}

$('#email').bind('focus change blur',function(){
 check();
});

โค้ดด้านล่างใช้งานได้ดีกว่าเพราะมันจะทริกเกอร์ทุกครั้งเมื่อผู้ใช้คลิกที่ช่องป้อนข้อมูลและจากนั้นคุณสามารถตรวจสอบช่องใส่ที่ว่างเปล่าได้หรือไม่

$('#email').bind('click', function(){
 check();
});

0

ฉันประสบความสำเร็จกับ chrome ด้วย:

    setTimeout(
       function(){
          $("#input_password").focus();
          $("#input_username").focus();
          console.log($("#input_username").val());
          console.log($("#input_password").val());
       }
    ,500);

ไม่แน่ใจว่าเมื่อใดที่ Chrome ป้อนอัตโนมัติจะทำงาน แต่ใน $ ('ป้อน, เลือก'). เปิด ('focusin', ฟังก์ชั่น (EVT) {... }); ฉันได้รับค่าป้อนอัตโนมัติสำหรับเขตข้อมูลทั้งหมดแล้ว
mirek

เวอร์ชั่นใหม่อาจจะ?
แอนทอนโอ

0

ทางออกของฉันคือ

    $.fn.onAutoFillEvent = function (callback) {
        var el = $(this),
            lastText = "",
            maxCheckCount = 10,
            checkCount = 0;

        (function infunc() {
            var text = el.val();

            if (text != lastText) {
                lastText = text;
                callback(el);
            }
            if (checkCount > maxCheckCount) {
                return false;
            }
            checkCount++;
            setTimeout(infunc, 100);
        }());
    };

  $(".group > input").each(function (i, element) {
      var el = $(element);

      el.onAutoFillEvent(
          function () {
              el.addClass('used');
          }
      );
  });

คำอธิบายสำหรับวิธีแก้ปัญหาของคุณจะช่วยได้
ตัน

ฉันคิดว่ามันชัดเจน ดังนั้นแนวคิดโดยทั่วไปคือการตรวจสอบค่าของฟิลด์อินพุตสองเท่า ในการใช้งานในปัจจุบันจะมี 10 ครั้งโดยมีความล่าช้า 100 ms ดังนั้นเมื่อในช่วง 10 * 1000 = 1 วินาทีเบราว์เซอร์ที่เติมค่าป้อนอัตโนมัติการโทรกลับที่ส่งไปที่ป้อนอัตโนมัติจะถูกเรียก ในตัวอย่างปัจจุบันมันเพิ่งเพิ่มคลาส หากคุณมีคำถามเพิ่มเติมโปรดอย่าลังเลและเพียงแค่ถาม :)
Romick

0

หลังจากการวิจัยปัญหาคือเบราว์เซอร์ webkit จะไม่ดำเนินการเหตุการณ์การเปลี่ยนแปลงในการเติมข้อความอัตโนมัติ ทางออกของฉันคือการได้รับชั้นป้อนอัตโนมัติที่ webkit เพิ่มและทริกเกอร์เหตุการณ์การเปลี่ยนแปลงด้วยตนเอง

setTimeout(function() {
 if($('input:-webkit-autofill').length > 0) {
   //do some stuff
 }
},300)

นี่คือลิงค์สำหรับปัญหาในโครเมียม https://bugs.chromium.org/p/chromium/issues/detail?id=636425


0

เมื่อต้องการตรวจสอบอีเมลฉันลอง "เปลี่ยน" และผู้สังเกตการณ์การกลายพันธุ์ไม่ทำงาน setInterval ทำงานได้ดีกับการป้อนอัตโนมัติของ LinkedIn (ไม่เปิดเผยรหัสของฉันทั้งหมด แต่คุณได้รับแนวคิด) และมันเล่นได้ดีกับแบ็กเอนด์ถ้าคุณเพิ่มเงื่อนไขพิเศษที่นี่เพื่อชะลอ AJAX และหากไม่มีการเปลี่ยนแปลงในเขตข้อมูลฟอร์มเหมือนพวกเขาไม่ได้พิมพ์เพื่อแก้ไขอีเมลของพวกเขา LastEmail ป้องกันไม่ให้ AJAX ส่ง Ping ไร้จุดหมาย

// lastEmail needs scope outside of setInterval for persistence.
var lastEmail = 'nobody';
window.setInterval(function() { // Auto-fill detection is hard.
    var theEmail = $("#email-input").val();
    if (
        ( theEmail.includes("@") ) &&
        ( theEmail != lastEmail )
    ) {
        lastEmail = theEmail;
        // Do some AJAX
    }
}, 1000); // Check the field every 1 second

0

ฉันมีปัญหาในการตรวจหาการเติมคำอัตโนมัติใน Firefox นี่เป็นทางออกเดียวที่ได้ผลสำหรับฉัน:

การสาธิต

HTML:

<div class="inputFields">
   <div class="f_o">
      <div class="field_set">
        <label class="phold">User</label>
        <input type="tel" class="form_field " autocomplete="off" value="" maxlength="50">
      </div>
   </div>
   <div class="f_o">
      <div class="field_set">
         <label class="phold">Password</label>
         <input type="password" class="form_field " autocomplete="off" value="" maxlength="50">
      </div>
   </div>
</div>

CSS:

/* Detect autofill for Chrome */
.inputFields input:-webkit-autofill {
    animation-name: onAutoFillStart;
    transition: background-color 50000s ease-in-out 0s;
}
.inputFields input:not(:-webkit-autofill) {
    animation-name: onAutoFillCancel;
}

@keyframes onAutoFillStart {
}

@keyframes onAutoFillCancel {
}
.inputFields {
  max-width: 414px;
}

.field_set .phold{
  display: inline-block;
  position: absolute;
  font-size: 14px;
  color: #848484;
  -webkit-transform: translate3d(0,8px,0);
  -ms-transform: translate3d(0,8px,0);
  transform: translate3d(0,8px,0);
  -webkit-transition: all 200ms ease-out;
  transition: all 200ms ease-out;
  background-color: transparent;
  -webkit-backface-visibility: hidden;
  backface-visibility: hidden;
  margin-left: 8px;
  z-index: 1;
  left: 0;
  pointer-events: none;
}

.field_set .phold_active {
   font-size: 12px;
   -webkit-transform: translate3d(0,-8px,0);
  -ms-transform: translate3d(0,-8px,0);
  transform: translate3d(0,-8px,0);
  background-color: #FFF;
  padding-left: 3px;
  padding-right: 3px;
}

.field_set input[type='text'], .field_set select, .field_set input[type='tel'], .field_set input[type='password'] {
    height: 36px;
}

.field_set input[type='text'], .field_set input[type='tel'], .field_set input[type='password'], .field_set select, .field_set textarea {
    box-sizing: border-box;
    width: 100%;
    padding: 5px;
    -webkit-appearance: none;
    -moz-appearance: none;
    appearance: none;
    border: 1px solid #ababab;
    border-radius: 0;
}

.field_set {
    margin-bottom: 10px;
    position: relative;
}

.inputFields .f_o {
    width: 100%;
    line-height: 1.42857143;
    float: none;
}

JavaScript:

    // detect auto-fill when page is loading
  $(window).on('load', function() {
    // for sign in forms when the user name and password are filled by browser
    getAutofill('.inputFields');
  });

  function getAutofill(parentClass) {
    if ($(parentClass + ' .form_field').length > 0) {    
      var formInput = $(parentClass + ' .form_field');
      formInput.each(function(){   
        // for Chrome:  $(this).css('animation-name') == 'onAutoFillStart'
        // for Firefox: $(this).val() != ''
        if ($(this).css('animation-name') == 'onAutoFillStart' || $(this).val() != '') {
          $(this).siblings('.phold').addClass('phold_active');
        } else {
          $(this).siblings('.phold').removeClass('phold_active');
        }
      });
    }
  } 

  $(document).ready(function(){

    $(document).on('click','.phold',function(){
      $(this).siblings('input, textarea').focus();
    });
    $(document).on('focus','.form_field', function(){
      $(this).siblings('.phold').addClass('phold_active');
    });

    // blur for Chrome and change for Firefox
    $(document).on('blur change','.form_field', function(){
      var $this = $(this);
      if ($this.val().length == 0) {        
        $(this).siblings('.phold').removeClass('phold_active');
      } else {
        $(this).siblings('.phold').addClass('phold_active');
      }
    });

    // case when form is reloaded due to errors
    if ($('.form_field').length > 0) {
      var formInput = $('.form_field');
      formInput.each(function(){
        if ($(this).val() != '') {
          $(this).siblings('.phold').addClass('phold_active');
        } else {
          $(this).siblings('.phold').removeClass('phold_active');
        }
      });
    }

  }); 

สำหรับ Chrome ฉันใช้: if ($(this).css('animation-name') == 'onAutoFillStart')

สำหรับ Firefox: if ($(this).val() != '')


โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.