Attributes Plugin can also tween color attributes: fill, stroke, stopColor. Perhaps some things can be removed from SVG Plugin.

This commit is contained in:
thednp 2016-09-24 06:02:25 +03:00
parent 3d7f6721b9
commit 877005df3b
13 changed files with 85 additions and 36 deletions

View file

@ -16,7 +16,7 @@ circleBtn.addEventListener('click', function(){
});
// coordinatea of gradient
// coordinates of gradient
var gradBtn = document.getElementById('gradBtn');
var closingGradient = KUTE.to('#gradient',{attr: {x1:'49%', x2:'49%', y1:'49%', y2:'51%'}}, {easing: 'easingCubicInOut'});
var rotatingGradient1 = KUTE.to('#gradient',{attr: {x1:'49%', x2:'51%', y1:'51%', y2:'51%'}}, {easing: 'easingCubicInOut'});
@ -28,3 +28,10 @@ rotatingGradient2.chain(openingGradient);
gradBtn.addEventListener('click', function(){
!closingGradient.playing && !rotatingGradient1.playing && !rotatingGradient2.playing && !openingGradient.playing && closingGradient.start();
});
// fill color
var fillBtn = document.getElementById('fillBtn');
var fillAttribute = KUTE.to('#fill',{attr: {fill: 'red'}}, {duration: 1500, repeat: 1, yoyo: true });
fillBtn.addEventListener('click', function(){
!fillAttribute.playing && fillAttribute.start();
});

View file

