Polymer: Rendering looped JSON - javascript

I've seen a few answer to this but for some reason I can't wrap my head around why this isn't working. I'm trying to get the values of a JSON array and output them in custom HTML elements in my template.
Polymer Element:
<polymer-element name="graph-optionsLoad">
<template>
<core-ajax auto url="/getDataHeaders"
handleAs="json" response="{{headerList}}"></core-ajax>
<div>TEST</div>
<ul>
<template repeat="{{h in headerList}}">
<li> {{h}}</li>
</template>
</ul>
</template>
<script>
Polymer( "graph-optionsLoad", {
headerListChanged: function(oldValue) {
console.log(this.headerList);
// this.headers;
}
});
</script>
</polymer-element>
JSON:
{
"headers": [
"MakeSpawnFish",
"MakeEndGame",
"MakeModeChange",
"MakeConnectComponent",
"MakeCircuitCreated",
"MakeStartGame",
"MakeSnapshot",
"MakeResetBoard",
"MakeAddComponent",
"MakeCaptureFish",
"MakeRemoveComponent",
"MakeDisconnectComponent"
]
}
HTML
<!DOCTYPE html>
<html>
<head>
<script src="/static/bower_components/webcomponentsjs/webcomponents.js"></script>
<link rel="import" href="/static/bower_components/my-elements/graph-optionsLoad.html">
<link rel="import" href="/static/bower_components/core-ajax/core-ajax.html">
<!-- <link rel="import" href="/static/greeting-tag.html"> -->
</head>
<body>
<graph-optionsLoad></graph-optionsLoad>
<script>
</script>
</body>
</html>
All that seems to show up on the page is the "TEST" and the empty <ul></ul>

I don't know if this helps. But I'll put it up just in case it helps someone else. In Polymer 1.0:
<dom-module id="graph-optionsload">
<template>
<iron-ajax auto
url="/getDataHeaders"
handle-as="json"
last-response="{{headerList}}"
on-response="listChanged"></iron-ajax>
<div>TEST</div>
<ul>
<template is="dom-repeat" items="[[headerList]]" as="[[h]]">
<li>[[h]]</li>
</template>
</ul>
</template>
<script>
Polymer({
id: "graph-optionsload",
properties: {
headerList: {type: Array, value: ()=>{return []}, notify: true}
},
listChanged: function(oldValue) {
console.log(this.headerList);
// this.headers;
}
});
</script>
</dom-module>
That should work for you.

Related

Making polymer dom-repeat to work when a HTML block is added using .innerHTML

I am working on a polymer app where I need to fetch some HTML code block of code from external file and append to active file. I have specified the content to add myself.
Below is the code
<!DOCTYPE html>
<html>
<head>
<meta charset=utf-8 />
<title></title>
</head>
<body>
<!-- Bootstrap Core CSS -->
<link href="css/bootstrap.min.css" rel="stylesheet">
<link rel="import" href="bower_components/polymer/polymer.html">
<dom-module id="trail-app">
<template>
<style>
</style>
<button on-tap="loadContent">click</button>
<button on-tap="showContent">show</button>
<template is="dom-repeat" items='{{celsius}}'>
<div>[[item]]</div>
</template>
<div id="content"></div>
</template>
<script>
Polymer({
is: "trail-app",
properties:{
celsius:{}
},
ready:function(){
this.celsius = ["36","37","38","39","40","41"];
},
loadContent:function(data){
document.getElementById("content").innerHTML = '<template is="dom-repeat" items="{{Celsius}}">'+
'<div>[[item]]</div>'+
'</template>';
},
showContent:function(){
console.log(document.getElementById("content").innerHTML);
},
});
</script>
</dom-module>
<trail-app></trail-app>
</body>
</html>
when I loop through celsius using dom-repeat its working fine.
but if the same code is added using document.getElementById("content").innerHTML its giving
Polymer::Attributes: couldnt decode Array as JSON warning.
How to resolve this.
So I've addressed dynamic content like this using the templatizer behavior (https://www.polymer-project.org/1.0/docs/api/Polymer.Templatizer).
To use, create just a plain template with your dom-repeat inside that. Then in your loadContent method that's where you'll apply templatize and then stamp the template into the DOM.
<template id="repeatTempl">
<template is="dom-repeat" items="{{Celsius}}">
<div>[[item]]</div>
</template>
</template>
Include the Templatizer behavior:
behaviors: [Polymer.Templatizer]
Then your loadContent method would look something like this:
loadContent: function(data) {
var templ = this.$.repeatTempl;
this.templatize(templ);
var elem = this.stamp({Celsius: data});
Polymer.dom(this.$.content).appendChild(elem.root);
}

