Javascript 检测浏览器自动填充
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/11708092/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
Detecting Browser Autofill
提问by Undefined
How do you tell if a browser has auto filled a text-box? Especially with username & password boxes that autofill around page load.
如何判断浏览器是否自动填充了文本框?尤其是在页面加载时自动填充的用户名和密码框。
My first question is when does this occur in the page load sequence? Is it before or after document.ready?
我的第一个问题是页面加载顺序中何时会出现这种情况?它是在 document.ready 之前还是之后?
Secondly how can I use logic to find out if this occurred? Its not that i want to stop this from occurring, just hook into the event. Preferably something like this:
其次,我如何使用逻辑来确定是否发生了这种情况?不是我想阻止这种情况发生,只是挂接到事件中。最好是这样的:
if (autoFilled == true) {
} else {
}
If possible I would love to see a jsfiddle showing your answer.
如果可能的话,我很想看到一个 jsfiddle 显示你的答案。
Possible duplicates
可能重复
DOM event for browser password autofill?
Browser Autofill and Javascript triggered events
--Both these questions don't really explain what events are triggered, they just continuously recheck the text-box (not good for performance!).
--这两个问题都没有真正解释触发了什么事件,它们只是不断地重新检查文本框(不利于性能!)。
采纳答案by afrin216
The problem is autofill is handled differently by different browsers. Some dispatch the change event, some don't. So it is almost impossible to hook onto an event which is triggered when browser autocompletes an input field.
问题是不同浏览器对自动填充的处理方式不同。有些派发 change 事件,有些不派发。因此,几乎不可能挂钩浏览器自动完成输入字段时触发的事件。
Change event trigger for different browsers:
For username/password fields:
- Firefox 4, IE 7, and IE 8 don't dispatch the change event.
- Safari 5 and Chrome 9 do dispatch the change event.
For other form fields:
- IE 7 and IE 8 don't dispatch the change event.
- Firefox 4 does dispatch the change change event when users select a value from a list of suggestions and tab out of the field.
- Chrome 9 does not dispatch the change event.
- Safari 5 does dispatch the change event.
不同浏览器的更改事件触发器:
对于用户名/密码字段:
- Firefox 4、IE 7 和 IE 8 不分派 change 事件。
- Safari 5 和 Chrome 9 确实会调度 change 事件。
对于其他表单字段:
- IE 7 和 IE 8 不分派 change 事件。
- 当用户从建议列表中选择一个值并从该字段中选择一个选项卡时,Firefox 4 确实会调度 change change 事件。
- Chrome 9 不会调度 change 事件。
- Safari 5 确实会调度 change 事件。
You best options are to either disable autocomplete for a form using autocomplete="off"
in your form or poll at regular interval to see if its filled.
您最好的选择是禁用表单中使用autocomplete="off"
的表单的自动完成功能,或者定期轮询以查看其是否已填写。
For your question on whether it is filled on or before document.ready again it varies from browser to browser and even version to version. For username/password fields only when you select a username password field is filled. So altogether you would have a very messy code if you try to attach to any event.
对于您关于它是在 document.ready 上还是之前填写的问题,它因浏览器而异,甚至因版本而异。对于用户名/密码字段,仅当您选择用户名时才会填写密码字段。因此,如果您尝试附加到任何事件,那么总的来说您将拥有一个非常混乱的代码。
You can have a good read on this HERE
你可以在这里好好读一读
回答by Lev Kazakov
Solution for WebKit browsers
WebKit 浏览器解决方案
From the MDN docs for the :-webkit-autofillCSS pseudo-class:
来自:-webkit-autofillCSS 伪类的 MDN 文档:
The :-webkit-autofill CSS pseudo-class matches when an element has its value autofilled by the browser
:-webkit-autofill CSS 伪类在元素具有由浏览器自动填充的值时匹配
We can define a void transitioncss rule on the desired <input>
element once it is :-webkit-autofill
ed. JS will then be able to hook onto the animationstart
event.
一旦它被编辑,我们就可以在所需的元素上定义一个void transitioncss规则。然后 JS 将能够挂钩该事件。<input>
:-webkit-autofill
animationstart
Credits to the Klarna UIteam. See their nice implementation here:
感谢Klarna UI团队。在这里看到他们很好的实现:
回答by James
This works for me in the latest Firefox, Chrome, and Edge:
这在最新的 Firefox、Chrome 和 Edge 中对我有用:
$('#email').on('blur input', function() {
....
});
回答by ThdK
For google chrome autocomplete, this worked for me:
对于谷歌浏览器自动完成,这对我有用:
if ($("#textbox").is(":-webkit-autofill"))
{
// the value in the input field of the form was filled in with google chrome autocomplete
}
回答by LcSalazar
Just in case someone is looking for a solution (just as I was today), to listen to a browser autofill change, here's a custom jquery method that I've built, just to simplify the proccess when adding a change listener to an input:
以防万一有人正在寻找解决方案(就像我今天一样),要侦听浏览器自动填充更改,这是我构建的自定义 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);
};
You can call it like this:
你可以这样称呼它:
$("#myInput").allchange(function () {
alert("change!");
});
回答by DrNio
I was reading a lot about this issue and wanted to provide a very quick workaround that helped me.
我阅读了很多关于这个问题的文章,并希望提供一个非常快速的解决方法来帮助我。
let style = window.getComputedStyle(document.getElementById('email'))
if (style && style.backgroundColor !== inputBackgroundNormalState) {
this.inputAutofilledByBrowser = true
}
where inputBackgroundNormalState
for my template is 'rgb(255, 255, 255)'.
inputBackgroundNormalState
我的模板在哪里是 'rgb(255, 255, 255)'。
So basically when browsers apply autocomplete they tend to indicate that the input is autofilled by applying a different (annoying) yellow color on the input.
所以基本上当浏览器应用自动完成时,他们倾向于通过在输入上应用不同的(烦人的)黄色来指示输入是自动填充的。
Edit : this works for every browser
编辑:这适用于每个浏览器
回答by Bucket
Unfortunately the only reliable way i have found to check this cross browser is to poll the input. To make it responsive also listen to events. Chrome has started hiding auto fill values from javascript which needs a hack.
不幸的是,我发现检查这个跨浏览器的唯一可靠方法是轮询输入。为了使其响应,还可以侦听事件。Chrome 已开始从需要 hack 的 javascript 隐藏自动填充值。
- Poll every half to third of a second ( Does not need to be instant in most cases )
- Trigger the change event using JQuery then do your logic in a function listening to the change event.
Add a fix for Chrome hidden autofill password values.
$(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); });
- 每半秒到三分之一秒轮询一次(在大多数情况下不需要即时)
- 使用 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); });
回答by David
There is a new polyfill component to address this issue on github. Have a look at autofill-event. Just need to bower install it and voilà, autofill works as expected.
github 上有一个新的 polyfill 组件来解决这个问题。看看autofill-event。只需要 bower 安装它,瞧,自动填充按预期工作。
bower install autofill-event
回答by Camilo Martin
My solution:
我的解决方案:
Listen to change
events as you would normally, and on the DOM content load, do this:
change
像往常一样收听事件,并在 DOM 内容加载时执行以下操作:
setTimeout(function() {
$('input').each(function() {
var elem = $(this);
if (elem.val()) elem.change();
})
}, 250);
This will fire the change events for all the fields that aren't empty before the user had a chance to edit them.
在用户有机会编辑它们之前,这将为所有非空字段触发更改事件。
回答by Julesezaar
I was looking for a similar thing. Chrome only... In my case the wrapper div needed to know if the input field was autofilled. So I could give it extra css just like Chrome does on the input field when it autofills it. By looking at all the answers above my combined solution was the following:
我正在寻找类似的东西。仅 Chrome... 在我的情况下,包装 div 需要知道输入字段是否已自动填充。所以我可以给它额外的 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);
The html for this to work would be
这个工作的html将是
<div class="input-wrapper">
<input type="text" name="firstname">
</div>