herms-1.9.0.4: src/UnitConversions.hs
module UnitConversions where
import Data.Char (toLower)
import Types
data Conversion = Metric | Imperial | None deriving (Show, Read, Eq)
--- NOTE: Here, "imperial" means "U.S. Customary".
--- Conversion to British, Australian, Canadian, etc. imperial units is not yet implemented
convertRecipeUnits :: Conversion -> Recipe -> Recipe
convertRecipeUnits unit recp =
case unit of
None -> recp
Metric -> recp{ingredients = map convertIngredientToMetric (ingredients recp)}
Imperial -> recp{ingredients = map convertIngredientToImperial (ingredients recp)}
getSynonym :: String -> Maybe String
getSynonym units
| u `elem` tspSyns = Just "tsp"
| u `elem` tbspSyns = Just "Tbsp"
| u `elem` cupSyns = Just "cups"
| u `elem` ozSyns = Just "oz"
| u `elem` flOzSyns = Just "fl oz"
| u `elem` lbsSyns = Just "lbs"
| u `elem` pintSyns = Just "pint"
| u `elem` quartSyns= Just "quart"
| u `elem` galSyns = Just "gallon"
| otherwise = Nothing
where u = map toLower units
tspSyns = [ "tsp",
"tsp.",
"teaspoon",
"teaspoons" ]
tbspSyns = [ "tbsp",
"tbsp.",
"tablespoon",
"tablespoons" ]
cupSyns = [ "cup",
"cups",
"cp",
"cps",
"cp." ,
"cps." ]
ozSyns = [ "oz",
"oz.",
"ounce",
"ounces" ]
flOzSyns = [ "fl oz",
"fl. oz.",
"fl oz.",
"fl. oz",
"fluid ounce",
"fluid ounces",
"fluid oz",
"fluid oz.",
"fl ounce",
"fl ounces",
"fl. ounce",
"fl. ounces" ]
lbsSyns = [ "lb.",
"lbs.",
"lb",
"lbs",
"pound",
"pounds" ]
pintSyns = [ "pt",
"pt.",
"pts",
"pts.",
"pint",
"pints" ]
quartSyns = ["qt",
"qt.",
"qts",
"qts.",
"quart",
"quarts" ]
galSyns = [ "gal",
"gal.",
"gals",
"gals.",
"gallon",
"gallons" ]
convertIngredientToMetric :: Ingredient -> Ingredient
convertIngredientToMetric ingr =
case getSynonym units of
Just "tsp" -> ingr{quantity = qty * 5, unit = "mL"}
Just "Tbsp" -> ingr{quantity = qty * 15, unit = "mL"}
Just "fl oz" -> ingr{quantity = qty * 30, unit = "mL"}
Just "cups" -> ingr{quantity = qty * 237, unit = "mL"}
Just "oz" -> ingr{quantity = qty * 28, unit = "g"}
Just "lbs" -> ingr{quantity = qty * 454, unit = "g"}
Just "pint" -> ingr{quantity = qty * 473, unit = "mL"}
Just "quart" -> ingr{quantity = qty * 946, unit = "mL"}
Just "gallon"-> ingr{quantity = qty * 3.785, unit = "L"}
_ -> ingr
where
units = unit ingr
qty = quantity ingr
convertIngredientToImperial :: Ingredient -> Ingredient
convertIngredientToImperial ingr =
case un of
"mL" | qty < 15 -> ingr{quantity = qty / 5, unit = "tsp"}
| qty < 250 -> ingr{quantity = qty / 15, unit = "Tbsp"}
| otherwise -> ingr{quantity = qty / 250, unit = "cup(s)"}
"g" -> ingr{quantity = qty / 28, unit = "oz"}
_ -> ingr
where
un = unit ingr
qty = quantity ingr