Pendulum Movement

megumi014

Veteran
Veteran
Joined
Mar 8, 2017
Messages
130
Reaction score
213
First Language
Spanish
Primarily Uses
RMMV
Hi, I've been trying to emulate the movement of a pendulum and it's proving to be rather hard. I have managed to do something that resembles it but if I make it move faster the change of movement feels too abrupt, and the Y coordinate is hard to keep steady (I tried to anchor it).

Here I'm using a birdscage instead of a pendulum (I didn't make the picture).

Here is the mini video LINK

The question is: does anyone know if there is a better way to approach this? Or something to emulate the "cushion" movement on the edges?

This is how I have it now (Custom Scene_Title):

I load 2 pictures, one static (the "holder") and the other the chain&body together. Then I anchor the Y of the moving picture to the middle as precise as I can and rotate it.

Code:
Scene_Title.prototype.create = function() {
        Scene_Base.prototype.create.call(this);
        this.createBackground();
        this.createPendulo(); // Here I create the 2 pictures.
        this.createForeground();
        this.createWindowLayer();
        this.createCommandWindow();
        this._commandWindow.opacity = 0;
        this.createPictureCommands();
    };

Scene_Title.prototype.createPendulo = function() {
        this.createJailChainAndBody(); //Moving
        this.createJailHolder(); //Static
    };
   
Scene_Title.prototype.createJailHolder = function() {
        this._jailHolder = new Sprite();
        this._jailHolder.bitmap = ImageManager.loadPicture('JailHolder');
        this._jailHolder.x = 600;
        this._jailHolder.y = 0;
        this.addChild(this._jailHolder);
    };

Scene_Title.prototype.createJailChainAndBody = function() {
        this._jailChainAndBody = new Sprite();
        this._jailChainAndBody.bitmap = ImageManager.loadPicture('JailChainAndBody');
        this._jailChainAndBody.x = 610;
        this._jailChainAndBody.y = 20;
        this._jailChainAndBody.anchor.x = 0.50;
        this._jailChainAndBody.anchor.y = 0;
        this.addChild(this._jailChainAndBody);
    };

Scene_Title.prototype.update = function() {
        if (!this.isBusy()) {
            this._commandWindow.open();
        }
        Scene_Base.prototype.update.call(this);
        this.updatePictureCommands();
        this.updateJailChainAndBodyPosition(); // Here I Update the Chain&Body Picture.
    };

Scene_Title.prototype.start = function() {
        Scene_Base.prototype.start.call(this);
        SceneManager.clearStack();
        this.centerSprite(this._titleBackground);
        this.playTitleMusic();
        this._isGoingRight = false; // Here I define the condition for the movement
    };

Scene_Title.prototype.updateJailChainAndBodyPosition = function() {
        if (this._isGoingRight === false) {
            this._jailChainAndBody.rotation += 0.0002;
            if (this._jailChainAndBody.rotation >= 0.0100) {
                this._isGoingRight = true;
            }
        }
        if (this._isGoingRight === true) {
            this._jailChainAndBody.rotation -= 0.0002;
            if (this._jailChainAndBody.rotation <= -0.0100) {
                this._isGoingRight = false;
            }
        }
    };
 

MushroomCake28

KAMO Studio
Global Mod
Joined
Nov 18, 2015
Messages
3,729
Reaction score
4,682
First Language
English
Primarily Uses
RMMZ
I don't think the rotation speed is linear like you coded. It follows the function sinus.

EDIT: The movement speed is maximal when your rotation is = 0 and the speed is 0 when your rotation is at its max value. So sin(x) = 0 when your rotation is 0 and sin(x) = 1 when your rotation is as its max value.
 

Jonforum

Veteran
Veteran
Joined
Mar 28, 2016
Messages
1,623
Reaction score
1,439
First Language
French
Primarily Uses
RMMV
I don't think the rotation speed is linear like you coded. It follows the function sinus.

