Dynamically changing the favicon in Rails
How to render a favicon depending on the page or action in Ruby on Rails
The little details often make a big difference in the ever-evolving web development landscape. One such detail that can enhance user experience is the favicon — that tiny icon displayed in a browser’s tab or bookmarks. In this article, we’ll delve into how we should go about implementing dynamically changing the favicon. We’ll uncover the techniques and best practices for seamlessly altering this often overlooked feature, allowing your web application to adapt and communicate various states, notifications, or branding changes to your users in real time. Whether you’re a seasoned Rails developer or just getting started, this guide will equip you with the knowledge and tools to enhance your web applications with a dynamic favicon that reflects your site’s vitality and utility.
Let’s get right into it. I have created a Rails 7 application to demonstrate the ideas and concepts that I am going to go through in this article. If you are in a hurry please go to the end of the article to check out the whole Rails application code.
Page wise Favicon
First, we will discuss how to show a different favicon on different pages depending on a condition. This condition can be whatever you choose. For example, the root path of our application should show a heart favicon and when we go to another page it should show a star favicon and so and so forth for other pages as we need. This is the requirement we trying to achieve with page-wise favicons.
In my Rails 7 application, we have 4 favicons in app/assets/images
folder as follows:
Then we will change the application.html.erb
as we need. Here we would call a method select_favicon
with two arguments named controller_name
and action_name
(Provided by Rails. Read about it here and here.) to choose which favicon should be rendered on a particular page. The actual method definition we will discuss later.
After changing the main layout, we can discuss how to implement the select_favicon
method. For this, I am going to use a helper module called FaviconHelper
in the app/helpers
folder as follows:
So here what I have done is check the controller_name
and action_name
and depending on that render the favicon that I want whether it be 1st, 2nd, 3rd, or 4th. In Rails, we use favicon_link_tag
for the rendering of the favicon and asset_path
to get the favicons’ asset pipeline path. I have added the id favicon
to the favicon link tag for further improvements.
Here are a few screenshots after implementing page wise favicon feature:
Action-based and Event-based Favicon
In this section, we will discuss how to implement an action-based or event-based favicon change in the web page using Javascript with the Rails 7 application. Using default Rails 7 configurations, I will use Stimulus to change the favicon on a button click.
My home page HTML would look as follows. In there, you will see that I have used the Stimulus controller as “hello” which is the default controller in a new Rails 7 application as this is for demo purposes. If you desire you can create a new controller and use that one instead. I have given the asset_path
of each favicon in the format of an array to the controller value. If you want to learn more about what is happening with Stimulus related code please check out the resource from here.
On the button click favicon
method will trigger in the hello_controller.js
file. Let’s see how I implemented the Javascript code to change the favicon randomly in the favicon
method.
In the above code what we are doing is we get the array of favicons
which would be the favicons’ image paths and First we get the current favicon element using the getElementById
using the id which we added earlier and get a random value from 1 to 4 to choose the new favicon and then set that favicon using the setAttribute
method.
Here are a few screenshots after implementing this feature using the Change Favicon button:
Conclusion
In this article, I have presented two ways to dynamically change the favicon in a Rails application. Depending on the application one of them or both of them could be used. Please share your thoughts and any improvements that we might be able to make for these two approaches. I have written this article based on a Rails 7 application and older versions of Rails might need slightly different implementations to achieve the same results.
For reference here is my routes.rb
file:
Lastly, you can check out my Rails 7 application code hosted in Github from here.
I will be bringing these kinds of exciting articles where I explore nuggets throughout the Ruby ecosystem. Follow me now for a thrilling ride through all things Ruby 💎🤗
Email: randika.banura@gmail.com
LinkedIn: https://www.linkedin.com/in/randika-banura/
Github: https://github.com/randikabanura