/** * main.js * http://www.codrops.com * * licensed under the mit license. * http://www.opensource.org/licenses/mit-license.php * * copyright 2016, codrops * http://www.codrops.com */ ;(function(window) { 'use strict'; // helper vars and functions. function extend( a, b ) { for( var key in b ) { if( b.hasownproperty( key ) ) { a[key] = b[key]; } } return a; } // from http://www.quirksmode.org/js/events_properties.html#position function getmousepos(e) { var posx = 0, posy = 0; if (!e) var e = window.event; if (e.pagex || e.pagey) { posx = e.pagex; posy = e.pagey; } else if (e.clientx || e.clienty) { posx = e.clientx + document.body.scrollleft + document.documentelement.scrollleft; posy = e.clienty + document.body.scrolltop + document.documentelement.scrolltop; } return { x : posx, y : posy } } /** * tiltfx obj. */ function tiltfx(el, options) { this.dom = {}; this.dom.el = el; this.options = extend({}, this.options); extend(this.options, options); this._init(); } tiltfx.prototype.options = { movement: { imgwrapper : { translation : {x: 0, y: 0, z: 0}, rotation : {x: -5, y: 5, z: 0}, reverseanimation : { duration : 1200, easing : 'easeoutelastic', elasticity : 600 } }, lines : { translation : {x: 10, y: 10, z: [0,10]}, reverseanimation : { duration : 1000, easing : 'easeoutexpo', elasticity : 600 } }, caption : { translation : {x: 20, y: 20, z: 0}, rotation : {x: 0, y: 0, z: 0}, reverseanimation : { duration : 1500, easing : 'easeoutelastic', elasticity : 600 } }, /* overlay : { translation : {x: 10, y: 10, z: [0,50]}, reverseanimation : { duration : 500, easing : 'easeoutexpo' } }, */ shine : { translation : {x: 50, y: 50, z: 0}, reverseanimation : { duration : 1200, easing : 'easeoutelastic', elasticity: 600 } } } }; /** * init. */ tiltfx.prototype._init = function() { this.dom.animatable = {}; this.dom.animatable.imgwrapper = this.dom.el.queryselector('.tilter__figure'); this.dom.animatable.lines = this.dom.el.queryselector('.tilter__deco--lines'); this.dom.animatable.caption = this.dom.el.queryselector('.tilter__caption'); this.dom.animatable.overlay = this.dom.el.queryselector('.tilter__deco--overlay'); this.dom.animatable.shine = this.dom.el.queryselector('.tilter__deco--shine > div'); this._initevents(); }; /** * init/bind events. */ tiltfx.prototype._initevents = function() { var self = this; this.mouseenterfn = function() { for(var key in self.dom.animatable) { anime.remove(self.dom.animatable[key]); } }; this.mousemovefn = function(ev) { requestanimationframe(function() { self._layout(ev); }); }; this.mouseleavefn = function(ev) { requestanimationframe(function() { for(var key in self.dom.animatable) { if( self.options.movement[key] == undefined ) {continue;} anime({ targets: self.dom.animatable[key], duration: self.options.movement[key].reverseanimation != undefined ? self.options.movement[key].reverseanimation.duration || 0 : 1, easing: self.options.movement[key].reverseanimation != undefined ? self.options.movement[key].reverseanimation.easing || 'linear' : 'linear', elasticity: self.options.movement[key].reverseanimation != undefined ? self.options.movement[key].reverseanimation.elasticity || null : null, scalex: 1, scaley: 1, scalez: 1, translatex: 0, translatey: 0, translatez: 0, rotatex: 0, rotatey: 0, rotatez: 0 }); } }); }; this.dom.el.addeventlistener('mousemove', this.mousemovefn); this.dom.el.addeventlistener('mouseleave', this.mouseleavefn); this.dom.el.addeventlistener('mouseenter', this.mouseenterfn); }; tiltfx.prototype._layout = function(ev) { // mouse position relative to the document. var mousepos = getmousepos(ev), // document scrolls. docscrolls = {left : document.body.scrollleft + document.documentelement.scrollleft, top : document.body.scrolltop + document.documentelement.scrolltop}, bounds = this.dom.el.getboundingclientrect(), // mouse position relative to the main element (this.dom.el). relmousepos = { x : mousepos.x - bounds.left - docscrolls.left, y : mousepos.y - bounds.top - docscrolls.top }; // movement settings for the animatable elements. for(var key in this.dom.animatable) { if( this.dom.animatable[key] == undefined || this.options.movement[key] == undefined ) { continue; } var t = this.options.movement[key] != undefined ? this.options.movement[key].translation || {x:0,y:0,z:0} : {x:0,y:0,z:0}, r = this.options.movement[key] != undefined ? this.options.movement[key].rotation || {x:0,y:0,z:0} : {x:0,y:0,z:0}, setrange = function (obj) { for(var k in obj) { if( obj[k] == undefined ) { obj[k] = [0,0]; } else if( typeof obj[k] === 'number' ) { obj[k] = [-1*obj[k],obj[k]]; } } }; setrange(t); setrange(r); var transforms = { translation : { x: (t.x[1]-t.x[0])/bounds.width*relmousepos.x + t.x[0], y: (t.y[1]-t.y[0])/bounds.height*relmousepos.y + t.y[0], z: (t.z[1]-t.z[0])/bounds.height*relmousepos.y + t.z[0], }, rotation : { x: (r.x[1]-r.x[0])/bounds.height*relmousepos.y + r.x[0], y: (r.y[1]-r.y[0])/bounds.width*relmousepos.x + r.y[0], z: (r.z[1]-r.z[0])/bounds.width*relmousepos.x + r.z[0] } }; this.dom.animatable[key].style.webkittransform = this.dom.animatable[key].style.transform = 'translatex(' + transforms.translation.x + 'px) translatey(' + transforms.translation.y + 'px) translatez(' + transforms.translation.z + 'px) rotatex(' + transforms.rotation.x + 'deg) rotatey(' + transforms.rotation.y + 'deg) rotatez(' + transforms.rotation.z + 'deg)'; } }; window.tiltfx = tiltfx; })(window);