猿问

如何解决 chrome 自动完成与 vuetify 中的标签重叠的问题?

outlined尝试在 Vutify中创建带有文本字段的登录表单时,chrome 自动完成功能与labels,


<v-text-field

  v-model="email"

  label="e-mail"

  name="email"

  outlined

  prepend-icon="mdi-account"

  type="text"

  required

>

</v-text-field>

你可以在这里重新生成请填写并提交,然后返回。



MYYA
浏览 199回答 5
5回答

回首忆惘然

这就是我解决这个问题的方法。看来我们的主要问题如下:Chrome 的自动填充,在加载页面时,不会让界面做出反应,让设计像你的图像一样。所以在注入的时候,我们应该自己做一个修复,但是当登录名/密码被自动填充时,Chrome 没有任何事件可以通知我们。有趣的是,浏览器窗口中的任何点击 FROM USER 都会自动通知反应性,并且一切正常,但 FROM 触发器/调度内部方式不起作用。所以首先,我们需要找到一种在登录/密码自动填充后做出反应的方法。其次,我们需要自己修复设计,因为只有 FROM USER 操作才能使设计再次正常工作。1.加载页面自动填充后反应就像 Harkness 提到的那样,我们可以尝试:-webkit-autofill在安装代码后的 X 秒内定期检查以查看是否注入了自动填充(从我的测试来看,Chrome/Firefox/Edge 工作正常)另一种解决方案是使用animationstart事件(参见此处:https&nbsp;://github.com/material-components/material-components-web/issues/4447#issuecomment-580401216 )我使用第一个解决方案:export default {&nbsp; //...&nbsp; data() {&nbsp; &nbsp; return {&nbsp; &nbsp; &nbsp; //...&nbsp; &nbsp; &nbsp; autofillFix: false,&nbsp; &nbsp; }&nbsp; },&nbsp; //...&nbsp; mounted() {&nbsp; &nbsp; this.autoLoginCheckingInterface()&nbsp; },&nbsp; //...&nbsp; autoLoginCheckingInterface() {&nbsp; &nbsp; // each 100ms we check if the issue was produced&nbsp; &nbsp; let intervalDetectAutofill = setInterval(() => {&nbsp; &nbsp; &nbsp; if (&nbsp; &nbsp; &nbsp; &nbsp; // we target at least one of the stuff that will be affected by autofill&nbsp; &nbsp; &nbsp; &nbsp; // to do our checking&nbsp; &nbsp; &nbsp; &nbsp; document.querySelectorAll('input[type="password"]:-webkit-autofill')&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; .length > 0&nbsp; &nbsp; &nbsp; ) {&nbsp; &nbsp; &nbsp; &nbsp; // and we inform the system about the issue if it is produced&nbsp; &nbsp; &nbsp; &nbsp; this.autofillFix = true&nbsp; &nbsp; &nbsp; &nbsp; // we stop to check if issue was produced&nbsp; &nbsp; &nbsp; &nbsp; clearInterval(intervalDetectAutofill)&nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }, 100)&nbsp; &nbsp; // if after 3s nothing appear, means no autofill was made&nbsp; &nbsp; setTimeout(() => {&nbsp; &nbsp; &nbsp; if (intervalDetectAutofill) {&nbsp; &nbsp; &nbsp; &nbsp; clearInterval(intervalDetectAutofill)&nbsp; &nbsp; &nbsp; &nbsp; intervalDetectAutofill = null&nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; }, 3000)&nbsp; },&nbsp; //...}<!--we will inject `.autofill-fix` class to be able fix design ourself at time of this bug occur-->&nbsp;<v-text-field&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; :class="{ 'autofill-fix': autofillFix }"&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; label="Email address or username"&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; dense&nbsp; &nbsp; &nbsp; outlined&nbsp; &nbsp; &nbsp; @focus="autofillFix = false"/><!--we use @focus to let the normal behavior take again the leadbecause we know this USER ACTION will made Chrome work well again--><v-text-field&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; :class="{ 'autofill-fix': autofillFix }"&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; label="Password"&nbsp; &nbsp; &nbsp; type="password"&nbsp; &nbsp; &nbsp; ...&nbsp; &nbsp; &nbsp; dense&nbsp; &nbsp; &nbsp; outlined&nbsp; &nbsp; &nbsp; @focus="autofillFix = false"/>2. 修正自己的设计v-text-field我们可以看到填充时有什么变化。没有内容,我们可以看到:自动填充后,我们可以看到:所以从红色部分,我们可以看到需要在存在时注入以下代码以.autofill-fix正确的方式修复设计.autofill-fix.v-text-field--outlined.v-input--dense .v-label {&nbsp; left: -28px!important;&nbsp; transform: translateY(-16px) scale(.75);}注意:如果不使用outlinedor ,则需要更改 CSS 选择器dense。注意选择器https://specificity.keegan.st/的特异性。事实上,您需要使固定更改适应您的设计

哆啦的时光机

我相信我已经用非常通用的几行代码取得了很好的结果。&nbsp;mounted() {&nbsp; &nbsp; setTimeout(() => {&nbsp; &nbsp; &nbsp; const els = document.querySelectorAll("input:-webkit-autofill")&nbsp; &nbsp; &nbsp; els.forEach((el) => {&nbsp; &nbsp; &nbsp; &nbsp; const label = el.parentElement.querySelector("label")&nbsp; &nbsp; &nbsp; &nbsp; label.classList.add("v-label--active")&nbsp; &nbsp; &nbsp; })&nbsp; &nbsp; }, 500)&nbsp; },如果浏览器自动填充 v-text-field,此代码会将“active”类添加到 Label。v-text-field 的行为没有变化。

一只斗牛犬

另一种方法是像@elazard在这里建议这样定义一个自动填充变量data () {&nbsp; &nbsp; &nbsp; &nbsp; return {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; login: null,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; password: null,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; autofill: false,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; intervalDetectAutofill: null&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; },<v-text-field&nbsp; &nbsp; v-model="password"&nbsp; &nbsp; type="password"&nbsp; &nbsp; label="Password"&nbsp; &nbsp; :placeholder="autofill ? ` ` : null"/>使用@adam-reis 给出的解决方案mounted(),在登录页面的mounted () {&nbsp; &nbsp; &nbsp; &nbsp; // search for autofill every 100ms&nbsp; &nbsp; &nbsp; &nbsp; this.intervalDetectAutofill = setInterval(() => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (document.querySelectorAll("input[type=\"password\"]:-webkit-autofill").length > 0) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.autofill = true&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; }, 100)&nbsp; &nbsp; &nbsp; &nbsp; // clean interval if needed after 3s&nbsp; &nbsp; &nbsp; &nbsp; setTimeout(() => {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (this.intervalDetectAutofill) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; clearInterval(this.intervalDetectAutofill)&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.intervalDetectAutofill = null&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; }, 3000)&nbsp; &nbsp; },当然,如果用户输入,则将自动填充设置为 falsewatch: {&nbsp; &nbsp; &nbsp; &nbsp; password () {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.autofill = false&nbsp; &nbsp; &nbsp; &nbsp; },&nbsp; &nbsp; &nbsp; &nbsp; autofill () {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; // clean interval if autofill detected or user input&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; if (this.intervalDetectAutofill) {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; clearInterval(this.intervalDetectAutofill)&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; this.intervalDetectAutofill = null&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; &nbsp; &nbsp; }&nbsp; &nbsp; },

智慧大石

好的,所以我所做的是这样的:在输入:placeholder="!autofilled ? ' ' : ''"在脚本中data() {&nbsp; &nbsp; &nbsp; &nbsp; return {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; form: {&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; email: '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; password: '',&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; },&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; error: null,&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; autofilled: false,&nbsp; &nbsp; &nbsp; &nbsp; };},watch: {&nbsp; &nbsp; 'form.email'() {&nbsp; &nbsp; &nbsp; &nbsp; this.autofilled = true;&nbsp; &nbsp; &nbsp;},},它的作用:基本上将占位符设置为一个空格总是“提升”标签。不幸的是,静态设置它会使标签无法返回,即使您在填充后清空输入。所以我所做的是使占位符动态化,并且在该占位符恢复为空后对输入进行任何更改之前仅将其设置为空白。它并不完美,因为在用户保存密码之前的初始加载时,标签会被提升,但我还没有发现比这更好的东西。

喵喵时光机

浏览器上的自动填充功能通常通过直接设置相关字段的值来工作。在这种情况下,字段的标签仅在输入字段获得焦点时才移开,而在与字段中的值模糊时则远离。在自动填充的情况下,不会触发焦点事件,因此标签会保留在原处。要解决此问题,您必须(或让某人)在 Vuetify 中进行更改。
随时随地看视频慕课网APP

相关分类

JavaScript
我要回答