@ -101,8 +101,30 @@ var myDashedAttrStringTween = KUTE.to('selector', {attr: {'stroke-width': 75}});
var myNonDashedAttrStringTween = KUTE.to('selector', {attr:{strokeWidth: '15px'}});
</code></pre>
<p>The <code>strokeWidth</code> example is very interesting because this attribute along with many others can work with <code>px</code>, <code>%</code> or with no unit/suffix.</p>
<h3>Color Attributes</h3>
<p>Starting with KUTE.js version 1.5.7, the Attributes Plugin can also animate color attributes: <code>fill</code>, <code>stroke</code> and <code>stopColor</code>. If the elements are affected by their CSS counterparts, the effect is not visible, so always make sure you know what you're doing.</p>
<pre><code class="language-javascript">// some fill rgb, rgba, hex
var fillTween = KUTE.to('#element-to-fill', {attr: { fill: 'red' }});
// some stopColor or 'stop-color'
var stopColorTween = KUTE.to('#element-to-do-stop-color', {attr: {stopColor: 'rgb(0,66,99)'}});
</code></pre>
<div class="featurettes">
<svg class="example-box-model example-box" xmlns="http://www.w3.org/2000/svg" viewBox="0 0 615 615">
<h3>Unitless Properties</h3>
<path id="fill" fill="#673AB7" d="M38.01,5.653h526.531c17.905,0,32.422,14.516,32.422,32.422v526.531
c0,17.905-14.517,32.422-32.422,32.422H38.01c-17.906,0-32.422-14.517-32.422-32.422V38.075C5.588,20.169,20.104,5.653,38.01,5.653z"/>
</svg>
<div class="example-buttons">
<a id="fillBtn" class="btn btn-blue" href="javascript:void(0)">Start</a>
</div>
</div>
<p>If in this example the <code>fill</code> attribute value would reference a gradient, then <i>rgba(0,0,0,0)</i> is used.</p>
<h3>Unitless Attributes</h3>
<p>In the first example, let's play with the attributes of a <code>&lt;circle&gt;</code> element: radius and center coordinates.</p>
<pre><code class="language-javascript">// radius attribute
var radiusTween = KUTE.to('#circle', {attr: {r: 75}});
@ -121,7 +143,7 @@ var coordinatesTween = KUTE.to('#circle', {attr:{cx:0,cy:0}});
</div>
</div>
<h3>Suffixed Properties</h3>
<h3>Suffixed Attributes</h3>
<p>Similar to the example on gradients with <a href="svg.html">SVG Plugin</a>, we can also animate the gradient positions, and the plugin will make sure to always include the suffix for you, as in this example the <code>%</code> unit is found in the current value and used as unit for the DOM update:</p>
<pre><code class="language-javascript">// gradient positions to middle
var closingGradient = KUTE.to('#gradient', {attr: {x1:'49%', x2:'49%', y1:'49%', y2:'49%'}});
@ -147,6 +169,7 @@ var rotatingGradient = KUTE.to('#gradient', {attr: {x1:'49%', x2:'51%', y1:'51%'
</div>
</div>
<p>This plugin is quite handy and a great addition to the <a href="svg.html">SVG Plugin</a>.</p>
</div>
<ul id="share" class="nav">

View file

@ -176,7 +176,7 @@
<h3>Cubic Bezier Functions</h3>
<p>While modern browsers support CSS3 <code>transition</code> with <code>transition-timing-function: cubic-bezier(0.1,0.5,0.8,0.5)</code>, in Javascript animation we need some specific functions to cover that kind of functionality. As mentioned in the <a href="features.html">features page</a>, we are using a modified version of the <a href="https://github.com/gre/bezier-easing" target="_blank">cubic-bezier</a> by Gaëtan Renaudeau. I believe this must be most accurate easing functions set.</p>
<p>You can use them either with <code>easing: KUTE.Ease.bezier(mX1, mY1, mX2, mY2)</code> or <code>easing: 'bezier(mX1, mY1, mX2, mY2)'</code>, where mX1, mY1, mX2, mY2 are <em>Float</em> values from 0 to 1. You can find the right values you need <a href="http://cubic-bezier.com/" target="_blank">right here</a>.</p>
<p>You can use them either with <code>easing: Bezier(mX1, mY1, mX2, mY2)</code> or <code>easing: 'bezier(mX1, mY1, mX2, mY2)'</code>, where mX1, mY1, mX2, mY2 are <em>Float</em> values from 0 to 1. You can find the right values you need <a href="http://cubic-bezier.com/" target="_blank">right here</a>.</p>
<p>There is also a pack of presets, and the keywords look very similar if you have used jQuery.Easing plugin before:</p>
<ul>
<li>Equivalents of the browser's <strong>generic</strong> timing functions: <kbd>easeIn</kbd>, <kbd>easeOut</kbd> and <kbd>easeInOut</kbd></li>
@ -257,7 +257,7 @@ easing: BezierMultiPoint({points: [{"x":0,"y":0,"cp":[{"x":0.387,"y":0.007}]},{"
</code></pre>
</li>
</ul>
<p>The presets can be used both as a string <code>easing:'physicsIn'</code> or <code>easing:physicsIn(friction:200)</code>. The list is:</p>
<p>The presets can be used both as a string <code>easing:'physicsIn'</code> or <code>easing: Physics.physicsIn(friction:200)</code>. The list is:</p>
<ul>
<li><strong>curves</strong>: <kbd>physicsIn</kbd>, <kbd>physicsOut</kbd>, <kbd>physicsInOut</kbd> can do all multipliers (from sinusoidal to exponential) via the <code>friction</code> option;</li>
<li><strong>back</strong>: <kbd>physicsBackIn</kbd>, <kbd>physicsBackOut</kbd>, <kbd>physicsBackInOut</kbd> also benefit from the <code>friction</code> option.</li>
@ -329,4 +329,4 @@ easing: BezierMultiPoint({points: [{"x":0,"y":0,"cp":[{"x":0.387,"y":0.007}]},{"
<script src="./assets/js/scripts.js"></script> <!-- global scripts stuff -->
<script src="./assets/js/easing.js"></script> <!-- examples stuff -->
</body>
</html>
</html>

View file

@ -1,2 +1,2 @@
// KUTE.js v1.5.7 | © dnp_theme | Attributes Plugin | MIT-License
!function(t){if("function"==typeof define&&define.amd)define(["./kute.js"],function(e){return t(e),e});else if("object"==typeof module&&"function"==typeof require){var e=require("./kute.js");module.exports=t(e)}else{if("undefined"==typeof window.KUTE)throw new Error("Attributes Plugin require KUTE.js.");t(e)}}(function(t){"use strict";var e,r=window,n=r.KUTE,i=r.dom,u=n.prS,a=n.pp,o=r.Interpolate.unit,f=r.Interpolate.number,c=function(t,e){return t.getAttribute(e)},s=function(t){return/[A-Z]/g.test(t)?t.replace(t.match(/[A-Z]/g)[0],"-"+t.match(/[A-Z]/g)[0].toLowerCase()):t};u.attr=function(t,e,r){var n={};for(var i in r){var u=s(i).replace(/_+[a-z]+/,""),a=c(t,u);n[u]=a||(/opacity/i.test(i)?1:0)}return n},a.attr=function(t,r,u){"attr"in i||(i.attr=function(t,e,r,n,u){for(var a in n)i.attributes[a](t,a,r[a],n[a],u)},e=i.attributes={});var a,p={};for(a in r){var l=s(a),v=c(u,l.replace(/_+[a-z]+/,""));if(/(%|[a-z]+)$/.test(r[a])||/(%|[a-z]+)$/.test(v)){var d=n.truD(v).u||n.truD(r[a]).u,b=/%/.test(d)?"_percent":"_"+d;a+b in e||(e[a+b]=function(t,e,r,n,i){var u=u||s(e).replace(b,"");t.setAttribute(u,o(r.v,n.v,n.u,i))}),p[a+b]=n.truD(r[a])}else a in e||(e[a]=function(t,e,r,n,i){var u=u||s(e);t.setAttribute(u,f(r,n,i))}),p[a]=parseFloat(r[a])}return p}});
!function(t){if("function"==typeof define&&define.amd)define(["./kute.js"],function(e){return t(e),e});else if("object"==typeof module&&"function"==typeof require){var e=require("./kute.js");module.exports=t(e)}else{if("undefined"==typeof window.KUTE)throw new Error("Attributes Plugin requires KUTE.js.");t(e)}}(function(t){"use strict";var e,r=window,n=r.KUTE,i=r.dom,o=n.prS,u=n.pp,a=r.Interpolate.unit,f=r.Interpolate.number,c=r.Interpolate.color,s=function(t,e){return t.getAttribute(e)},p=["fill","stroke","stop-color"],l=n.truC,d=n.truD,v=function(t){return/[A-Z]/g.test(t)?t.replace(t.match(/[A-Z]/g)[0],"-"+t.match(/[A-Z]/g)[0].toLowerCase()):t};o.attr=function(t,e,r){var n={};for(var i in r){var o=v(i).replace(/_+[a-z]+/,""),u=s(t,o);n[o]=p.indexOf(v(i))!==-1?u||"rgba(0,0,0,0)":u||(/opacity/i.test(i)?1:0)}return n},u.attr=function(t,r,n){"attr"in i||(i.attr=function(t,e,r,n,o){for(var u in n)i.attributes[u](t,u,r[u],n[u],o)},e=i.attributes={});var o,u={};for(o in r){var b=v(o),A=s(n,b.replace(/_+[a-z]+/,""));if(p.indexOf(b)===-1&&(/(%|[a-z]+)$/.test(r[o])||/(%|[a-z]+)$/.test(A))){var m=d(A).u||d(r[o]).u,w=/%/.test(m)?"_percent":"_"+m;o+w in e||(e[o+w]=function(t,e,r,n,i){var o=o||v(e).replace(w,"");t.setAttribute(o,a(r.v,n.v,n.u,i))}),u[o+w]=d(r[o])}else p.indexOf(b)>-1?(o in e||(e[o]=function(t,e,n,i,o){var u=u||v(e);t.setAttribute(u,c(n,i,o,r.keepHex))}),u[o]=l(r[o])):(o in e||(e[o]=function(t,e,r,n,i){var o=o||v(e);t.setAttribute(o,f(r,n,i))}),u[o]=parseFloat(r[o]))}return u}});

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View file

@ -438,7 +438,7 @@ var rotationTween = KUTE.to(element, {svgTransform: {rotate: [150, svgOriginX, s
<h4>Recommendations for SVG Transforms</h4>
<ul>
<li>The SVG Plugin coming with KUTE.js version 1.5.3 is trying to make sure animations don't go out of control, but you need to <b>always use same order of transform functions</b>: <code>translate</code>, <code>scale</code>, <code>rotate</code>, <code>skewX</code> and <code>skewY</code>. All this to make sure the animation looks like we would expect from regular HTML elements transformations. Maybe future versions will feature <code>.matrix()</code> transformations to handle all possible transform function combinations, but I'm going to need help with implementation and testing.</li>
<li>The SVG Plugin coming with KUTE.js version 1.5.3 is trying to make sure animations don't go out of control, and <b>always uses same order of transform functions</b>: <code>translate</code>, <code>scale</code>, <code>rotate</code>, <code>skewX</code> and <code>skewY</code>. All this to make sure the animation looks like we would expect from regular HTML elements transformations. Maybe future versions will feature <code>.matrix()</code> transformations to handle all possible transform function combinations, but I'm going to need help with implementation and testing.</li>
<li>Keep in mind the adjustments required for rotations, remember the <code>.getBBox()</code> method, it's really useful to set custom <code>transform-origin</code>.</li>
<li>By default browsers use <code>overflow: hidden</code> for <code>&lt;svg></code> so child elements are partialy/completely hidden while animating. You might want to set <code>overflow: visible</code> or some browser specific tricks if that is the case.</li>
<li>When using <code>viewBox="0 0 500 500"</code> attribute for <code>&lt;svg></code> and no <code>width</code> and/or <code>height</code> attribute(s), means that you expect the SVG to be scalable and most Internet Explorer versions simply don't work. You might want to <a href="https://css-tricks.com/scale-svg/" target="_blank">check this tutorial</a>.</li>

View file

@ -1,2 +1,2 @@
// KUTE.js v1.5.7 | © dnp_theme | Attributes Plugin | MIT-License
!function(t){if("function"==typeof define&&define.amd)define(["./kute.js"],function(e){return t(e),e});else if("object"==typeof module&&"function"==typeof require){var e=require("./kute.js");module.exports=t(e)}else{if("undefined"==typeof window.KUTE)throw new Error("Attributes Plugin require KUTE.js.");t(e)}}(function(t){"use strict";var e,r=window,n=r.KUTE,i=r.dom,u=n.prS,a=n.pp,o=r.Interpolate.unit,f=r.Interpolate.number,c=function(t,e){return t.getAttribute(e)},s=function(t){return/[A-Z]/g.test(t)?t.replace(t.match(/[A-Z]/g)[0],"-"+t.match(/[A-Z]/g)[0].toLowerCase()):t};u.attr=function(t,e,r){var n={};for(var i in r){var u=s(i).replace(/_+[a-z]+/,""),a=c(t,u);n[u]=a||(/opacity/i.test(i)?1:0)}return n},a.attr=function(t,r,u){"attr"in i||(i.attr=function(t,e,r,n,u){for(var a in n)i.attributes[a](t,a,r[a],n[a],u)},e=i.attributes={});var a,p={};for(a in r){var l=s(a),v=c(u,l.replace(/_+[a-z]+/,""));if(/(%|[a-z]+)$/.test(r[a])||/(%|[a-z]+)$/.test(v)){var d=n.truD(v).u||n.truD(r[a]).u,b=/%/.test(d)?"_percent":"_"+d;a+b in e||(e[a+b]=function(t,e,r,n,i){var u=u||s(e).replace(b,"");t.setAttribute(u,o(r.v,n.v,n.u,i))}),p[a+b]=n.truD(r[a])}else a in e||(e[a]=function(t,e,r,n,i){var u=u||s(e);t.setAttribute(u,f(r,n,i))}),p[a]=parseFloat(r[a])}return p}});
!function(t){if("function"==typeof define&&define.amd)define(["./kute.js"],function(e){return t(e),e});else if("object"==typeof module&&"function"==typeof require){var e=require("./kute.js");module.exports=t(e)}else{if("undefined"==typeof window.KUTE)throw new Error("Attributes Plugin requires KUTE.js.");t(e)}}(function(t){"use strict";var e,r=window,n=r.KUTE,i=r.dom,o=n.prS,u=n.pp,a=r.Interpolate.unit,f=r.Interpolate.number,c=r.Interpolate.color,s=function(t,e){return t.getAttribute(e)},p=["fill","stroke","stop-color"],l=n.truC,d=n.truD,v=function(t){return/[A-Z]/g.test(t)?t.replace(t.match(/[A-Z]/g)[0],"-"+t.match(/[A-Z]/g)[0].toLowerCase()):t};o.attr=function(t,e,r){var n={};for(var i in r){var o=v(i).replace(/_+[a-z]+/,""),u=s(t,o);n[o]=p.indexOf(v(i))!==-1?u||"rgba(0,0,0,0)":u||(/opacity/i.test(i)?1:0)}return n},u.attr=function(t,r,n){"attr"in i||(i.attr=function(t,e,r,n,o){for(var u in n)i.attributes[u](t,u,r[u],n[u],o)},e=i.attributes={});var o,u={};for(o in r){var b=v(o),A=s(n,b.replace(/_+[a-z]+/,""));if(p.indexOf(b)===-1&&(/(%|[a-z]+)$/.test(r[o])||/(%|[a-z]+)$/.test(A))){var m=d(A).u||d(r[o]).u,w=/%/.test(m)?"_percent":"_"+m;o+w in e||(e[o+w]=function(t,e,r,n,i){var o=o||v(e).replace(w,"");t.setAttribute(o,a(r.v,n.v,n.u,i))}),u[o+w]=d(r[o])}else p.indexOf(b)>-1?(o in e||(e[o]=function(t,e,n,i,o){var u=u||v(e);t.setAttribute(u,c(n,i,o,r.keepHex))}),u[o]=l(r[o])):(o in e||(e[o]=function(t,e,r,n,i){var o=o||v(e);t.setAttribute(o,f(r,n,i))}),u[o]=parseFloat(r[o]))}return u}});

File diff suppressed because one or more lines are too long

2
dist/kute.min.js vendored

File diff suppressed because one or more lines are too long

View file

@ -17,14 +17,15 @@
// Browser globals
factory(KUTE);
} else {
throw new Error("Attributes Plugin require KUTE.js.");
throw new Error("Attributes Plugin requires KUTE.js.");
}
}( function (KUTE) {
'use strict';
var g = window, K = g.KUTE, DOM = g.dom, prepareStart = K.prS, parseProperty = K.pp,
unit = g.Interpolate.unit, number = g.Interpolate.number, atts,
var g = window, K = g.KUTE, DOM = g.dom, prepareStart = K.prS, parseProperty = K.pp,
unit = g.Interpolate.unit, number = g.Interpolate.number, color = g.Interpolate.color,
getCurrentValue = function(e,a){ return e.getAttribute(a); }, // get current attribute value
svgColors = ['fill','stroke','stop-color'], trueColor = K.truC, trueDimension = K.truD, atts,
replaceUppercase = function(a) {
return /[A-Z]/g.test(a) ? a.replace(a.match(/[A-Z]/g)[0],'-'+a.match(/[A-Z]/g)[0].toLowerCase()) : a;
};
@ -34,7 +35,7 @@
for (var a in v){
var _a = replaceUppercase(a).replace(/_+[a-z]+/,''),
_v = getCurrentValue(el,_a); // get the value for 'fill-opacity' not fillOpacity
f[_a] = _v || (/opacity/i.test(a) ? 1 : 0);
f[_a] = svgColors.indexOf(replaceUppercase(a)) !== -1 ? (_v || 'rgba(0,0,0,0)') : (_v || (/opacity/i.test(a) ? 1 : 0));
}
return f;
};
@ -54,15 +55,23 @@
var ats = {}, p;
for ( p in o ) {
var prop = replaceUppercase(p), cv = getCurrentValue(l,prop.replace(/_+[a-z]+/,''));
if ( /(%|[a-z]+)$/.test(o[p]) || /(%|[a-z]+)$/.test(cv) ) {
var u = K.truD(cv).u || K.truD(o[p]).u, s = /%/.test(u) ? '_percent' : '_'+u;
if ( svgColors.indexOf(prop) === -1 && (/(%|[a-z]+)$/.test(o[p]) || /(%|[a-z]+)$/.test(cv)) ) {
var u = trueDimension(cv).u || trueDimension(o[p]).u, s = /%/.test(u) ? '_percent' : '_'+u;
if (!(p+s in atts)) {
atts[p+s] = function(l,p,a,b,v) {
var _p = _p || replaceUppercase(p).replace(s,'');
l.setAttribute(_p, unit(a.v,b.v,b.u,v) );
}
}
ats[p+s] = K.truD(o[p]);
ats[p+s] = trueDimension(o[p]);
} else if ( svgColors.indexOf(prop) > -1 ) {
if (!(p in atts)) {
atts[p] = function(l,u,a,b,v) {
var _u = _u || replaceUppercase(u);
l.setAttribute(_u, color(a,b,v,o.keepHex));
}
}
ats[p] = trueColor(o[p]);
} else {
if (!(p in atts)) {
atts[p] = function(l,o,a,b,v) {

View file

@ -15,7 +15,7 @@
module.exports = factory(KUTE);
} else if ( typeof window.KUTE !== 'undefined' ) {
// Browser globals
window.KUTE.svg = window.KUTE.svg || factory(KUTE);
window.KUTE.svg = factory(KUTE);
} else {
throw new Error("SVG Plugin require KUTE.js.");
}
@ -141,7 +141,7 @@
return p;
},
showCircles = 1,
S = K.svg = {
S = {
showStartingPoints : function(s,e,v){ // showPoints helper function to visualize the points on the path
if (showCircles){
var c, a = arguments, cl, p, l;
@ -404,6 +404,15 @@
}
return c;
},
translate = g.Interpolate.translateSVG = function (s,e,a,b,v){ // translate(i+'(',')',a[i],b[i],v)
return s + ((a[1] === b[1] && b[1] === 0 ) ? number(a[0],b[0],v) : number(a[0],b[0],v) + ' ' + number(a[1],b[1],v)) + e;
},
rotate = g.Interpolate.rotateSVG = function (s,e,a,b,v){
return s + (number(a[0],b[0],v) + ' ' + b[1] + ',' + b[2]) + e;
},
scaleOrSkew = g.Interpolate.stfSVG = function (s,e,a,b,v){ // scale / skew
return s + number(a,b,v) + e;
},
stackTransform = function (w){ // helper function that helps preserve current transform properties into the objects
var bb = w._el.getBBox(), ctr = parseTransform(w._el.getAttribute('transform')), r, t, i,
cx = bb.x + bb.width/2, cy = bb.y + bb.height/2;
@ -439,22 +448,23 @@
// register the render function
if (!('svgTransform' in DOM)) {
DOM['svgTransform'] = function(l,p,a,b,v){
var tr = '', i;
for (i in b){
tr += i + '('; // start string
var tl = '', rt = '', sx = '', sy = '', s = '';
for (var i in b){
if ( i === 'translate'){ // translate
tr += (a[i][1] === b[i][1] && b[i][1] === 0 )
? number(a[i][0],b[i][0],v)
: number(a[i][0],b[i][0],v) + ' ' + number(a[i][1],b[i][1],v);
tl += translate(i+'(',')',a[i],b[i],v);
} else if ( i === 'rotate'){ // rotate
tr += number(a[i][0],b[i][0],v) + ' ';
tr += b[i][1] + ',' + b[i][2];
} else { // scale, skewX or skewY
tr += number(a[i],b[i],v);
rt += rotate(i+'(',')',a[i],b[i],v);
} else if ( i === 'scale'){ // scale
s += scaleOrSkew(i+'(',')',a[i],b[i],v);
} else if ( i === 'skewX'){ // skewX
sx += scaleOrSkew(i+'(',')',a[i],b[i],v);
} else if ( i === 'skewY'){ // skewY
sy += scaleOrSkew(i+'(',')',a[i],b[i],v);
}
tr += ') '; // end string
}
l.setAttribute('transform', tr.trim() );
l.setAttribute('transform', (tl+s+rt+sx+sy) );
}
}

View file

@ -57,13 +57,13 @@
return { r: parseInt(vrgb[0]), g: parseInt(vrgb[1]), b: parseInt(vrgb[2]), a: y*1 };
}
}
if (/#/.test(v)) {
if (/^#/.test(v)) {
vrgb = hexToRGB(v); return { r: vrgb.r, g: vrgb.g, b: vrgb.b };
}
if (/transparent|none|initial|inherit/.test(v)) {
return { r: 0, g: 0, b: 0, a: 0 };
}
if (!/#|rgb/.test(v) ) { // maybe we can check for web safe colors
if (!/^#|^rgb/.test(v) ) { // maybe we can check for web safe colors
var h = document.getElementsByTagName('head')[0]; h.style.color = v; vrgb = g.getComputedStyle(h,null).color;
h.style.color = ''; return v !== vrgb ? trueColor(vrgb) : {r:0,g:0,b:0};
}