So i've been playing around with the neon element examples. Specifically the load example.
I'm able to accomplish what I want but I feel there should be a more elegant way to do it. The way the example loads content is by creating an array inside of a config
object and then uses a dom-repeat
to stamp them out all from within animated-grid.html
This seems to force very tight coupling between the animations and the content that is being animating. I don't want to encapsulate content in side of my grid I basically want to say Hey I want an animated grid here are the cells/content to be put inside of it
and then having the animated grid take care of laying out and animating those children
I set out to create an API that was more declarative like this.
<animated-grid id="grid">
<div style="background-color: #9C27B0"> <span>1</span> </div>
<div style="background-color: #4CAF50"> <span>2</span> </div>
<div style="background-color: #2196F3"> <span>3</span> </div>
<div style="background-color: #673AB7"> <span>4</span> </div>
<div style="background-color: #FF9800"> <span>5</span> </div>
<div style="background-color: #049688"> <span>6</span> </div>
</animated-grid>
I figured I could change the css selectors from .tile
to :host::content div
.
Then the template to
<template>
<content id='content'></content>
</template>
I then took a stab at rewritting the attached method to get the children in the lightdom instead of queryselecting for .tile
attached: function() {
this.async(function() {
var nodeList = Polymer.dom(this.$.content).getDistributedNodes();
// I only want to animate divs
nodelist = nodeList.filter(function(node){
return (node.nodeName === "DIV");
});
this.animationConfig['entry'][0].nodes = nodeList;
});
},
However, I keep getting a nasty error in my console.
The final code for animated-grid looked like this:
<!--
Copyright (c) 2015 The Polymer Project Authors. All rights reserved.
This code may only be used under the BSD style license found at http://polymer.github.io/LICENSE.txt
The complete set of authors may be found at http://polymer.github.io/AUTHORS.txt
The complete set of contributors may be found at http://polymer.github.io/CONTRIBUTORS.txt
Code distributed by Google as part of the polymer project is also
subject to an additional IP rights grant found at http://polymer.github.io/PATENTS.txt
-->
<link rel="import" href="../../../polymer/polymer.html">
<link rel="import" href="../../../paper-styles/paper-styles.html">
<link rel="import" href="../../neon-shared-element-animatable-behavior.html">
<dom-module id="animated-grid">
<link rel="import" type="css" href="../shared.css">
<style>
:host {
display: block;
}
:host::content div {
display: inline-block;
float: left;
color: white;
vertical-align: top;
width: calc(100% / 3);
height: calc(100% / 2);
@apply(--paper-font-title);
@apply(--layout-vertical);
@apply(--layout-center-center);
}
:host::content div:hover {
@apply(--shadow-elevation-2dp);
position:relative;
}
</style>
<template>
<content id='content'></content>
</template>
</dom-module>
<script>
Polymer({
is: 'animated-grid',
behaviors: [
Polymer.NeonSharedElementAnimatableBehavior
],
properties: {
animationConfig: {
type: Object,
value: function() {
return {
'entry': [{
name: 'cascaded-animation',
animation: 'transform-animation',
transformFrom: 'translateY(100%)',
transformTo: 'none',
timing: {
delay: 50
}
}]
}
}
}
},
attached: function() {
this.async(function() {
var nodeList = Polymer.dom(this.$.content).getDistributedNodes();
// I only want to animate divs
nodelist = nodeList.filter(function(node){
return (node.nodeName === "DIV");
});
this.animationConfig['entry'][0].nodes = nodeList;
});
},
_computeTileClass: function(color) {
return 'background-color: ' + color + '';
}
});
</script>
UPDATE: A good friend pointed out that while JavaScript is still insane, it's insane for different reasons than erroneously listed here. The error was that the variable being assigned into, nodelist
, from the filter, did not have a capital "L", like the var nodeList
does. In JS, this means nodelist
is now in the global variable object, global.nodelist
, which is why nodeList
seemingly wasn't filtered or assigned correctly into. So, another solution is to simply capitalize nodelist
to nodeList
in the filter return, and it should be fine.
Everything you're doing is fine and good (the async
in attached is the right way to setup your animationConfig
), with the exception of one thing.
The error you're getting is because you're attempting to animate text nodes with the cascade-animation
you setup.
You're attempting to animate text nodes because your variable nodeList
contains all the original 13 light dom children, which includes the text nodes, instead of just divs.
The reason your filtered array wasn't filtered, is because JavaScript is insane, and assigning into the array doesn't work as expected, like in every other language.
A solution is to use a new variable for the filter results:
var divNodes = nodeList.filter(function(node){
return (node.nodeName === 'DIV');
});
this.animationConfig.entry[0].nodes = divNodes;