How to get properties in Polymer content element?

Probably something super easy, but I seem unable to find the answer.
I would like to replace the properties in the <content> section. But I don't understand how to push the title (with content hola) to the <content> section.
demo-app.html
<dom-module id="demo-app">
<template>
<style>
:host {
display: block;
}
</style>
<my-el>
[[title]] or {{title}}
</my-el>
</template>
...
my-el.html
<link rel="import" href="../../bower_components/polymer/polymer.html">
<dom-module id="my-el">
<template>
<style>
:host {
display: block;
}
</style>
<content></content>
</template>
<script>
Polymer({
is: 'my-el',
properties: {
title: {
type: String,
value: 'hola',
},
}
})
</script>
</dom-module>
PS:
I'm 99% sure there are some docs that I'm missing... Any link is welcome :-P
That's technically possible if <demo-app> had its own title property that you bound to <my-el>.title like this:
<dom-module id="demo-app">
<template>
<my-el title="{{title}}">
[[title]] or {{title}}
</my-el>
...
HTMLImports.whenReady(() => {
Polymer({
is: 'my-el',
properties: {
title: {
type: String,
value: 'Hello world!',
notify: true
}
}
});
Polymer({
is: 'demo-app'
});
});
<head>
<base href="https://polygit.org/polymer+1.7.0/components/">
<script src="webcomponentsjs/webcomponents-lite.min.js"></script>
<link rel="import" href="polymer/polymer.html">
</head>
<body>
<demo-app></demo-app>
<dom-module id="demo-app">
<template>
<style>
h1 {
color: blue;
}
</style>
<my-el title="{{title}}">
<h1>[[title]]</h1>
</my-el>
</template>
</dom-module>
<dom-module id="my-el">
<template>
<content></content>
<section>
<input type="text" value="{{title::input}}">
</section>
</template>
</dom-module>
</body>
codepen

How can I create a repeating element from data received from <iron-ajax>?

<iron-ajax auto
url='http://api.fantasy.nfl.com/v1/players/stats'
handle-as="json"
last-response="{{response}}"></iron-ajax>
<template is="dom-repeat" items="{{response}}">
<paper-material class="add-players">
<div class="layout horizontal center">
<h2>{{item.players.name}}</h2> //NOT SURE WHAT SYNTAX SHOULD BE
</div>
</paper-material>
</template>
I am using to return a response from a public API. The problem I have is that the API returns an object and Polymer does not allow us to do a dom-repeat over an object. I am really trying to access an array within that object, is there some way to extract that array from the object returned and do a dom-repeat over that array? If not is there another solution to accessing the response from polymer? Thank you!
You have to use {{response.players}} instead of {{response}} in the dom-repeat. Here is a working demo.
<!DOCTYPE html>
<html>
<head>
<title>paper-scroll-header-panel not working</title>
<script src="https://rawgit.com/webcomponents/webcomponentsjs/master/webcomponents.js"></script>
<base href="https://cdn.rawgit.com/download/polymer-cdn/1.0.1/lib/">
<link rel="import" href="iron-ajax/iron-ajax.html">
<link rel="import" href="paper-material/paper-material.html">
<!--<link rel="import" href="all-elements.html">-->
</head>
<body class="fullbleed">
<test-elem></test-elem>
<dom-module id="test-elem">
<template>
<iron-ajax auto
url='http://api.fantasy.nfl.com/v1/players/stats'
handle-as="json"
last-response="{{response}}"></iron-ajax>
<template is="dom-repeat" items="{{response.players}}">
<paper-material class="add-players">
<div class="layout horizontal center">
<h2>{{item.name}}</h2>
</div>
</paper-material>
</template>
</template>
<script>
Polymer({
is : "test-elem"
});
</script>
</dom-module>
</body>
</html>

