iron-media-query doesn't work - Polymer 1.0 - polymer

I'm new to Polymer (1.0).
My <iron-media-query> element is not working. No errors in the console but it does not display anything.
Some improvements would be awesome! I'm trying to get it up and running since 2 hours. :)
Thanks in advance
Ron
<!-- Works correctly -->
<link rel="import" href="../polymer/polymer.html">
<link rel="import" href="../iron-media-query/iron-media-query.html">
<dom-module id="custom-element">
<style>
// Styles here
</style>
<template>
<iron-media-query query="{{query}}" queryMatches="{{smallScreen}}"></iron-media-query>
<template if="{{smallScreen}}">
<strong>Small Screen</strong>
</template>
<template if="{{!smallScreen}}">
<strong>Big Screen</strong>
</template>
</template>
</dom-module>
<script>
Polymer({
is: 'custom-element',
properties: {
query: {
type: String,
notify: true
}
}
});
</script>
<custom-element query="(max-width:400px)"></custom-element>

You have to change queryMatches="{{}}" to query-matches="{{}}".

Since you also asked about optmizations:
Since you don't have a massive difference in the data between SmallScreen and not, so:
<strong>[[screenType]] Screen</strong>
<script>
Polymer({
is: 'custom-element',
properties: {
query: {
type: String,
notify: true
},
screenType: {type: String, computed: '_computeScreenType(smallScreen)'}
},
_computeScreenType: (t)=>{return t?"Small":"Big"}
});
</script>

Related

Array value initialized in element doesn't show at the mediator level

Not sure what I'm doing wrong, but I expect to see the length of an array I've initialized. However, I see an empty value instead, when I access the data at 'mediator' level.
This code is also in a jsbin: http://jsbin.com/wujaruy/edit?html,output
<!doctype html>
<head>
<base href="https://cdn.rawgit.com/download/polymer-cdn/1.5.0/lib/">
<link rel="import" href="polymer/polymer.html">
</head>
<body>
<dom-module id="x-container">
<template>
<!-- doesn't show the expected value of '3' -->
<div>In container; # of items:[[listItems.length]]</div>
<x-list listItems="{{listItems}}"></x-list>
</template>
<script>
Polymer({
is: 'x-container'
});
</script>
</dom-module>
<dom-module id="x-list">
<template>
<div>In x-list 1; # of items:[[listItems.length]]</div>
</template>
<script>
Polymer({
is: 'x-list',
properties: {
listItems: {type: Array, value: [1,2,3], notify: true}
}});
</script>
</dom-module>
<x-container listItems="{{listItems}}"></x-container >
</body>
Figured it out; I got bitten by the upper-case issue. Changing
<x-list listItems="{{listItems}}"></x-list>
to
<x-list list-items="{{listItems}}"></x-list>
fixes the issue

How to implement html chart in vaadin?

