simlimsd3
simlimsd3

Reputation: 619

How can I make my entity spin when the user hovers over it?

I am using the event-set-component to cause my obj model under to increase scale when the cursor hovers over it.

This is working correctly.

But how would I make it spin as well as increase size?

I found the following code on AFrame docs but I do not know how to implement it so it triggers when the mouse is over the entity.

<a-animation attribute="material.opacity" begin="fade" to="0"></a-animation>

Upvotes: 0

Views: 349

Answers (2)

Piotr Adam Milewski
Piotr Adam Milewski

Reputation: 14645

The quoted animation will work, if You set the begin event properly:

<a-animation attribute="rotation"
             dur="2000"
             begin="mouseenter"
             to="0 360 0"
             repeat="1"><a-animation>

On mouseenter, the animation triggers, and rotates the entity once.


To gain more control over what You do, You would need to get deep into making components.

1. The Easiest way i can think of, is using both the animation component, and Your own. You would need to set up a component listening for the mouseenter/mousexit, and trigger the animation:

AFRAME.registerComponent('mouseenterhandler', {
  init: function () {    
  let el = this.el; //Your element reference
  el.addEventListener('mouseenter, function () {
      // get the rotation, by getAttribute, or by accessing the 
      //object3D.rotation
      let rotation = el.getAttribute('rotation');
      //lets rotate it to the same position
      rotation.y += 360; 
      //set the animation component accordingly:
      el.children[0].setAttribute('to',rotation);
      //emit the 'begin' event:
      el.emit('startrotating');
      });
    }   
});

Quick Improvement if necessary: disable the listener, when the animation is triggered. Made with a boolean switched on the mouseenter event, and the animationend event.

2. You can choose not to use the animation component, and check on tick() if the cursor is over. If so, rotate the element by the actualRotation.y+0.1 ( or any other desired rotation ).
As noted before, You can access the rotation by getAttribute() or el.object3D.rotation.


As for the scale, You if You need to rotate + rescale the object on the mouseenter event, just add another animation, and use it like i did with the rotation.
I'm not sure how it's usually done, in my experience animations are good, when there are not that many interactions, because they sometimes do unexpected things, which You have to predict/find out, and prevent.
On the other hand, making any animation manually ( changing properties on tick ) may seem laggy if the rotation delta is too big.
You need to play with it, and find out which suits You best.

Upvotes: 1

Riccardo
Riccardo

Reputation: 165

As you have asked for a different method in your comment I suggest to use a multi use component like the one I have written:

AFRAME.registerComponent('event-animate', {
schema: {
    target: {type: 'selector'},
    aevent: {default: 'animation1'},
    triggeraction: {default: 'click'}
},

init: function () {
    var data = this.data;

    this.el.addEventListener(data.triggeraction, function () {
        data.target.emit(data.aevent);
    });
}

});

So in HTML it would look something like this:

<a-entity id="object1" 
          event-animate="target:object1;    
          triggeraction:mouseenter; 
          aevent:eventstart">
<a-animation attribute="scale" 
             dur="5000" 
             begin="eventstart" 
             from="1" 
             to ="5" 
             direction="alternate"> 
</a-animation>
<a-animation attribute="rotation" 
             dur="5000" 
             begin="eventstart" 
             from="0 0 0" 
             to="0 360 0" 
             direction="alternate">
</a-animation>
</a-entity>

The direction="alternate" should bring it back to its original position.

Upvotes: 2

Related Questions