How to two-way bind iron-input to dom-repeat's item?

I just started playing with Polymer 1.0 and am trying to do a very simple binding to collection. I am able to display text within dom-repeat, but the two-way binding to iron-input does not work.
I tried array of strings, and objects. No luck.
<link rel="import" href="bower_components/polymer/polymer.html">
<link rel="import" href="bower_components/iron-input/iron-input.html">
<dom-module id="hello-world">
<template>
<ul>
<template is="dom-repeat" items="{{data}}">
<li>{{item.value}}</li>
</template>
</ul>
<ul>
<template is="dom-repeat" items="{{data}}">
<li><input is="iron-input" bind-value="{{item.value}}"></input></li>
</template>
</ul>
</template>
</dom-module>
<script>
Polymer({
is: "hello-world",
ready: function() {
this.data = [
{ value: "Hello" },
{ value: "World!" }
];
}
});
</script>
Change to: value="{{item.value::input}}"
See here: http://plnkr.co/edit/QWdCk7ReXxtdKndwPdqq

How to pass object literals as polymer attributes

In order to test some polymer custom elements of mine in isolation, I would like to be able to pass in js object literals for some attributes that would ordinarily come from parent elements. I'm having trouble figuring out how to do this. See this example code. If it were working as I would like it to, it would display a 1 and a 2 next to each other, but it doesn't work.
<script src="http://www.polymer-project.org/webcomponents.js"></script>
<link rel="import" href="http://www.polymer-project.org/components/polymer/polymer.html">
<polymer-element name="my-element" attributes="stuff">
<template>
{{stuff.one}} {{stuff.two}}
</template>
<script>
Polymer('my-element', {
ready: function () {
console.log(this.stuff);
}
});
</script>
</polymer-element>
<my-element stuff='{"one": 1, "two": 2}'></my-element>
Polymer only converts the JSON text into an object, if you initialize the stuff property with an empty hash:
Polymer('my-element', {
stuff: {},
ready: function () {
console.log(this.stuff);
}
});
Without this, the stuff attribute is passed in as a string. The same goes for arrays.
Another way to do it:
myElem.html
<link rel="import"
href="http://www.polymer-project.org/1.0/samples/components/polymer/polymer.html">
<dom-module id="my-element">
<template>
<div> {{stuff.one}} {{stuff.two}} </div>
</template>
<script>
Polymer({
is: "my-element",
properties: {
stuff:{
type: Object,
value: {"one":"default_1","two":"default_2"}
}
}
});
</script>
</dom-module>
index.html
<!DOCTYPE html>
<html lang="en">
<head>
<script src="http://www.polymer-project.org/1.0/samples/components/webcomponentsjs/webcomponents-lite.js"></script>
<link rel="import" href="myElem.html">
</head>
<body>
<my-element></my-element>
<my-element stuff={"one":"1","two":"2"}></my-element>
</body>
</html>
Result
default_1 default_2
1 2
index.html
...
<body unresolved fullbleed layout vertical>
<my-post info='{"name":"Alex","id":"123"}' posts='[{"id":"456","name":"post1"},{"id":"789","name":"post2"}]'></my-post>
</body>
...
my-post.html
<link rel="import" href="../../bower_components/polymer/polymer.html">
<polymer-element name="my-post" attributes="info posts" >
<template>
{{info.name}}
<template repeat="{{post in posts}}">
<br> {{post.id}} - {{post.name}}
</template>
</template>
<script>
(function () {
Polymer({
ready: function() {
this.info=JSON.parse(this.info)
this.posts=JSON.parse(this.posts)
},
});
})();
</script>
</polymer-element>

Categories

Resources