如何通过Aframe组件恢复元素初始值?——悬停后缩放属性无法恢复的问题解决
解决A-Frame组件中鼠标离开时Scale属性无法恢复初始值的问题
这个问题我之前也碰到过,根源在于A-Frame对vec3这类对象类型属性的处理方式。你直接保存el.getAttribute('scale')的引用,但这个返回的对象是实时绑定到元素属性的——当你在mouseenter事件里修改元素的scale时,你存在defaultScale里的那个对象的属性也会跟着被更新,导致鼠标离开时你设置的其实是已经被改变后的scale值,而不是最初的初始值。
修复方案:深拷贝初始Scale值
只需要在保存初始scale的时候,创建一个独立的副本,而不是直接引用A-Frame返回的实时对象。可以用对象解构或者Object.assign来实现深拷贝:
修改后的完整组件代码:
AFRAME.registerComponent('change-hotspots-on-hover', { schema: { src: {default: '#hotspots'}, scale: {type: 'vec3', default: {x: 1, y: 1, z: 1}}, }, init: function () { var data = this.data; var el = this.el; var defaultSrc = el.getAttribute('src'); // 用解构语法创建初始scale的副本,避免引用实时对象 var defaultScale = {...el.getAttribute('scale')}; // 也可以用Object.assign:var defaultScale = Object.assign({}, el.getAttribute('scale')); console.log("Init"); el.addEventListener('mouseenter', function (){ console.log("Enter"); el.setAttribute('src', data.src); // 其实这里的setTimeout可以去掉,直接设置scale就行 el.setAttribute('scale', data.scale); }); el.addEventListener('mouseleave', function (){ console.log("Exit"); el.setAttribute('src', defaultSrc); el.setAttribute('scale', defaultScale); }); } });
原理说明
- A-Frame的
getAttribute('scale')返回的是框架内部维护的一个对象,元素的scale属性变化时,这个对象的x/y/z值会自动同步更新。 - 通过
{...}或者Object.assign创建新对象,我们把初始的scale值复制到了一个完全独立的对象中,后续元素scale的任何变化都不会影响这个保存的默认值,这样鼠标离开时就能正确重置了。
另外,你原来代码里的setTimeout其实没必要,直接设置scale属性就能正常生效,去掉后代码会更简洁。
内容的提问来源于stack exchange,提问作者Clovinoux
相关产品推荐
相关产品推荐

