I'm trying to convert this Popmotion
example to GreenSock
.
https://codepen.io/popmotion/pen/xVeWmm
var SELECTOR = '.box';
var velocityRange = [-1000, 1000];
var maxRotate = 30;
var smoothing = 100;
var box = ui.select(SELECTOR, {
values: {
x: 0,
y: 0,
rotateY: {
watch: function (actor) {
return actor.values.x.velocity;
},
mapFrom: velocityRange,
mapTo: [-maxRotate, maxRotate],
smooth: smoothing
},
rotateX: {
watch: function (actor) {
return actor.values.y.velocity;
},
mapFrom: velocityRange,
mapTo: [maxRotate, -maxRotate],
smooth: smoothing
}
}
});
var track2D = new ui.Track({
values: {
x: {},
y: {}
}
});
var springBack = new ui.Simulate({
simulate: 'spring',
spring: 500,
friction: 0.3,
values: {
x: 0,
y: 0
}
});
$('body').on('touchstart mousedown', SELECTOR, function (e) {
e.preventDefault();
box.start(track2D, e);
});
$('body').on('touchend mouseup', function () {
box.start(springBack);
});
Being a total noob at GreenSock
, is this easy to do? Does GreenSock
have actors and simulators?
I have never used GreenSock
to make continuous dynamic animations (maybe it is possible, I am not an expert in GreenSock
). I prefer to left this library to make a specific animation. In the next example, I've tried to replicate the same Popmotion
effect you have posted using my own calculations and I just use the animation library to return the box to its original place. I think that it can help you in your purpose:
I've removed the vendor prefixes to make the code easier to read, but the
CodePen
example has the prefixes.
HTML Code:
<div id="container">
<div class="box"></div>
</div>
CSS Code
html {
height: 100%;
}
body {
background: #e25875;
height: 100%;
}
#container {
height: 100%;
perspective: 700;
perspective-origin: 50% 50%;
position: relative;
transform-style: preserve-3d;
width: 100%;
}
.box {
background: white;
border-radius: 4px;
height: 150px;
left: 50%;
margin-left: -75px;
margin-top: -75px;
position: absolute;
cursor: pointer;
top: 50%;
will-change: transform;
width: 150px;
}
JavaScript Code:
//---Variables
var doc = document,
box = doc.querySelector(".box"),
startX = 0,
startY = 0,
posX = 0,
posY = 0,
speedX = 0,
speedY = 0,
obj = {x: 0, y: 0, speedX: 0, speedY: 0};
//---Main Events
box.addEventListener("mousedown", startMove);
doc.addEventListener("mouseup", stopMove);
//---Start the movement
function startMove (evt) {
startX = evt.pageX;
startY = evt.pageY;
//---Add the mouse move events
doc.addEventListener("mousemove", updatePosition);
}
//---Update variables
function updatePosition (evt) {
speedX = (evt.pageX - posX) * 5;
speedY = (evt.pageY - posY) * 5;
if (speedX < -45) { speedX = -45 }
if (speedX > 45) { speedX = 45 }
if (speedY < -45) { speedY = -45 }
if (speedY > 45) { speedY = 45 }
posX = evt.pageX;
posY = evt.pageY;
obj.x += (posX - startX - obj.x) * .15;
obj.y += (posY - startY - obj.y) * .15;
obj.speedX += (speedX - obj.speedX) * .15;
obj.speedY += (speedY - obj.speedY) * .15;
updateTransform();
}
//---Stop movement, returns the box to its place
function stopMove () {
TweenLite.to(obj, 0.75, {
ease: Elastic.easeOut.config(1, 0.3),
x: 0,
y: 0,
speedX: 0,
speedY: 0,
onUpdate: updateTransform
});
doc.removeEventListener("mousemove", updatePosition);
}
//---Update the box transformations
function updateTransform () {
var transformStr = "translate(" + obj.x + "px, " + obj.y + "px) rotateX(" + (-obj.speedY) + "deg) rotateY(" + obj.speedX + "deg)";
box.style.transform = transformStr;
}
Here you have a CodePen
with a working example.
EDIT: I've updated the CodePen
to work with Touch Events
.