Exploring The Turbo Drive Navigation Progress Bar In Lucee CFML
When you enable Turbo Drive in a Hotwire application, Turbo Drive intercepts native link clicks and form submissions and then re-implements them using the browser's fetch()
API. If a fetch()
call takes longer than 500ms
to complete (a configurable default), Hotwire will render a progress bar at the top of the window. The progress bar is a simple <div>
element that can be lightly styled using CSS. I just wanted to take a quick look at how the progress bar works in a ColdFusion application.
View this code in my ColdFusion + Hotwire Demos project on GitHub.
To test Hotwire's progress bar functionality, I created a small ColdFusion application with three pages:
index.cfm
- loads instantly.products.cfm
- sleeps between 1-5 seconds before rendering.about.cfm
- sleeps 25-seconds before rendering.
These pages - and their embedded sleep()
commands - give me enough time to look at the DOM (Document Object Model) while the progress bar is being rendered. Here's my about.cfm
page, which does the most sleeping:
<cfscript>
sleep( 25000 ); // 25-seconds.
</cfscript>
<cfmodule template="./tags/page.cfm">
<cfoutput>
<h1>
ColdFusion + Hotwire Navigation Progress Bar Demo
</h1>
<p>
<a href="index.htm">Home</a> -
<a href="products.htm">Products</a> -
<a href="about.htm"><strong>About</strong></a>
</p>
<!--- ... truncated, filler copy ... --->
</cfoutput>
</cfmodule>
The sleep( 25000 )
function call is the only thing of note in this template - the rest of the template is just navigation links and filler copy. And, if I load this app and then navigate to the about.cfm
page, we get the following page output:
As you can see, the Turbo Drive progress bar is implemented as an empty div element with position: fixed
. It's injected in between the <head>
and <body>
tags. And, to be honest, I didn't even know that you could put DOM content in between those two elements. I'm sure that works to side-step display
and z-index
issues that might occur if placed inside the body tag.
ASIDE: Turbo Drive is using a
z-index
of 2,147,483,647. This is the largest value that can fit inside a 32-bit signed integer. According to this post by Tan Li Hau, the CSS specification doesn't mention any limit onz-index
; however, thez-index
value is often stored as a 32-bit signed integer, making the Turbo Drivez-index
value the highest possible value.
The .turbo-progress-bar
CSS class definition is defined in a <style>
tag that is prepended to the <head>
tag as the first child. This means, from a cascading and specificity standpoint, overriding the progress bar style is extremely easy. All you have to do is define your own .turbo-progress-bar
property block. For example, I changed the background to pink:
.turbo-progress-bar {
background-color: #ec005a ;
}
And, when I re-render the page and navigate to about.cfm
, I get pink!
Hotwire's Turbo Drive feels like such an elegant drop-in solution to progressively enhance a ColdFusion application. I love all this attention to detail that the Basecamp team put into this stuff.
fetch()
Calls
Turbo Drive Cancels Irrelevant Unrelated to the Turbo Drive progress bar functionality, I noticed something interesting as I was playing around with slow-loading pages: pending navigation fetch()
calls are aborted if the user initiates a new navigation. For example, if I load this ColdFusion application and then click the About section a few times before it has a chance to load, here's what we see in the Chrome Dev Tools Network activity:
As you can see, the two prior navigation calls have been aborted, leaving only the most recent navigation still in progress. The ColdFusion requests are almost certainly still being processed on the server-side; but, at least this approach reduces the number of open network connections on the client-side. Again, lots of great attention to detail in the Hotwire framework.
Want to use code from this post? Check out the license.
Reader Comments
Post A Comment — ❤️ I'd Love To Hear From You! ❤️
Post a Comment →