Looking for different pattern match in app-route - polymer

I am using the Polymer CLI to create an app. I am utilizing Encapsulated Routing with Elements and Step 1. Get set up am trying to match the following patterns:
/analyze/:p1
/analyze/:p1/:p2
/analyze/:p1/:p2/:p3
That routes to 3 different web components.

For your <app-route> element, set the following attributes:
pattern = your desired route pattern
data = property binding to contain the parsed paths
In your case:
<app-route
pattern="/analyze/:p1/:p2/:p3"
data="{{routeData}}">
</app-route>
{{routeData}} will contain:
{
p1: 'a',
p2: 'b',
p3: 'c'
}
<head>
<base href="https://polygit.org/polymer+:master/components/">
<script src="webcomponentsjs/webcomponents-lite.min.js"></script>
<link rel="import" href="polymer/polymer.html">
<link rel="import" href="app-route/app-route.html">
<link rel="import" href="paper-input/paper-input.html">
</head>
<body>
<x-foo></x-foo>
<dom-module id="x-foo">
<template>
<app-route
route="{{route}}"
pattern="/analyze/:p1/:p2/:p3"
data="{{routeData}}"
tail="{{tail}}">
</app-route>
</template>
<script>
Polymer({
is: 'x-foo',
ready: function() {
this.route = {path: "/analyze/a/b/c/d/e/f"};
console.log('p1', this.routeData.p1);
console.log('p2', this.routeData.p2);
console.log('p3', this.routeData.p3);
console.log('tail', this.tail.path);
}
});
</script>
</dom-module>
</body>
jsbin

Related

Polymer dom-if not re-firing

I have been having problems with my Polymer 2 app, I first through it was the routing but I found that after hitting this page and the Dom-if fires when navigating back to the page it is not re-firing.
EG,
If I am on url/matters/6719 it displays the details page, but if I click the back button and go to url/matters the dom-if is not being hit again and its still showing me the details page,
It also happens when using my navigation selector which is set up like the PWA starter kit.
<link rel="import" href="../bower_components/polymer/polymer-element.html">
<link rel="import" href="../bower_components/app-route/app-location.html">
<link rel="import" href="../bower_components/app-route/app-route.html">
<link rel="import" href="../bower_components/iron-pages/iron-pages.html">
<link rel="import" href="../bower_components/iron-selector/iron-selector.html">
<link rel="import" href="shared-styles.html">
<link rel="import" href="Matters/matter-list.html">
<link rel="import" href="MatParties/matparty-list.html">
<link rel="lazy-import" href="Matters/matter-detail.html">
<dom-module id="my-matters">
<template>
<style include="shared-styles">
:host {
display: block;
padding: 10px;
}
</style>
<app-route route="{{route}}" pattern="/:matter_id" data="{{routeData}}" tail="{{subroute}}">
<app-route route="{{subroute}}" pattern="/matparties/:this_page" data="{{pageData}}"></app-route>
</app-route>
<div class="card">
<template is="dom-if" if="[[_subidIsDefined(pageData.this_page)]]">
<matparty-list linkedmatpartyid="[[pageData.this_page]]"></matparty-list>
</template>
<template is="dom-if" if="[[!_subidIsDefined(pageData.this_page)]]">
<template is="dom-if" if="[[!_idIsDefined(routeData.matter_id)]]">
<matter-list></matter-list>
</template>
<template is="dom-if" if="[[_idIsDefined(routeData.matter_id)]]">
<matter-detail linkedmatterid="[[routeData.matter_id]]"></matter-detail>
</template>
</template>
</template>
<script>
class Matters extends Polymer.Element {
static get is() { return 'my-matters'; }
_subidIsDefined(subid) {
//There are probably ways to optimize this
if (subid) {
return true;
}
return false;
}
_idIsDefined(id) {
//There are probably ways to optimize this
if (id) {
return true;
}
return false;
}
}
window.customElements.define(Matters.is, Matters);
</script>
</dom-module>
have you checked the pattern? Normally the pattern should respect the url pattern.... in your case "url/matters/6719"
Since you have defined the pattern="/matparties/:this_page" on the router and matparties is != 'matters' in 'url/matters/6719' that could generate the error. I don't know if you have defined a base url that generate also some issues on this regards.
So the url should be matparties/6719 to match the pattern and resolve into the dom-if

Imperatively setting attribute to declaratively created child element before ready in Polymer

Similar to this question, Init polymer attributes before ready(), but not quite the same.
Is it possible to imperatively set attribute of a child element in Polymer before the ready event of that child element fires?
https://plnkr.co/edit/fM7lAflOLWOFuIiE7e9q?p=preview
index.html:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<script src="https://polygit.org/components/webcomponentsjs/webcomponents-lite.min.js"></script>
<link href="https://polygit.org/components/polymer/polymer.html" rel="import">
<link href="user-profile.html" rel="import">
</head>
<body>
<user-profile></user-profile>
</body>
</html>
user-profile.html:
<link href="https://polygit.org/components/polymer/polymer.html" rel="import">
<link href="address-card.html" rel="import">
<dom-module id="user-profile">
<template>
<address-card address$="{{address}}"></address-card>
</template>
<script>
Polymer({
is: "user-profile",
properties: {
address: {
type: String,
value: "Pass the value to the child"
}
}
});
</script>
</dom-module>
address-card.html:
<link href="https://polygit.org/components/polymer/polymer.html" rel="import">
<dom-module id="address-card">
<template>
{{content}}
</template>
<script>
Polymer({
is: "address-card",
properties: {
address: String
},
ready: function () {
alert(this.address);
}
});
</script>
</dom-module>
The element <user-profile>, pass the value {{primaryAddress}} to his child the element <address-card>. The element <user-profile> is a "mediator" that control/assing value to his child.
<dom-module id="user-profile">
<template>
…
<address-card address="{{address}}"></address-card>
</template>
…
properties: {
address: {
type: String,
value: "Pass the value to the child"
}
}
</dom-module>
In this scenario, I use the data binding system to pass the value from the parent to the child.
Linking paths with data bindings

