fix collection filters, hero spacing, sale filter, and error page CSS

- collection filter bar: horizontal scroll on mobile instead of wrapping
  across 3 rows, smaller pills at mobile sizes
- add sale collection filter at /collections/sale (filters on_sale products)
- hero :page variant: add consistent top padding (var(--space-2xl))
- contact page: remove redundant top padding (hero handles it now)
- error page: fix CSS path from /assets/app.css to /assets/css/app.css
  (broken in production due to asset fingerprinting)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
jamey 2026-02-11 08:38:54 +00:00
parent 7c9fe57e6e
commit 0d583ca9a8
5 changed files with 50 additions and 18 deletions

View File

@ -59,16 +59,16 @@ Issues found during hands-on testing of the deployed prod site on mobile and des
- [x] Footer social icons should match the "Find me on" icons from the contact page - [x] Footer social icons should match the "Find me on" icons from the contact page
### Collections / all products ### Collections / all products
- [ ] Categories on all-products page are too spaced out - [x] Categories on all-products page are too spaced out
### Content pages ### Content pages
- [ ] Hero title spacing differs between content pages (about, delivery, etc.) — contact is fine - [x] Hero title spacing differs between content pages (about, delivery, etc.) — contact is fine
### Sale / filtering ### Sale / filtering
- [ ] Should there be a "Sale" section or filter for discounted products? - [x] Should there be a "Sale" section or filter for discounted products?
### Errors ### Errors
- [ ] 404 page is broken - [x] 404 page is broken (CSS path was wrong — `/assets/app.css` instead of `/assets/css/app.css`)
### Search (deferred — after usability fixes) ### Search (deferred — after usability fixes)
- [ ] Search doesn't work (modal opens but no results/functionality) — see [docs/plans/search.md](docs/plans/search.md) - [ ] Search doesn't work (modal opens but no results/functionality) — see [docs/plans/search.md](docs/plans/search.md)

View File

@ -10,7 +10,7 @@
cart_status={assigns[:cart_status]} cart_status={assigns[:cart_status]}
active_page="contact" active_page="contact"
> >
<main id="main-content" class="max-w-4xl mx-auto px-4 sm:px-6 lg:px-8 py-16"> <main id="main-content" class="max-w-4xl mx-auto px-4 sm:px-6 lg:px-8 pb-16">
<.hero_section <.hero_section
variant={:page} variant={:page}
title="Get in touch" title="Get in touch"

View File

@ -568,7 +568,7 @@ defmodule SimpleshopThemeWeb.ShopComponents.Product do
/> />
</section> </section>
<% :page -> %> <% :page -> %>
<div class="text-center"> <div class="text-center" style="padding-top: var(--space-2xl);">
<h1 <h1
class="text-4xl md:text-5xl font-bold mb-6" class="text-4xl md:text-5xl font-bold mb-6"
style="font-family: var(--t-font-heading); color: var(--t-text-primary); font-weight: var(--t-heading-weight); letter-spacing: var(--t-heading-tracking);" style="font-family: var(--t-font-heading); color: var(--t-text-primary); font-weight: var(--t-heading-weight); letter-spacing: var(--t-heading-tracking);"

View File

@ -66,7 +66,7 @@ defmodule SimpleshopThemeWeb.ErrorHTML do
<meta charset="utf-8" /> <meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" /> <meta name="viewport" content="width=device-width, initial-scale=1" />
<title>{@error_code} - {@error_title}</title> <title>{@error_code} - {@error_title}</title>
<link phx-track-static rel="stylesheet" href={~p"/assets/app.css"} /> <link phx-track-static rel="stylesheet" href={~p"/assets/css/app.css"} />
<style id="theme-css"> <style id="theme-css">
<%= Phoenix.HTML.raw(@generated_css) %> <%= Phoenix.HTML.raw(@generated_css) %>
</style> </style>

View File

