diff --git a/src/App.css b/src/App.css index f4bb3b5..5e842db 100644 --- a/src/App.css +++ b/src/App.css @@ -1,38 +1,66 @@ -/* Keep desktop layout as established */ -* { - text-align: center; - -webkit-user-select: none; /* Safari */ - -ms-user-select: none; /* Internet Explorer/Edge */ - user-select: none; /* Standard syntax */ +:root { + --bg: #eef1f6; + --panel: #ffffff; + --text: #1f2430; + --muted: #6b7280; + --border: #e3e7ee; + --accent: #3b6ef5; + --accent-soft: #e8efff; + --radius: 12px; + --shadow: 0 1px 2px rgba(16, 24, 40, 0.04), 0 4px 12px rgba(16, 24, 40, 0.06); +} + +*, +*::before, +*::after { + box-sizing: border-box; } body { - overflow: hidden; + margin: 0; + background: var(--bg); + color: var(--text); + font-family: + system-ui, + -apple-system, + "Segoe UI", + Roboto, + sans-serif; } +/* Sprites are decorative, so stop them being dragged out of the page. + Text stays selectable */ img { - pointer-events: none; -webkit-user-drag: none; user-drag: none; } +button { + font-family: inherit; +} + .app-layout { display: flex; flex-direction: row; align-items: stretch; - justify-self: center; justify-content: center; - height: 100vh; - width: 90%; - box-sizing: border-box; + gap: 12px; + padding: 12px; + width: min(100%, 1600px); + margin: 0 auto; + /* dvh rather than vh so mobile browser chrome does not cut the page off */ + height: 100dvh; } .app-layout > div { - border: 1px solid #ccc; - padding: 10px; - box-sizing: border-box; + background: var(--panel); + border: 1px solid var(--border); + border-radius: var(--radius); + box-shadow: var(--shadow); + padding: 12px; display: flex; min-height: 0; + min-width: 0; } .app-layout > #pokemonList { @@ -44,6 +72,8 @@ img { order: 2; flex: 2; flex-direction: column; + min-height: 0; + overflow-y: auto; } .app-layout > #favoritePokemon { @@ -51,72 +81,141 @@ img { flex: 1; } -.toggle-yellow-btn { - margin-bottom: 8px; - align-self: flex-end; - cursor: pointer; - padding: 4px 8px; -} - -input { - width: 25%; -} - .row { position: relative; display: flex; align-items: center; justify-content: space-between; + gap: 8px; width: 100%; - margin-bottom: 10px; + margin-bottom: 12px; } .nav { display: flex; gap: 6px; + align-items: center; justify-content: center; } -@media (max-width: 1000px) { - body { - -ms-overflow-style: none; /* Internet Explorer 10+ */ - scrollbar-width: none; /* Firefox, Safari 18.2+, Chromium 121+ */ - overflow: scroll; - } +.nav button, +.filter summary, +.filter-reset { + border: 1px solid var(--border); + background: var(--panel); + border-radius: 8px; + padding: 6px 10px; + font-size: 14px; + color: var(--text); + cursor: pointer; +} + +.nav button:hover:not(:disabled), +.filter summary:hover, +.filter-reset:hover { + background: var(--accent-soft); + border-color: var(--accent); +} + +.nav button:disabled { + color: #b6bcc7; + cursor: default; +} + +.nav input { + width: 68px; + text-align: center; + padding: 6px; + border: 1px solid var(--border); + border-radius: 8px; + font-size: 14px; + font-family: inherit; +} + +.app-layout h2 { + margin: 0 0 10px; + font-size: 15px; + font-weight: 600; + letter-spacing: 0.02em; + text-transform: uppercase; + color: var(--muted); + text-align: center; +} +.app-layout [role="status"], +.app-layout [role="alert"] { + text-align: center; + color: var(--muted); + padding: 24px 0; +} + +:focus-visible { + outline: 2px solid var(--accent); + outline-offset: 2px; +} + +/* Stack the three panels once there is no room for columns */ +@media (max-width: 1000px) { .app-layout { flex-direction: column; - width: 100%; height: auto; - align-items: stretch; + min-height: 100dvh; } .app-layout > div { - flex: 0 0 auto !important; - width: 100% !important; - height: auto !important; - min-height: 0; + flex: 0 0 auto; + width: 100%; + height: auto; } - /* Explicit stack order: Card -> List -> Favorite */ - #pokemonCard { + .app-layout > #pokemonList { order: 1; } - #pokemonList { + .app-layout > #pokemonCard { order: 2; - height: auto !important; + overflow-y: visible; } - #favoritePokemon { + .app-layout > #favoritePokemon { order: 3; } +} + +/* A phone in landscape has the width for columns but nowhere near the + height to stack, so keep the row and let each panel scroll on its own */ +@media (max-height: 600px) and (orientation: landscape) { + .app-layout { + flex-direction: row; + height: 100dvh; + min-height: 0; + } + + .app-layout > div { + flex: 1; + width: auto; + height: auto; + min-height: 0; + overflow-y: auto; + } + + .app-layout > #pokemonCard { + flex: 2; + } +} + +@media (max-width: 600px) { + .app-layout { + gap: 8px; + padding: 8px; + } + + .app-layout > div { + padding: 10px; + } - /* Disable inner scroll constraints and let blocks expand full vertical height */ - .pokemon-list, - .favorite-list { - max-height: none !important; - overflow-y: visible !important; - flex: 0 0 auto !important; + .row { + flex-wrap: wrap; + justify-content: center; } } diff --git a/src/components/FavoritePokemon/FavoritePokemon.css b/src/components/FavoritePokemon/FavoritePokemon.css index 9f840b2..bed3a94 100644 --- a/src/components/FavoritePokemon/FavoritePokemon.css +++ b/src/components/FavoritePokemon/FavoritePokemon.css @@ -1,90 +1,99 @@ .favorite-container { + display: flex; + flex-direction: column; width: 100%; + min-width: 0; + min-height: 0; margin: 0; - overflow: hidden; } .favorite-list { list-style-type: none; margin: 0; + padding: 2px; display: flex; flex-direction: column; - gap: 8px; - max-height: 95%; - box-sizing: border-box; - background: #f8f9fa; - padding: 12px; - border-radius: 8px; - box-shadow: 0 2px 8px rgba(0, 0, 0, 0.05); - overflow: scroll !important; - -ms-overflow-style: none; /* Internet Explorer 10+ */ - scrollbar-width: none; /* Firefox, Safari 18.2+, Chromium 121+ */ + gap: 6px; + /* Same flex item rule as the pokemon list, it has to be allowed to shrink + under its content before it will scroll */ + flex: 1; + min-height: 0; + max-height: 100%; + overflow-y: auto; } -.favorite-list .selected { - border-color: #007bff; - background: #e6f2ff; - box-shadow: 0 0 0 2px rgba(0, 123, 255, 0.25); +.favorite-empty { + color: var(--muted); + font-size: 14px; + text-align: center; + margin: 0; + padding: 8px 0; } /* Rendered as a