EDIT: The movement speed is maximal when your rotation is = 0 and the speed is 0 when your rotation is at its max value. So sin(x) = 0 when your rotation is 0 and sin(x) = 1 when your rotation is as its max value.
the example show how use yoyo and infinite rotation Pendulum .
Is juste code, after you need to play with value to do what you need.
yoyo.gif

PHP:
    IN_itemSlot(e) {
        this.itemsFrame.d.displayOrder = 9999999;
        const itemsFrame = this.itemsFrame;
        const items = this.items;
        const itemTxt = this.itemTxt;
        const txtFx = this.txtFx;
        itemsFrame.d.blendMode = 1;
        itemsFrame.n.blendMode = 1;

        const rot = 0.15;
        itemsFrame.d.rotation = -rot;
        itemsFrame.n.rotation = rot;
        TweenLite.killTweensOf(itemsFrame.d);
        TweenLite.killTweensOf(itemsFrame.n);
        TweenMax.to(itemsFrame.d, 2, {
            rotation: rot,
            ease: Power1.easeInOut,
            repeat: -1,
            yoyoEase: true
        });
        TweenMax.to(itemsFrame.n, 2, {
            rotation: -rot,
            ease: Power1.easeInOut,
            repeat: -1,
            yoyoEase: true
        });
        TweenLite.to(itemsFrame.d.scale, 0.8, {
            x: 1.5,
            y: 1.5,
            ease: Expo.easeOut
        });
        TweenLite.to(itemsFrame.n.scale, 0.8, {
            x: 1.1,
            y: 1.1,
            ease: Expo.easeOut
        });
        TweenLite.to([items.d.scale, items.n.scale], 0.8, {
            x: 1.2,
            y: 1.2,
            ease: Expo.easeOut
        });
        TweenLite.to(itemTxt.scale, 2, {
            x: 1.2,
            y: 1.2,
            ease: Expo.easeOut
        });
    };
 

megumi014

Veteran
Veteran
Joined
Mar 8, 2017
Messages
130
Reaction score
213
First Language
Spanish
Primarily Uses
RMMV
@Jonforum
Thank you but I didn't understand anything ^^U I don't know how to use libraries or how to implement them in a plugin but thank you anyways, I guess is time to start learning again lol

EDIT: I just saw the new post. So where should I save that code? In the libs folder? Or inside Scene_Title? I'm sorry I'm so lost :kaodes:

@MushroomCake28
I feel like this pendulum thing is just out of my reach/understandment. I kinda understood the Edit explanation as a concept but not mathematically :kaoswt2: It makes sense that the speed "stops" and becomes 0 when it reaches the max rotation point or edge (at least that is the effect that I have goten), and I guess the sinus function is what will give it the slowly reducing speed until the edge? How could I write it on the plugin then? On the updateJailChainAndBodyPosition function? Or a completely new one?
 

Jonforum

Veteran
Veteran
Joined
Mar 28, 2016
Messages
1,623
Reaction score
1,439
First Language
French
Primarily Uses
RMMV
@Jonforum
Thank you but I didn't understand anything ^^U I don't know how to use libraries or how to implement them in a plugin but thank you anyways, I guess is time to start learning again lol
just add the plugin in your index.html
and you will have access to the plugin by global.
TweenMax or TweenLight

PHP:
        sprite.proprety = ?; // start proprety of you sprite

TweenMax.to(sprite, time, {
            proprety: value, // end proprety of your sprite
            ease: Power1.easeInOut,
            repeat: -1,
            yoyoEase: true
        });
and yes you need study the api doc
https://greensock.com/docs/TweenMax
 

MushroomCake28

KAMO Studio
Global Mod
Joined
Nov 18, 2015
Messages
3,729
Reaction score
4,682
First Language
English
Primarily Uses
RMMZ
Or my method (calculating the rotation position each frame with a sin function)

