I originally wrote this post with my 1st implementation and noted that I didn’t have time to rebuild in a better way, but actually, it was easier than I expected, so here’s the final code to achieve this kind of meter bar:
<html>
<div class="meter-container">
<div class="heading-container">
<div class="quota-available">Remaining Credits:</div>
<div class="quota-expired" style="display: none;">You've run out of credits</div>
</div>
<div class="meter">
<div class="meter-bar"></div>
</div>
<div class="meter-label"></div>
</div>
</html>
<style>
html,
body {
background-color: transparent;
margin: 0;
padding: 0;
}
.meter-container {
display: flex;
flex-direction: column;
align-items: center;
width: 100%;
text-align: center;
background-color: transparent !important;
}
.labels {
display: flex;
justify-content: space-between;
width: 100%;
max-width: 500px;
font-size: 8px;
color: #333;
margin-bottom: 5px;
}
.meter {
width: 100%;
max-width: 500px;
height: 20px;
background-color: rgba(128, 128, 128, 0.2);
position: relative;
border-radius: 0px;
overflow: hidden;
margin-bottom: 5px;
}
.meter-bar {
height: 100%;
background-image: linear-gradient(45deg, #f1a161, #f1a161);
position: absolute;
left: 0;
top: 0;
border-radius: 0px;
}
.meter-label {
font-size: 10px;
color: #333;
}
.heading-container {
margin-bottom: 10px;
font-size: 14px;
}
</style>
<script>
document.addEventListener("DOMContentLoaded", function () {
const meterBar = document.querySelector(".meter-bar");
const meterLabel = document.querySelector(".meter-label");
const quotaAvailable = document.querySelector(".quota-available");
const quotaExpired = document.querySelector(".quota-expired");
let maxTokens, usedTokens;
if(window['logged_in_user'] && window['logged_in_user']['airtable_record_id']) {
maxTokens = window['logged_in_user']['Credit Allowance in Period'];
usedTokens = window['logged_in_user']['Total Tokens In Period'][0];
}
function updateMeter() {
if (maxTokens && usedTokens) {
const percentage = (usedTokens / maxTokens) * 100;
meterBar.style.width = `${percentage}%`;
meterLabel.textContent = `Used: ${usedTokens.toLocaleString()} credits / ${maxTokens.toLocaleString()} credits (${percentage.toFixed(2)}%)`;
// Change gradient to red when percentage reaches 100%
if (percentage >= 100) {
meterBar.style.backgroundImage = 'linear-gradient(45deg, #ff0000, #ff7f7f)';
quotaAvailable.style.display = 'none';
quotaExpired.style.display = 'block';
} else {
meterBar.style.backgroundImage = 'linear-gradient(45deg, #f1a161, #f1a161)';
quotaAvailable.style.display = 'block';
}
}
}
updateMeter();
});
</script>
The only things you’ll need to update to get this working are:
- The “Credit Allowance in Period” and “Total Tokens In Period” field names in Airtable. These are my field names and denote the total number of credits their allowed within the period, and the number of credits a user has consumed within their current billing period, respectively.
- You’ll also want to go and update the CSS styles to design / colour the bar however you want. This is super flexible and can adapt to your needs.
Things to note:
- The bar will auto-calculate the % used and adjust the progression of the bar (and include a % figure).
- If the % > 100% then the bar will turn red and display an out of credits warning.
- This is fully dynamic and will update each time the page reloads to include the newest data in Airtable.
- You can use this code in any custom code block anywhere on your Softr site, though I recommend only including it on pages/blocks that only logged in users can see (otherwise it’ll be zeroed as no data).
Let me know if any questions!