UNPKG

toloframework

Version:

Javascript/HTML/CSS compiler for Firefox OS or nodewebkit apps using modules in the nodejs style.

128 lines (112 loc) 3.8 kB
"use strict"; /** * @module tfw.touchable * * @description * Turn a DOM element into a touchable one with material design * animation: a growing transparent disk. * * @example * var Touchable = require('tfw.touchable'); * var div = document.querySelector('#button'); * var touchable = new Touchable( div, { * opacity: .2, * color: "white" * }); * touchable.tap.add(function() { ... }); * touchable.press.add(function() { ... }); */ var $ = require("dom"); var Fx = require("dom.fx"); var Listeners = require("tfw.listeners"); var Touchable = function(elem, opts) { var that = this; if( typeof opts === 'undefined' ) opts = {}; if( typeof opts.enabled === 'undefined' ) opts.enabled = true; elem = $( elem ); this.enabled = opts.enabled; this.color = opts.color || "#fd8"; this.classToAdd = opts.classToAdd; this.opacity = opts.opacity || .4; this.element = $(elem); this.tap = new Listeners(); this.press = new Listeners(); $.addClass( elem, 'tfw-touchable' ); var shadow = $.div( 'tfw-touchable-shadow' ); var fxDown = Fx().css( shadow, { transition: "none" }) .exec(function( session ) { var cls = that.classToAdd; if( typeof cls === 'string' ) { $.addClass( elem, cls ); } // Position must not be `static`. var position = getComputedStyle(elem).position; if( ['relative', 'absolute', 'fixed'].indexOf( position ) == -1 ) { elem.style.position = 'relative'; } elem.style.overflow = 'hidden'; var rect = elem.getBoundingClientRect(); var w = rect.width; var h = rect.height; w = Math.max( lastX, w - lastX ); h = Math.max( lastY, h - lastY ); var radius = Math.ceil( Math.sqrt( w*w + h*h ) ); $.css( shadow, { left: lastX + "px", top: lastY + "px", margin: "-" + radius + "px", width: 2*radius + "px", height: 2*radius + "px", opacity: that.opacity, background: that.color, transform: "scale(0)" }); $.add( elem, shadow ); }) .css( shadow, { transition: "all .3s ease" } ) .css( shadow, { transform: "scale(1)" } ) .wait( 300 ) .css( shadow, { transition: "all .2s ease" } ) .css( shadow, { opacity: 0 } ) .wait( 200 ) .detach( shadow ); var time = 0; var lastX, lastY; var removeShadow = 0; $.on(elem, { down: function(evt) { if( !that.enabled ) return; evt.stopPropagation(); evt.preventDefault(); lastX = Math.floor( evt.x ); lastY = Math.floor( evt.y ); fxDown.start(); time = Date.now(); }, tap: function(evt) { if( !that.enabled ) return; console.log('TAP', evt); that.tap.fire( evt ); } }); }; module.exports = Touchable; /* https://jsfiddle.net/mzmaczdn/7/ var div = document.createElement('div'); div.className = 'shadow'; var btn = document.querySelector('button'); btn.addEventListener('mousedown', function(evt) { btn.className = "press"; btn.appendChild( div ); div.style.left = evt.offsetX + "px"; div.style.top = evt.offsetY + "px"; window.setTimeout(function() { div.style.transform = "scale(1)"; }); }); btn.addEventListener('mouseup', function(evt) { div.style.transform = "scale(0)"; btn.removeChild(div); }); */