Vue3中按钮加载Spinner无法停止问题求助(附代码)
解决Vue组件中grecaptcha回调里无法修改loading状态的问题
问题原因
你遇到的错误是因为回调函数的this指向不对:grecaptcha.ready()和grecaptcha.execute()里用的是普通function,这类函数会改变this的指向,不再指向Vue组件实例。即使onSuccess用了箭头函数,它继承的是外层普通函数的this(浏览器环境下是window),自然无法访问组件的loading属性。
解决方案
有两种简单的修复方式:
方案1:提前保存Vue实例引用
在recaptcha方法开头把组件实例的this存到一个变量里,后续所有需要访问组件数据的地方都用这个变量代替this:
export default { name: 'form-loading-spinner', data(){ return{ loading: false, form : { phone: "", token: null, }, } }, methods:{ recaptcha(){ const vm = this; // 保存组件实例引用 vm.loading = true; let form = vm.form; grecaptcha.ready(function() { grecaptcha.execute('XXXXXXXXXXXXXXXXXX', {action: 'submit'}).then(function(token) { form.token = token; Inertia.post("/phone/send", form, { preserveScroll: true, onSuccess: () => vm.loading = false // 用vm访问loading }) }); }) }, reset(){ this.loading = false; }, } }
方案2:把所有回调改成箭头函数
箭头函数不会改变this指向,会继承外层作用域的this(也就是Vue组件实例),所以把grecaptcha.ready()和grecaptcha.execute()里的回调都换成箭头函数即可:
export default { name: 'form-loading-spinner', data(){ return{ loading: false, form : { phone: "", token: null, }, } }, methods:{ recaptcha(){ this.loading = true; let form = this.form; grecaptcha.ready(() => { // 改成箭头函数 grecaptcha.execute('XXXXXXXXXXXXXXXXXX', {action: 'submit'}).then((token) => { // 改成箭头函数 form.token = token; Inertia.post("/phone/send", form, { preserveScroll: true, onSuccess: () => this.loading = false }) }); }) }, reset(){ this.loading = false; }, } }
额外提示
注意你按钮上的:disabled="form.processing",如果form.processing不是组件数据里的属性,建议改成:disabled="loading",让按钮禁用状态和Spinner的显示状态保持一致,避免出现状态不同步的问题。
内容的提问来源于stack exchange,提问作者Марк Мина
相关产品推荐
相关产品推荐

