Free shipping bars are one of the highest-ROI additions you can make to a Shopify store. They increase average order value by nudging customers to add more to their cart — and the best part is, you don't need a $10/month app to get one.

In this tutorial, you'll add a fully responsive, animated progress bar that shows customers exactly how close they are to free shipping. It updates dynamically with the cart and works on every OS 2.0 theme.

What You'll Build

The Code

Here's the complete snippet. Copy it, paste it into a new file in your Shopify theme, and you're done.

snippets/plynthr-free-shipping-bar.liquid
{% comment %}
  Plynthr — Free Shipping Progress Bar
  https://plynthr.com/snippets/free-shipping-bar/

  INSTALL:
  1. Create snippets/plynthr-free-shipping-bar.liquid
  2. Paste this code
  3. Add {%- render 'plynthr-free-shipping-bar' -%} in your cart drawer,
     cart page, or announcement area

  CUSTOMIZE:
  - Set your free shipping threshold below
  - --pfs-bar-color for the progress bar color
{% endcomment %}

{%- assign free_shipping_threshold = 100 -%}
{%- assign cart_total = cart.total_price | divided_by: 100.0 -%}
{%- assign remaining = free_shipping_threshold | minus: cart_total -%}
{%- assign progress = cart_total | divided_by: free_shipping_threshold | times: 100 | at_most: 100 -%}

<style>
  :root {
    --pfs-bg: #f5f5f5;
    --pfs-bar-color: #10b981;
    --pfs-bar-complete: #059669;
    --pfs-text-color: #333;
    --pfs-radius: 20px;
    --pfs-height: 8px;
  }

  .plynthr-shipping-bar {
    padding: 12px 16px;
    text-align: center;
  }

  .plynthr-shipping-bar__text {
    font-size: 13px;
    color: var(--pfs-text-color);
    margin-bottom: 8px;
    font-weight: 500;
  }

  .plynthr-shipping-bar__text strong {
    font-weight: 700;
  }

  .plynthr-shipping-bar__track {
    width: 100%;
    height: var(--pfs-height);
    background: var(--pfs-bg);
    border-radius: var(--pfs-radius);
    overflow: hidden;
  }

  .plynthr-shipping-bar__fill {
    height: 100%;
    border-radius: var(--pfs-radius);
    background: var(--pfs-bar-color);
    transition: width 0.5s ease;
    width: {{ progress }}%;
  }

  .plynthr-shipping-bar__fill.is-complete {
    background: var(--pfs-bar-complete);
  }
</style>

<div class="plynthr-shipping-bar">
  {%- if remaining <= 0 -%}
    <p class="plynthr-shipping-bar__text">🎉 You qualify for <strong>free shipping!</strong></p>
    <div class="plynthr-shipping-bar__track">
      <div class="plynthr-shipping-bar__fill is-complete" style="width: 100%"></div>
    </div>
  {%- elsif cart.item_count == 0 -%}
    <p class="plynthr-shipping-bar__text">Free shipping on orders over <strong>{{ free_shipping_threshold | money }}</strong></p>
    <div class="plynthr-shipping-bar__track">
      <div class="plynthr-shipping-bar__fill" style="width: 0%"></div>
    </div>
  {%- else -%}
    <p class="plynthr-shipping-bar__text">You're <strong>{{ remaining | money }}</strong> away from free shipping!</p>
    <div class="plynthr-shipping-bar__track">
      <div class="plynthr-shipping-bar__fill" style="width: {{ progress }}%"></div>
    </div>
  {%- endif -%}
</div>

You can also grab this from the snippet page on Plynthr.

Installation

  1. In your Shopify admin, go to Online Store → Themes → Edit Code
  2. Under Snippets, click "Add a new snippet" and name it plynthr-free-shipping-bar
  3. Paste the code above and hit Save
  4. Open the file where you want the bar to appear — typically sections/cart-drawer.liquid, sections/main-cart.liquid, or your announcement bar section
  5. Add this render tag: {%- render 'plynthr-free-shipping-bar' -%}
  6. Set your free shipping threshold by editing the free_shipping_threshold variable (default is 100)
  7. Save and preview your store

Customisation

All the visual properties are controlled by CSS custom properties (variables) in the :root block. Here's what you can change:

Troubleshooting

Bar isn't showing: Make sure the render tag is placed inside a Liquid template file, not a JSON template. Check your theme's structure — if you're on Dawn or a similar theme, the cart drawer is usually in sections/cart-drawer.liquid.

Progress doesn't update when adding items: The bar renders server-side, so it needs a page reload to update. For AJAX cart drawers, you'll need to re-render the snippet via JavaScript after cart updates, or use a fetch('/cart.js') call to get the cart total and update the bar width programmatically.

Currency symbol is wrong: The snippet uses Shopify's money filter, which automatically follows your store's currency settings. If it's showing the wrong format, check Settings → General → Store currency.

Threshold doesn't match your shipping rules: This snippet uses a hardcoded threshold for simplicity. If your free shipping rules are complex (region-based, weight-based), you may need to adjust the logic or use Shopify's native shipping calculator.

Want this done for you?

I'll install this on your Shopify store, test it across devices, and make sure it's working perfectly. Done within 24 hours.