This widget came in light since the launch of medium.com back in 2013.
The idea is simple, we create a function that calculate number of words in an article and divide that by 200 which is a count of words what an average person read in a minute. It gives our estimated reading time. You can definitely set that standard value. Medium uses 275 wpm.
Still confused? 🤔
Lets take an example: We have a 1200 words article. We assume a reading time of 200 words per minute that gives us 6 minutes of reading time (1200/200). Of course, you don’t have to manually calculate the read time of all your articles.
Now, you have an idea of what reading time is and how it is calculated. Lets check,
- Why you need to add one and
- How the estimated reading time widget provided by us for blogger homepage and posts different from other available articles online?
Why you need to show Reading time on blogger posts and homepage?
- It adds relevance/timeliness (just as we list author/date of publication...)
- It strives to display a transparent experience to potential readers (people may be commuting to work and have 10 minutes left on their trip),
- When readers are viewing the article page itself, they may look at the size of the scroll bar for an indication of article length. This is often erroneous as there may be a bunch of non-article content below the article itself (related posts, comments, footers etc).
How is this reading time widget different?
There are many plugins and widgets that display reading time on posts and homepage of Wordpress, Ghost and other platforms. What they do is calculate reading time on server and display on client's machine.
However, for blogger.com, there is no widget that can display reading time on homepage since blogger do not provide server-side support.
So, we are going to perform client side calculations and display reading times for every posts. This enables showing read time not only on blogger posts, but on homepage too.
We use AJAX requests to fetch contents of all articles and calculate reading time. This is the only solution for now. Please note, this will cause additional requests from your page and causes performance issues.
And this widget is not limited to Blogger, it works for Wordpress, Ghost and other platforms too.
Cool, hah?
Lets find out how you can add one to your blog. Here's a demo from one of my blogs:
How to add estimated reading time to blogger homepage and posts?
Take a backup of your blog and add this script above closing body tag.
You have my permission to share this widget in your blog, however, a backlink to this article is must. Also, keep credits intact.
There are two versions of code. Use one that fits your blog.
1) If your blog do not have load more button or Infinite Scroll
<script> /*<![CDATA[*/
// Estimated Reading Post Widget for Blogger Homepage and posts
// Code by : TwistBlogg.com
// Function to calculate Reading Time
// By default, reading speed is set to 200
function calcTime(content) {
const words = content.trim().split(/\s+/).length;
const time = Math.ceil(words / 200); // Adjust the value 200 to your desired reading speed
const label = time === 1 ? 'min' : 'mins';
return time + ' ' + label + ' read';
}
// Remote File Access
// Returns reading time of individual posts
function fetchContent(url, timeEl) {
const xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
const responseText = xhr.responseText;
const parser = new DOMParser();
const postDOM = parser.parseFromString(responseText, 'text/html');
const postContent = postDOM.querySelector('.post-body');
if (postContent) {
const readingTime = calcTime(postContent.textContent);
const childTimeEl = timeEl.querySelector('.reading-time');
if (childTimeEl) {
childTimeEl.textContent = readingTime;
childTimeEl.setAttribute('title', 'It takes ' + readingTime + 'ing time');
childTimeEl.setAttribute('aria-label', 'It takes ' + readingTime + 'ing time');
}
}
}
};
xhr.send();
}
// Grab attribute value of data-remote-path
function displayTime() {
const elemsWithDataPath = document.querySelectorAll('[data-remote-path]');
elemsWithDataPath.forEach(function(elem) {
const url = elem.dataset.remotePath;
fetchContent(url, elem);
});
}
document.addEventListener('DOMContentLoaded', displayTime);
/*]]>*/
</script>
2) If your blogger homepage has AJAX Load more or infinite scroll enabled, use this code instead of above. We added an active listener that reads dynamic changes in blogger HTML.
<script> /*<![CDATA[*/
// Estimated Reading Post Widget for Blogger Homepage and posts
// Code by : TwistBlogg.com
// Function to calculate Reading Time
// By default, reading speed is set to 200
function calcTime(content) {
const words = content.trim().split(/\s+/).length;
const time = Math.ceil(words / 200); // Adjust the value 200 to your desired reading speed
const label = time === 1 ? 'min' : 'mins';
return time + ' ' + label + ' read';
}
// Remote File Access
// Returns reading time of individual posts
function fetchContent(url, timeEl) {
const xhr = new XMLHttpRequest();
xhr.open('GET', url, true);
xhr.onreadystatechange = function() {
if (xhr.readyState === 4 && xhr.status === 200) {
const responseText = xhr.responseText;
const parser = new DOMParser();
const postDOM = parser.parseFromString(responseText, 'text/html');
const postContent = postDOM.querySelector('.post-body');
if (postContent) {
const readingTime = calcTime(postContent.textContent);
const childTimeEl = timeEl.querySelector('.reading-time');
if (childTimeEl) {
childTimeEl.textContent = readingTime;
childTimeEl.setAttribute('title', 'It takes ' + readingTime + 'ing time');
childTimeEl.setAttribute('aria-label', 'It takes ' + readingTime + 'ing time');
}
}
}
};
xhr.send();
}
// Grab attribute value of data-remote-path
function displayTime() {
const elemsWithDataPath = document.querySelectorAll('[data-remote-path]');
elemsWithDataPath.forEach(function(elem) {
const url = elem.dataset.remotePath;
fetchContent(url, elem);
});
}
document.addEventListener('DOMContentLoaded', displayTime);
// Catch changes in HTML Structure
// Add this for Infinite Scroll Homepage
if (window.location.pathname === '/' || window.location.pathname === '/search') {
const targetNode = document.body;
const observer = new MutationObserver(function(mutationsList) {
mutationsList.forEach(function(mutation) {
if (mutation.type === 'childList') {
mutation.addedNodes.forEach(function(node) {
if (node.nodeType === Node.ELEMENT_NODE && node.matches('[data-remote-path]')) {
fetchContent(node.dataset.remotePath, node);
}
});
}
});
});
observer.observe(targetNode, {
childList: true,
subtree: true
});
}
/*]]>*/
</script>
Now, you need to do two things:
1) Add link to data-remote-path
This step is important, you must pass links through data-remote-path
attribute in parent element for this widget to work. This enables you to not rely on any classes and set reading time for any posts. So, it works for:
- Homepage posts
- Related posts
- Pager Navigation posts - Hey, just a reminder we have shared cool pager navigation widget.
- Popular posts
- Anything...
Since we are focusing on blogger homepage, I will show you how to set data-remote-path in homepage articles and posts.
Search for <article>
tag and add this tag:
<article expr:data-remote-path='data:post.url'>
If you want to display reading time on other posts then you can directly pass link value to data-remote-path
. Example:
<li data-remote-path="https://www.twistblogg.com/2015/10/killer-seo-guides-for-newbie-blogger.html">
...
...
...
<!-- Location where you wish to display reading time-->
<span class="reading-time"/>
...
...
...
</li>
2) Add this piece of code where you want to display reading time.
In order to display reading time on blogger homepage, you need to add this class .reading-time
to positions you want to display.
<span class="reading-time"/>
That is all. You have a functioning estimated reading time widget for blogger that displays article on homepage and posts. Feel free to share and leave a comment. Happy Blogging 🙋💪