Polymer _routePageChagned running twice

When I change the page via a link or via JS this.set('route.path', 'packages'); the _routePageChagned method is running twice. Its also happening on when the page loads for the first time.
This is also happening in the default polymer starter kit template build from the CLI.
I'm I missing something? How can this occur?
<link rel="import" href="../bower_components/polymer/polymer.html">
<link rel="import" href="../bower_components/app-route/app-location.html">
<link rel="import" href="../bower_components/app-route/app-route.html">
<link rel="import" href="../bower_components/iron-pages/iron-pages.html">
<link rel="import" href="my-icons.html">
<link rel="import" href="pages/my-loading.html">
<dom-module id="my-app">
<template>
<style>
</style>
<app-location route="{{route}}"></app-location>
<app-route
route="{{route}}"
pattern="/:page"
data="{{routeData}}"
tail="{{subroute}}"></app-route>
<iron-pages
id="pages"
selected="[[page]]"
attr-for-selected="name"
fallback-selection="view404"
selected-attribute="visible"
role="main">
<my-loading name="loading"></my-loading>
<my-login name="login"></my-login>
<my-view404 name="view404"></my-view404>
<my-view403 name="view403"></my-view403>
<my-packages name="packages"></my-packages>
</iron-pages>
</template>
<script>
Polymer({
is: 'my-app',
properties: {
/**
* The current page.
*/
page: {
type: String,
reflectToAttribute: true
},
},
observers: [
'_routePageChanged(routeData.page)'
],
_routePageChanged: function(page) {
console.log(page);
var resolvedPageUrl = this.resolveUrl('pages/my-' + page + '.html');
this.importHref(resolvedPageUrl, function() {
this.page = page;
}.bind(this), undefined, false);
}
});
</script>
</dom-module>
This works as a hack fix, still no idea why it's needed though.
_pageChange: function(page) {
this.debounce(function() {
// Load page import on demand. Show 404 page if fails
var resolvedPageUrl = this.resolveUrl('pages/my-' + page + '.html');
this.importHref(resolvedPageUrl,
this._pageLoaded.bind(this, page), // loaded callback
this._pageChange.bind(this, 'view404'),
true);
}.bind(this), 100);
}

Subset hyphenated JSON element in Polymer data binding

Consider the following JSON:
{"EMD-4091":["EMD-4084","EMD-4090"]}
which is the result of a fictitious iron-ajax call as follows:
<iron-ajax
auto
url="http://me.com/get/EMD-4091"
handle-as="json"
last-response="{{my_data}}">
</iron-ajax>
Suppose I need to refer to the inner array, say, in a dom-repeat: how would I refer to 'EMD-4091' in a data binding? e.g.
<template is="dom-repeat" items="{{my_data????}}> <!-- what should this be?-->
<p>{{item}}</p>
</template>
If the data wasn't hyphenated this is a trivial task. The hyphen is the challenge I'm facing.
P
The data binding can still parse the hyphenated key without a problem, so your binding would be:
items="{{my_data.EMD-4091}}"
HTMLImports.whenReady(() => {
"use strict";
Polymer({
is: 'x-foo',
properties : {
my_data: {
type: Array,
value: () => ({"EMD-4091":["EMD-4084","EMD-4090"]})
}
}
});
});
<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>
<x-foo></x-foo>
<dom-module id="x-foo">
<template>
<template is="dom-repeat" items="[[my_data.EMD-4091]]">
<div>[[item]]</div>
</template>
</template>
</dom-module>
</body>
codepen

app-router not working imperatively way

I have this Polymer custom element:
<link rel="import" href="../../../bower_components/polymer/polymer.html">
<link rel="import" href="../../../bower_components/core-animated-pages/core-animated-pages.html">
<link rel="import" href="../../../bower_components/app-router/app-router.html">
<polymer-element name="custom-pages" attributes="selected">
<template>
<link rel="stylesheet" href="custom-pages.css">
<app-router id="router" bindRouter core-animated-pages transitions="cross-fade-all" trailingSlash="ignore">
<template repeat="{{page in pages}}">
<app-router path="{{page.path}}" import="{{page.url}}"></app-router>
</template>
</app-router>
</template>
<script>
(function() {
Polymer({
selected: 0,
pages: [{
path: "/home",
url: '../custom-home/custom-home.html'
}, {
path: "/about",
url: '../custom-about/custom-about.html'
}],
selectedChanged: function(oldValue, newValue) {
router = this.$.router;
router.go(this.pages[newValue].path);
}
});
})();
</script>
</polymer-element>
Elements custom-home and custom-about should be lazy loaded when "selected" change, but not is happening (no page is displayed).
You have a syntax error in your template definition, nested tags are to be app-route rather than app-routeR:
<app-router id="router" ...>
<template repeat="{{page in pages}}">
<!-- ⇓ superfluous r, nested are app-route -->
<app-router path="{{page.path}}" import="{{page.url}}"></app-router>
<!-- SHOULD BE: -->
<app-route path="{{page.path}}" import="{{page.url}}"></app-route>
</template>
</app-router>
Currently you have created a bundle of empty routers.
Plus, the documentation says:
If you use go(path, options) you should also set the mode to hash or pushstate on the router.
I am not sure if this affects your case, since you do not seem to pass options.
Hope it helps.