Building a Pager Web Component – Part 4: Attributes
In the last post, we put our pager web component in a separate HTML file that can be referenced from any HTML page. In this post we will make our pager component read the attrbutes declared on the x-pager
tag.
Reading attributes
Firstly, we need to create a couple of variables to hold the page number, pageNumber
, and the total number of pages, pageCount
. We then need to do some extra work in createdCallback()
that reads the attributes declared on the x-pager
tag which we do in a new function called _readAttributes()
.
<script>
(function() {
var Proto = Object.create(HTMLElement.prototype),
importDoc = document.currentScript.ownerDocument,
root,
pageNumber = 1,
pageCount = 0;
Proto.createdCallback = function() {
var template = importDoc.querySelector("template"),
clone = document.importNode(template.content, true);
root = this.createShadowRoot();
root.appendChild(clone);
this._readAttributes();
};
Proto._readAttributes = function() {
var pageStr, pageCountStr;
pageStr = this.getAttribute("page");
if (!pageStr) {
pageStr = "0";
}
this.pageNumber = parseInt(pageStr, 10);
pageCountStr = this.getAttribute("page-count");
if (!pageCountStr) {
pageCountStr = "0";
}
this.pageCount = parseInt(pageCountStr, 10);
};
document.registerElement("x-pager", { prototype: Proto });
})();
</script>
Displaying the correct page
So far, we have read the attributes and stuffed them into variables. Our next step is to display the correct page number in the pager text. Let’s do that in a new function called _changePage()
. Here’s our component script now:
<script>
(function() {
var Proto = Object.create(HTMLElement.prototype),
importDoc = document.currentScript.ownerDocument,
root,
pageNumber = 1,
pageCount = 0;
Proto.createdCallback = function() {
var template = importDoc.querySelector("template"),
clone = document.importNode(template.content, true);
root = this.createShadowRoot();
root.appendChild(clone);
this._readAttributes();
this._changePage();
};
Proto._readAttributes = function() {
var pageStr, pageCountStr;
pageStr = this.getAttribute("page");
if (!pageStr) {
pageStr = "0";
}
this.pageNumber = parseInt(pageStr, 10);
pageCountStr = this.getAttribute("page-count");
if (!pageCountStr) {
pageCountStr = "0";
}
this.pageCount = parseInt(pageCountStr, 10);
};
Proto._changePage = function() {
root.querySelector(".x-pager-text").innerHTML =
"page " + this.pageNumber + " of " + this.pageCount;
};
document.registerElement("x-pager", { prototype: Proto });
})();
</script>
When you now hit the page that references the pager component, you should see the following if you have page="1"
and page-count="5"
in the x-pager
tag:
Handling attribute changes
The last thing we are going to do in this post is handle attribute changes. Let’s say we put the following script tag in the page that references the pager component:
<script>document.querySelector("x-pager").setAttribute("page", 3);</script>
At the moment nothing will happen because nothing is handling attribute changes in our component. To handle attribute changes we need to use attributeChangedCallback()
which is a standard callback function in a web component that gets invoked when an attribute changes. So, let’s change our component script to the following:
<script>
(function() {
var Proto = Object.create(HTMLElement.prototype),
importDoc = document.currentScript.ownerDocument,
root,
pageNumber = 1,
pageCount = 0;
Proto.createdCallback = function() {
var template = importDoc.querySelector("template"),
clone = document.importNode(template.content, true);
root = this.createShadowRoot();
root.appendChild(clone);
this._readAttributes();
this._changePage();
};
Proto._readAttributes = function() {
var pageStr, pageCountStr;
pageStr = this.getAttribute("page");
if (!pageStr) {
pageStr = "0";
}
this.pageNumber = parseInt(pageStr, 10);
pageCountStr = this.getAttribute("page-count");
if (!pageCountStr) {
pageCountStr = "0";
}
this.pageCount = parseInt(pageCountStr, 10);
};
Proto.attributeChangedCallback = function(attrName, oldVal, newVal) {
this._readAttributes();
if (attrName === "page" || attrName === "page-count") {
this._changePage();
}
};
Proto._changePage = function() {
root.querySelector(".x-pager-text").innerHTML =
"page " + this.pageNumber + " of " + this.pageCount;
};
document.registerElement("x-pager", { prototype: Proto });
})();
</script>
You should now see that changing the page
attribute on x-pager
in the page’s script will trigger the change in the web component.
That’s enough for this post. In the next post we will look at events …