corpus

Log | Files | Refs | README | LICENSE

commit a57b108a149ea4784c8ed20c9474c65fa55972e6
parent 096e7ad5ffa73313e5695abc320a2eda81310ac4
Author: mtmn <miro@haravara.org>
Date:   Sun, 12 Apr 2026 20:18:16 +0200

feat(stats): add show all expander

Diffstat:
Msrc/Client.purs | 34+++++++++++++++++++++++++---------
Msrc/Main.purs | 15+++++++++++++++
2 files changed, 40 insertions(+), 9 deletions(-)

diff --git a/src/Client.purs b/src/Client.purs @@ -5,7 +5,7 @@ import Prelude import Affjax.Web as AX import Affjax.ResponseFormat as ResponseFormat import Data.Argonaut (decodeJson) -import Data.Array (mapWithIndex, length) +import Data.Array (mapWithIndex, length, take) import Data.Either (Either(..)) import Data.Int (floor, fromString, toNumber) import Data.Foldable (maximum) @@ -51,6 +51,7 @@ type State = , currentTime :: Maybe Milliseconds , failedCovers :: Set String , hoveredCover :: Maybe Int + , expandedSections :: Set String , offset :: Int , limit :: Int , activeTab :: Tab @@ -70,6 +71,7 @@ data Action | ClearFilter | HoverCover Int | UnhoverCover + | ToggleSection String component :: forall query input output m. MonadAff m => H.Component query input output m component = @@ -91,6 +93,7 @@ component = , currentTime: Nothing , failedCovers: Set.empty , hoveredCover: Nothing + , expandedSections: Set.empty , offset: 0 , limit: 25 , activeTab: ListensTab @@ -150,7 +153,7 @@ component = ] ] StatsTab -> - renderStatsView state.stats + renderStatsView state.expandedSections state.stats , HH.p [ HP.id "last-updated" , HP.class_ (H.ClassName "small") @@ -158,25 +161,36 @@ component = [ HH.text $ fromMaybe "" state.lastCheck ] ] - renderStatsView Nothing = + renderStatsView _ Nothing = HH.div [ HP.class_ (H.ClassName "loading") ] [ HH.text "Loading stats..." ] - renderStatsView (Just (Stats { genres, labels, years })) = + renderStatsView expandedSections (Just (Stats { genres, labels, years })) = HH.div_ - [ renderStatSection "genre" "genres" genres - , renderStatSection "label" "labels" labels - , renderStatSection "year" "years" years + [ renderStatSection expandedSections "genre" "genres" genres + , renderStatSection expandedSections "label" "labels" labels + , renderStatSection expandedSections "year" "years" years ] - renderStatSection field title entries = + renderStatSection expandedSections field title entries = let maxCount = fromMaybe 1 (maximum (map (\(StatsEntry e) -> e.count) entries)) + expanded = Set.member field expandedSections + visible = if expanded then entries else take 10 entries + hasMore = length entries > 10 in HH.div [ HP.class_ (H.ClassName "stats-section") ] [ HH.h2_ [ HH.text title ] , if entries == [] then HH.div [ HP.class_ (H.ClassName "stats-empty") ] [ HH.text "no data yet — enrichment in progress" ] else - HH.ul_ (map (renderStatEntry maxCount field) entries) + HH.ul_ (map (renderStatEntry maxCount field) visible) + , if hasMore then + HH.button + [ HP.class_ (H.ClassName "show-all-btn") + , HE.onClick \_ -> ToggleSection field + ] + [ HH.text $ if expanded then "show less" else "show all (" <> show (length entries) <> ")" ] + else + HH.text "" ] renderStatEntry maxCount field (StatsEntry { name, count }) = @@ -324,6 +338,8 @@ component = H.modify_ _ { hoveredCover = Just url } UnhoverCover -> do H.modify_ _ { hoveredCover = Nothing } + ToggleSection field -> do + H.modify_ \s -> s { expandedSections = if Set.member field s.expandedSections then Set.delete field s.expandedSections else Set.insert field s.expandedSections } updateUrl = do state <- H.get diff --git a/src/Main.purs b/src/Main.purs @@ -535,6 +535,21 @@ indexHtml = color: #ffffff; border-color: #ffffff; } + + .show-all-btn { + background: none; + border: none; + color: #9fbfe7; + cursor: pointer; + font-family: inherit; + font-size: 12px; + padding: 4px 0; + text-decoration: underline; + } + + .show-all-btn:hover { + color: #ffffff; + } </style> </head> <body>