aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md2
-rw-r--r--public/main.css73
-rw-r--r--src/Food.purs9
-rw-r--r--src/Format.purs13
-rw-r--r--src/Indicator.purs9
-rw-r--r--src/Main.purs2
-rw-r--r--src/Page.purs80
7 files changed, 111 insertions, 77 deletions
diff --git a/README.md b/README.md
index cf929f9..29c343f 100644
--- a/README.md
+++ b/README.md
@@ -30,6 +30,6 @@ Sources
-------
- http://www.aprifel.com/fiche-nutri-composant-glucides,6.html
-- http://www.aly-abbara.com/livre_gyn_obs/termes/diabete/index_glycemique.html#glucides
- http://www.montignac.com/fr/rechercher-l-index-glycemique-d-un-aliment/
- http://www.monmenu.fr/
+- https://www.lanutrition.fr/
diff --git a/public/main.css b/public/main.css
index 0f092cf..fc0850a 100644
--- a/public/main.css
+++ b/public/main.css
@@ -1,44 +1,59 @@
-h1 {
- text-align: center;
- margin-bottom: 1em;
- font-size: 46px;
- color: #33AA00;
-}
+body { margin: 0; }
-ul.aliments {
- display: table;
- margin: 0 auto;
-}
+/* Box sizing */
+html { box-sizing: border-box; }
+*, *:before, *:after { box-sizing: inherit; }
-ul.aliments > li {
- display: table-row;
+@media screen and (min-width: 700px) {
+ .page {
+ width: 700px;
+ margin: 0 auto;
+ }
}
-ul.aliments > li.title {
- font-weight: bold;
+@media screen and (max-width: 700px) {
+ .page { width: 100%; }
}
-ul.aliments > li > div {
- display: table-cell;
- padding: 15px;
+.header {
+ position: fixed;
+ top: 0;
+ width: inherit;
}
-ul.aliments > li > .Good {
- color: green;
+.line {
+ height: 50px;
+ display: flex;
+ align-items: center;
}
-ul.aliments > li > .Medium {
- color: orange;
+.line.title {
+ background-color: #333333;
+ color: white;
+ font-size: 18px;
+ height: 60px;
}
-ul.aliments > li > .Bad {
- color: red;
+.line.search {
+ width: 100%;
+ padding: 0 15px;
+ border: none;
+ box-shadow: 0px 4px 2px -2px rgba(0, 0, 0, 0.2);
+ font-size: 14px;
}
-ul.aliments > li > .number {
- text-align: right;
-}
+.aliments { margin-top: 110px; }
-ul.aliments > li:nth-child(2n+3) {
- background-color: #EEEEEE;
-}
+.line > * { padding: 15px; }
+
+.line > *:nth-child(1) { width: 40%; }
+.line > *:nth-child(2) { width: 20%; }
+.line > *:nth-child(3) { width: 20%; }
+.line > *:nth-child(4) { width: 20%; }
+
+.line > .good { color: green; }
+.line > .medium { color: orange; }
+.line > .bad { color: red; }
+.line > .number { text-align: right; }
+
+.aliment:nth-child(2n+1) { background-color: #F6F6F6; }
diff --git a/src/Food.purs b/src/Food.purs
index 9253959..980eb44 100644
--- a/src/Food.purs
+++ b/src/Food.purs
@@ -35,8 +35,6 @@ all =
, { name: "Banane", glycemicIndex: 60, carbohydrates: 22 }
, { name: "Betterave crue", glycemicIndex: 30, carbohydrates: 9 }
, { name: "Betterave cuite", glycemicIndex: 65, carbohydrates: 7 }
- -- , { name: "Blé (farine blanche)", glycemicIndex: 77, carbohydrates: 76 }
- -- , { name: "Blé (farine complète)", glycemicIndex: 40, carbohydrates: 73 }
, { name: "Boulghour", glycemicIndex: 55, carbohydrates: 20 }
, { name: "Brocoli", glycemicIndex: 15, carbohydrates: 5 }
, { name: "Brugnon", glycemicIndex: 35, carbohydrates: 14 }
@@ -54,6 +52,7 @@ all =
, { name: "Cerneaux de noix", glycemicIndex: 15, carbohydrates: 11 }
, { name: "Champignon", glycemicIndex: 0, carbohydrates: 1 }
, { name: "Chataigne grillée", glycemicIndex: 60, carbohydrates: 42 }
+ , { name: "Croissant", glycemicIndex: 60, carbohydrates: 57 }
, { name: "Choux blanc", glycemicIndex: 15, carbohydrates: 4 }
, { name: "Choux chinois", glycemicIndex: 15, carbohydrates: 1 }
@@ -83,10 +82,8 @@ all =
, { name: "Endive", glycemicIndex: 15, carbohydrates: 4 }
, { name: "Épinard", glycemicIndex: 15, carbohydrates: 3 }
-
, { name: "Faisselle 0%", glycemicIndex: 30, carbohydrates: 4 }
, { name: "Faisselle 40%", glycemicIndex: 30, carbohydrates: 3 }
-
, { name: "Farine de blé", glycemicIndex: 85, carbohydrates: 71 }
, { name: "Farine de blé à levure incorporée", glycemicIndex: 85, carbohydrates: 71 }
, { name: "Farine de blé complète T130", glycemicIndex: 45, carbohydrates: 64 }
@@ -180,9 +177,9 @@ all =
, { name: "Pain au seigle", glycemicIndex: 65, carbohydrates: 50 }
, { name: "pain aux céréales", glycemicIndex: 65, carbohydrates: 55 }
, { name: "Pain aux raisins", glycemicIndex: 70, carbohydrates: 46 }
- , { name: "Pain chocolat", glycemicIndex: 65, carbohydrates: 33 }
+ , { name: "Pain au chocolat", glycemicIndex: 65, carbohydrates: 49 }
, { name: "Pain complet", glycemicIndex: 65, carbohydrates: 44 }
- , { name: "pain hamburger complet", glycemicIndex: 20, carbohydrates: 48 }
+ , { name: "pain hamburger complet", glycemicIndex: 48, carbohydrates: 48 }
, { name: "Pastèque", glycemicIndex: 75, carbohydrates: 7 }
, { name: "Pâte", glycemicIndex: 70, carbohydrates: 20 }
, { name: "Pâte de fruit", glycemicIndex: 70, carbohydrates: 53 }
diff --git a/src/Format.purs b/src/Format.purs
index bed5927..e8ab661 100644
--- a/src/Format.purs
+++ b/src/Format.purs
@@ -1,17 +1,15 @@
module Format
( number
- , compare
+ , string
, unaccent
) where
-import Data.Int (toNumber, fromNumber)
import Data.Array (replicate)
+import Data.Int (toNumber, fromNumber)
import Data.Maybe (fromMaybe)
import Data.String (length, joinWith, fromCharArray, toCharArray, toLower)
import Math (round, trunc, pow)
-
-import Prelude hiding (compare)
-import Prelude as Prelude
+import Prelude
number :: Int -> Number -> String
number decimalLength num = formattedIntegerPart <> formattedDecimalPart
@@ -33,9 +31,8 @@ number decimalLength num = formattedIntegerPart <> formattedDecimalPart
else
""
-compare :: String -> String -> Ordering
-compare xs ys = Prelude.compare (formatString xs) (formatString ys)
- where formatString = unaccent <<< toLower
+string :: String -> String
+string = unaccent <<< toLower
unaccent :: String -> String
unaccent = fromCharArray <<< map unaccentChar <<< toCharArray
diff --git a/src/Indicator.purs b/src/Indicator.purs
index 39a98ca..751c069 100644
--- a/src/Indicator.purs
+++ b/src/Indicator.purs
@@ -1,5 +1,6 @@
module Indicator
( Indicator(..)
+ , className
, fromGlycemicLoad
) where
@@ -7,10 +8,10 @@ import Prelude
data Indicator = Good | Medium | Bad
-instance showIndicator :: Show Indicator where
- show Good = "Good"
- show Medium = "Medium"
- show Bad = "Bad"
+className :: Indicator -> String
+className Good = "good"
+className Medium = "medium"
+className Bad = "bad"
fromGlycemicLoad :: Number -> Indicator
fromGlycemicLoad n
diff --git a/src/Main.purs b/src/Main.purs
index e00f4ce..85346b3 100644
--- a/src/Main.purs
+++ b/src/Main.purs
@@ -12,4 +12,4 @@ import Page as Page
main :: Eff (HA.HalogenEffects ()) Unit
main = HA.runHalogenAff do
body <- HA.awaitBody
- runUI Page.component unit body
+ runUI Page.component "" body
diff --git a/src/Page.purs b/src/Page.purs
index c0b641c..850875a 100644
--- a/src/Page.purs
+++ b/src/Page.purs
@@ -3,10 +3,14 @@ module Page
, Query
) where
-import Data.Array ((:), sortBy)
+import Control.Monad.Aff (Aff)
+import Data.Array (sortBy, filter)
import Data.Maybe (Maybe(..))
+import Data.String (contains, Pattern(..))
+import DOM (DOM)
import Halogen as H
import Halogen.HTML as HH
+import Halogen.HTML.Events as HE
import Halogen.HTML.Properties as HP
import Prelude
@@ -15,14 +19,18 @@ import Food as Food
import Format as Format
import Indicator as Indicator
-data Query a = NoOp a
-type State = Unit
+data Query a =
+ NoOp a
+ | UpdateSearch String a
+
+type State = String
+
type Message = Unit
-component :: forall m . H.Component HH.HTML Query State Message m
+component :: forall eff. H.Component HH.HTML Query State Message (Aff (dom :: DOM | eff))
component =
H.component
- { initialState: const unit
+ { initialState: const ""
, render
, eval
, receiver: const Nothing
@@ -31,39 +39,55 @@ component =
render :: State -> H.ComponentHTML Query
render state =
HH.div
- []
- [ HH.h1 [] [ HH.text "Glycémie" ]
- , HH.ul
+ [ HP.class_ $ HH.ClassName "page" ]
+ [ renderHeader state
+ , HH.div
[ HP.class_ $ HH.ClassName "aliments" ]
- (renderTitle : (map renderAliment <<< sortBy (\a b -> Format.compare a.name b.name) $ Food.all))
+ ( Food.all
+ # filter (\a -> contains (Pattern $ Format.string state) (Format.string a.name))
+ # sortBy (\a b -> compare (Format.string a.name) (Format.string b.name))
+ # map renderAliment
+ )
]
- eval :: Query ~> H.ComponentDSL State Query Message m
+ eval :: Query ~> H.ComponentDSL State Query Message (Aff (dom :: DOM | eff))
eval = case _ of
NoOp next -> pure next
+ UpdateSearch search next -> do
+ H.put search
+ pure next
-renderTitle :: H.ComponentHTML Query
-renderTitle =
- HH.li
- [ HP.class_ $ HH.ClassName "title" ]
+renderHeader :: String -> H.ComponentHTML Query
+renderHeader search =
+ HH.div
+ [ HP.class_ $ HH.ClassName "header" ]
[ HH.div
- []
- [ HH.text "Aliment" ]
- , HH.div
- []
- [ HH.text "Index glycémique" ]
- , HH.div
- []
- [ HH.text "Glucides pour 100 g" ]
- , HH.div
- []
- [ HH.text "Charge glycémique" ]
+ [ HP.class_ $ HH.ClassName "title line" ]
+ [ HH.div
+ []
+ [ HH.text "Aliment" ]
+ , HH.div
+ []
+ [ HH.text "Index glycémique" ]
+ , HH.div
+ []
+ [ HH.text "Glucides pour 100g" ]
+ , HH.div
+ []
+ [ HH.text "Charge glycémique" ]
+ ]
+ , HH.input
+ [ HP.class_ $ HH.ClassName "search line"
+ , HP.placeholder "Rechercher…"
+ , HE.onValueInput (HE.input UpdateSearch)
+ , HP.value search
+ ]
]
renderAliment :: Aliment -> H.ComponentHTML Query
renderAliment aliment =
- HH.li
- []
+ HH.div
+ [ HP.class_ $ HH.ClassName "aliment line" ]
[ HH.div
[]
[ HH.text aliment.name ]
@@ -75,6 +99,6 @@ renderAliment aliment =
[ HH.text (show aliment.carbohydrates) ]
, let glycemicLoad = Food.glycemicLoad aliment
in HH.div
- [ HP.class_ $ HH.ClassName ("number " <> (show $ Indicator.fromGlycemicLoad glycemicLoad)) ]
+ [ HP.class_ $ HH.ClassName ("number " <> (Indicator.className $ Indicator.fromGlycemicLoad glycemicLoad)) ]
[ HH.text (Format.number 2 glycemicLoad) ]
]