If your oscillation duration is 120 frames:

Sin(0) = 0 // Maximum left angle, frame 0
Sin(π/2) = 1 // Center, frame 30
Sin(π) = 0 // Maximum right angle, frame 60
Sin(3π/2) = 1 // Center, frame 90

So in your case:
Code:
var d = 120; // The duration
var mr = 0.2; // max rotation
var f = 0; // Current frame

var cr = Math.sin( f / d * 2 * Math.PI) * mr; // This is the angular position at frame f
Try using this (the cr variable's function) to determine your angular position.

EDIT: Of course, you can change the duration and the max rotation variable. The f variable though (current frame) must be a local variable (don't know how you call them in javascript, but it's the "this._currentFrame") and must be updated every frame before the angular position calculation. Also, don't make f go over the max duration.
 
Last edited:

megumi014

Veteran
Veteran
Joined
Mar 8, 2017
Messages
130
Reaction score
213
First Language
Spanish
Primarily Uses
RMMV
@MushroomCake28 Thank you so much! It worked like a charm. I guess I will still study API and Libraries since they seem very useful, but this mathematical formula saved me all the hastle right now lol so thanks again.

This is the part I modified in the code I posted at the beginning, just in case someone wants to use it:

Code:
Scene_Title.prototype.start = function() {
        Scene_Base.prototype.start.call(this);
        SceneManager.clearStack();
        this.centerSprite(this._titleBackground);
        this.playTitleMusic();
        this._pendulumCurrentFrame = 0; // here the frames "variable"
    };

Scene_Title.prototype.createJailChainAndBody = function() {
        this._jailChainAndBody = new Sprite();
        this._jailChainAndBody.bitmap = ImageManager.loadPicture('JailChainAndBody');
        this._jailChainAndBody.x = 610;
        this._jailChainAndBody.y = 20;
        this._jailChainAndBody.anchor.x = 0.50;
        this._jailChainAndBody.anchor.y = 0;
        this._jailChainAndBody.rotation = 0.1; // Make the sprite start at the left edge (not in the middle).
        this.addChild(this._jailChainAndBody);
    };

Scene_Title.prototype.updateJailChainAndBodyPosition = function() {
        var duration = 120;
        var maxRotation = 0.005;
        var f = this._pendulumCurrentFrame;
        
        var cr = Math.sin(f / duration * 2 * Math.PI) * maxRotation;
        
        if (this._pendulumCurrentFrame <= duration) {
            this._pendulumCurrentFrame += 1;
            this._jailChainAndBody.rotation -= cr;
        } else {
            this._pendulumCurrentFrame = -1; // or 0, I'm not sure if it makes any difference with the speed I use. 
        }
    };
 

MushroomCake28

KAMO Studio
Global Mod
Joined
Nov 18, 2015
Messages
3,729
Reaction score
4,682
First Language
English
Primarily Uses
RMMZ
You're welcome :)
API and libraries are very powerful and useful, but a bit overkill for this situation lol.
 

Users Who Are Viewing This Thread (Users: 0, Guests: 1)

Latest Threads

Latest Posts

Latest Profile Posts

How many parameters is 'too many'??
Yay, now back in action Happy Christmas time, coming back!






Back in action to develop the indie game that has been long overdue... Final Fallacy. A game that keeps on giving! The development never ends as the developer thinks to be the smart cookie by coming back and beginning by saying... "Oh bother, this indie game has been long overdue..." How could one resist such? No-one c
So I was playing with filters and this looked interesting...

Versus the normal look...

Kind of gives a very different feel. :LZSexcite:
To whom ever person or persons who re-did the DS/DS+ asset packs for MV (as in, they are all 48x48, and not just x2 the pixel scale) .... THANK-YOU!!!!!!!!! XwwwwX

Forum statistics

Threads
105,849
Messages
1,016,977
Members
137,563
Latest member
cexojow
Top