@ -49,6 +49,11 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
{:ok, "All Products", nil, PreviewData.products()} {:ok, "All Products", nil, PreviewData.products()}
end end
defp load_collection("sale") do
sale_products = Enum.filter(PreviewData.products(), & &1.on_sale)
{:ok, "Sale", :sale, sale_products}
end
defp load_collection(slug) do defp load_collection(slug) do
case PreviewData.category_by_slug(slug) do case PreviewData.category_by_slug(slug) do
nil -> :not_found nil -> :not_found
@ -59,7 +64,11 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
@impl true @impl true
def handle_event("sort_changed", %{"sort" => sort}, socket) do def handle_event("sort_changed", %{"sort" => sort}, socket) do
slug = slug =
if socket.assigns.current_category, do: socket.assigns.current_category.slug, else: "all" case socket.assigns.current_category do
nil -> "all"
:sale -> "sale"
category -> category.slug
end
{:noreply, push_patch(socket, to: ~p"/collections/#{slug}?sort=#{sort}")} {:noreply, push_patch(socket, to: ~p"/collections/#{slug}?sort=#{sort}")}
end end
@ -99,7 +108,13 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
<div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8"> <div class="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8">
<.collection_filter_bar <.collection_filter_bar
categories={@categories} categories={@categories}
current_slug={@current_category && @current_category.slug} current_slug={
case @current_category do
:sale -> "sale"
nil -> nil
cat -> cat.slug
end
}
sort_options={@sort_options} sort_options={@sort_options}
current_sort={@current_sort} current_sort={@current_sort}
/> />
@ -111,7 +126,7 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
theme_settings={@theme_settings} theme_settings={@theme_settings}
mode={@mode} mode={@mode}
variant={:default} variant={:default}
show_category={@current_category == nil} show_category={@current_category in [nil, :sale]}
/> />
<% end %> <% end %>
</.product_grid> </.product_grid>
@ -136,14 +151,14 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
defp collection_filter_bar(assigns) do defp collection_filter_bar(assigns) do
~H""" ~H"""
<div class="flex flex-wrap items-center justify-between gap-4 mb-8"> <div class="flex flex-wrap items-center justify-between gap-3 mb-6">
<nav aria-label="Collection filters"> <nav aria-label="Collection filters" class="overflow-x-auto -mx-4 px-4 sm:mx-0 sm:px-0">
<ul class="flex flex-wrap gap-2"> <ul class="flex gap-1.5 sm:flex-wrap sm:gap-2">
<li> <li class="shrink-0">
<.link <.link
navigate={collection_path("all", @current_sort)} navigate={collection_path("all", @current_sort)}
class={[ class={[
"px-4 py-2 rounded-full text-sm transition-colors", "px-3 py-1.5 sm:px-4 sm:py-2 rounded-full text-xs sm:text-sm whitespace-nowrap transition-colors",
if(@current_slug == nil, do: "font-medium", else: "hover:opacity-80") if(@current_slug == nil, do: "font-medium", else: "hover:opacity-80")
]} ]}
style={ style={
@ -156,12 +171,29 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
All All
</.link> </.link>
</li> </li>
<li class="shrink-0">
<.link
navigate={collection_path("sale", @current_sort)}
class={[
"px-3 py-1.5 sm:px-4 sm:py-2 rounded-full text-xs sm:text-sm whitespace-nowrap transition-colors",
if(@current_slug == "sale", do: "font-medium", else: "hover:opacity-80")
]}
style={
if(@current_slug == "sale",
do: "background-color: var(--t-accent); color: var(--t-text-on-accent);",
else: "background-color: var(--t-surface-raised); color: var(--t-text-primary);"
)
}
>
Sale
</.link>
</li>
<%= for category <- @categories do %> <%= for category <- @categories do %>
<li> <li class="shrink-0">
<.link <.link
navigate={collection_path(category.slug, @current_sort)} navigate={collection_path(category.slug, @current_sort)}
class={[ class={[
"px-4 py-2 rounded-full text-sm transition-colors", "px-3 py-1.5 sm:px-4 sm:py-2 rounded-full text-xs sm:text-sm whitespace-nowrap transition-colors",
if(@current_slug == category.slug, do: "font-medium", else: "hover:opacity-80") if(@current_slug == category.slug, do: "font-medium", else: "hover:opacity-80")
]} ]}
style={ style={
@ -183,7 +215,7 @@ defmodule SimpleshopThemeWeb.ShopLive.Collection do
name="sort" name="sort"
options={@sort_options} options={@sort_options}
selected={@current_sort} selected={@current_sort}
class="px-4 py-2 text-sm" class="px-3 py-1.5 sm:px-4 sm:py-2 text-xs sm:text-sm"
aria-label="Sort products" aria-label="Sort products"
/> />
</form> </form>