I have used this code in vaadin html file. But output is nothing.
Code refrence: https://vaadin.com/charts-for-polymer
Please let me know how to correct and implement in my vaadin design.
<!DOCTYPE html>
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/webcomponentsjs/0.7.21/webcomponents-lite.min.js"></script>
<link rel="import" href="https://cdn.vaadin.com/vaadin-charts/3.0.0-alpha9/vaadin-
charts.html">
</head>
<body>
<template is="dom-bind" id="app">
<vaadin-pie-chart id="pie-with-legend">
<title>Revenue by industry</title>
<subtitle>2015</subtitle>
<tooltip point-format="<b>{point.percentage:.1f}%</b>">
</tooltip>
<plot-options>
<pie allow-point-select="true" show-in-legend="true"cursor="pointer">
<data-labels enabled="true"format="{point.name}: {point.y:.1f} M€"></data-labels>
</pie>
</plot-options>
<data-series name="Revenue" data="[[seriesData]]"></data-series>
</vaadin-pie-chart>
<my-data-source data="{{seriesData}}"></my-data-source>
</template>
<dom-module id="my-data-source">
<script>
Polymer({
is: "my-data-source",
properties: {
data: {
type: Array,
notify: true,
value: [
["Aerospace", 53.0],
["Medical", 53.6],
["Agriculture", 25.6],
["Automotive", 17.0],
["Consumers", 12.4],
["Subsidies", 1.4]]
}
}});
</script>
</dom-module>
</body>
</html>
Your code works perfectly in chrome, yet it fails on firefox
(console: Polymer not defined).
What you need to do is, wrap the polymer code in a check like:
addEventListener('WebComponentsReady', function() {
Polymer({
is: "my-data-source",
....
see working example here: https://jsbin.com/tifafepefi/edit?html,output

Polymer: Passing properties to child element doesn't work

I'm trying to output data from a custom Polymer component <data-component> in an <iron-list> but nothing is shown when I open the page. It works when I pass an array of objects directly to the iron-list like <iron-list items='[{"name": "test1"}, {"name":"test2"}]' >
What am I doing wrong here and is the <template is="dom-bind" id="t"> mandatory?
index.html
<html>
<head>
<script src="../../webcomponentsjs/webcomponents-lite.js"></script>
<link rel="import" href="../data-component.html">
<link rel="import" href="../../iron-list/iron-list.html">
</head>
<body unresolved>
<template is="dom-bind" id="t">
<data-component>
<!--<iron-list items='[{"name": "test1"}, {"name":"test2"}]' > WORKS -->
<iron-list items="{{data}}" >
<template>
<div>
Name: <span>{{item.name}}</span>
</div>
</template>
</iron-list>
</data-component>
</template>
</body>
</html>
data-component.html
<link rel="import" href="../polymer/polymer.html">
<dom-module id="data-component">
<template>
<content></content>
</template>
</dom-module>
<script>
window.coolData = [
{"name": "Bob"},
{"name": "Tim"},
{"name": "Mike"}
];
Polymer({
is: 'data-component',
properties: {
data: {
value: window.coolData
}
}
});
</script>
I'm going to suggest an alternative answer to what I have already posted. If you want your data-component to always contain the iron-list then you can use this version here. However, if the content of the data-component should be more flexible use my other answer.
If you move the iron-list inside the data-component you can remove the dom-bind in your index.html.
data-component.html
<link rel="import" href="../polymer/polymer.html">
<dom-module id="data-component">
<template>
<iron-list items="{{data}}" >
<template>
<div>
Name: <span>{{item.name}}</span>
</div>
</template>
</iron-list>
</template>
</dom-module>
<script>
window.coolData = [
{"name": "Bob"},
{"name": "Tim"},
{"name": "Mike"}
];
Polymer({
is: 'data-component',
properties: {
data: {
type: Array,
value: window.coolData
}
}
});
</script>
index.html
<body unresolved>
<data-component></data-component>
</body>
You also have to add a data-binding to your data-component. Otherwise, the system does not know that data (in your iron-list) should refer to the data property in your custom element.
<data-component data="{{data}}">
<iron-list items="{{data}}" >
...
</iron-list>
</data-component>
The dom-bind is necessary if you want to have data-binding outside of a Polymer element, which seems to be the case here.
You should also make sure that the data property is configured to notify changes and that its type is set to Array.
Polymer({
is: 'data-component',
properties: {
data: {
type: Array,
value: window.coolData,
notify: true
}
}
});

Polymer 1.0 deep path array binding

I am trying to get the following to work. It initially of course renders the content of parentItems, but when changing it, the template looping over the parentItems is not invoked. I have looked at the notifyPath, but am not sure if this is the right direction
<!doctype html>
<html>
<head>
<script src='bower_components/webcomponentsjs/webcomponents-lite.min.js'></script>
<link rel='import' href='bower_components/paper-button/paper-button.html'>
</head>
<body>
<dom-module id='my-element'>
<template>
<template is='dom-repeat' items='{{parentValues}}'>
<template is='dom-repeat' items='{{item.childValues}}'>
<div>{{item.value}}</div>
</template>
</template>
<paper-button on-tap='click'>click me</paper-button>
</template>
</dom-module>
<script>
Polymer({
is: 'my-element',
properties: {
parentValues: {
type: Array,
value: function() { return [ { childValues: [ { value: 'original value' } ] } ]}
}
},
click: function() {
this.parentValues[0].childValues[0].value = 'new value';
}
});
</script>
<my-element></my-element>
</body>
</html>
How can I get it to work?
Thanks a million :-)
I believe the issue, which #jeanPokou solved was that you need to use the 'this.set(Object, New Value)' to set the value on the nested object.
You can check this video from the 'Ask Polymer' series to learn more about why it doesn't update nested values: https://youtu.be/0GxteaIaj2Q
You need to use dom-repeat with as scope in your binding, and notifyPath to bubble up change to your array when changed
<!doctype html>
<html>
<head>
<script src='bower_components/webcomponentsjs/webcomponents-lite.min.js'></script>
<link rel='import' href='bower_components/paper-button/paper-button.html'>
</head>
<body>
<dom-module id='my-element'>
<template is='dom-repeat' items='{{parentValues}}' as ="parent">
<template is='dom-repeat' items='{{parent.childValues}}' as="child">
<div>{{child.value}}</div>
</template>
</template>
<paper-button on-tap='click'>click me</paper-button>
</template>
</dom-module>
<script>
Polymer({
is: 'my-element',
properties: {
parentValues: {
type: Array,
value: function() { return [ { childValues: [ { value: 'original value' } ] } ]}
}
},
click: function() {
// notify path to the properties using the polymer syntax
this.set('parentValues.0.childValues.0.value','changed value');
}
});
</script>
<my-element></my-element>
</body>
</html>

Polymer 1.0 services issue

I'm working on a reddit client using polymer to check out web compoments technologies. I started with the 0.5 version and got back on this project recently. That when I found out that polymer had the 1.0 released so I started over (as it wasn't that advanced anyway).
I have a service that use the iron-ajax to request reddit api and look for the posts. Here is the code :
<link rel="import" href="../../bower_components/polymer/polymer.html">
<link rel="import" href="../../bower_components/iron-ajax/iron-ajax.html">
<dom-module id="reddit-list-service">
<template>
<iron-ajax
url='https://www.reddit.com/new.json'
handle-as='json'
debounce-duration="300"
on-response='handleResponse'
debounce-duration="300"
auto>
</iron-ajax>
</template>
</dom-module>
<script>
(function () {
Polymer({
is: 'reddit-list-service',
properties: {
modhash: {
type: String,
value: function() {
return '';
}
},
posts: {
type: Array,
value: function () {
return [];
}
},
after: {
type: String,
value: function () {
return '';
}
}
},
// Update object properties from the ajax call response
handleResponse: function (resp) {
this.properties.modash = resp.detail.response.data.modhash;
this.properties.posts = resp.detail.response.data.children;
this.properties.after = resp.detail.response.data.after;
this.post = this.properties.posts; // just to try
console.log(this.properties.posts);
}
});
})();
</script>
My log shows me that I get posts from the API and that's great!
Here's the issue when I want to use this service to make a list out of the posts array I can't figure out how to get them into my list compoment which is below :
<link rel="import" href="../../bower_components/polymer/polymer.html">
<link rel="import" href="../reddit-list-service/reddit-list-service.html">
<dom-module id="reddit-post-list">
<template>
<reddit-list-service posts="{{posts}}">
</reddit-list-service>
<template is="dom-repeat" id="post-list" posts="{{posts}}">
<p>{{post.author}}</p>
<template>
</template>
</dom-module>
<script>
(function () {
Polymer({
is: 'reddit-post-list',
properties: {
},
});
})();
</script>
I've tried several think I saw in the documentation but I can't figure out what's wrong the author property doesn't show up.
Any clue?
You have a few things that aren't quite right here. In reddit-post-list you are not using the dom-repeat template correctly. See below:
<link rel="import" href="bower_components/polymer/polymer.html">
<link rel="import" href="reddit-list-service.html">
<dom-module id="reddit-post-list">
<template>
<reddit-list-service posts="{{posts}}"></reddit-list-service>
<template is="dom-repeat" items="[[posts]]">
<p>{{item.data.author}}</p>
</template>
</template>
</dom-module>
<script>
Polymer({
is: "reddit-post-list"
});
</script>
You need an attribute called items which is the array the dom-repeat will iterate over. Inside the iteration you need to refer to item as this is the array item for the current iteration. Here are the docs.
For you reddit-list-service, you need to set the the reflectToAttribute and notify attributes to true on your posts property. This means that any changes to this property are reflected back on the posts attribute on the reddit-list-service element. See here for more information.
<link rel="import" href="bower_components/polymer/polymer.html">
<link rel="import" href="bower_components/iron-ajax/iron-ajax.html">
<dom-module id="reddit-list-service">
<template>
<iron-ajax auto url="https://www.reddit.com/new.json" handle-as="json" on-response="handleResponse"></iron-ajax>
</template>
</dom-module>
<script>
Polymer({
is: "reddit-list-service",
properties: {
modhash: {
type: String,
value: ""
},
posts: {
type: Array,
value: function () {
return [];
},
reflectToAttribute: true, // note these two new attributes
notify: true
},
after: {
type: String,
value: ""
}
},
// Update object properties from the ajax call response
handleResponse: function (resp) {
this.modash = resp.detail.response.data.modhash;
this.posts = resp.detail.response.data.children;
this.after = resp.detail.response.data.after;
}
});
</script>
I have also tidied up the following things:
Removed the immediately called function wrapper from the <script> tags as these are not needed.
When referring to properties in your element you only need to use this.PROPERTYNAME rather than this.properties.PROPERTYNAME.
Having looked at the JSON returned, it appears that the author property is on the another property called data.
When you declare a value for a property in your element, you only need to have a function that returns a value if the property type is an Object or Array.