-- | <https://www.unicode.org/reports/tr35/tr35-numbers.html#Language_Plural_Rules>
module Language.Fluent.Plural where

import Data.Char (toLower)
import Prelude

data Category
    = Zero
    | One
    | Two
    | Few
    | Many
    | Other
    deriving stock (Category -> Category -> Bool
(Category -> Category -> Bool)
-> (Category -> Category -> Bool) -> Eq Category
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: Category -> Category -> Bool
== :: Category -> Category -> Bool
$c/= :: Category -> Category -> Bool
/= :: Category -> Category -> Bool
Eq, Int -> Category -> ShowS
[Category] -> ShowS
Category -> String
(Int -> Category -> ShowS)
-> (Category -> String) -> ([Category] -> ShowS) -> Show Category
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Category -> ShowS
showsPrec :: Int -> Category -> ShowS
$cshow :: Category -> String
show :: Category -> String
$cshowList :: [Category] -> ShowS
showList :: [Category] -> ShowS
Show, Category
Category -> Category -> Bounded Category
forall a. a -> a -> Bounded a
$cminBound :: Category
minBound :: Category
$cmaxBound :: Category
maxBound :: Category
Bounded, Int -> Category
Category -> Int
Category -> [Category]
Category -> Category
Category -> Category -> [Category]
Category -> Category -> Category -> [Category]
(Category -> Category)
-> (Category -> Category)
-> (Int -> Category)
-> (Category -> Int)
-> (Category -> [Category])
-> (Category -> Category -> [Category])
-> (Category -> Category -> [Category])
-> (Category -> Category -> Category -> [Category])
-> Enum Category
forall a.
(a -> a)
-> (a -> a)
-> (Int -> a)
-> (a -> Int)
-> (a -> [a])
-> (a -> a -> [a])
-> (a -> a -> [a])
-> (a -> a -> a -> [a])
-> Enum a
$csucc :: Category -> Category
succ :: Category -> Category
$cpred :: Category -> Category
pred :: Category -> Category
$ctoEnum :: Int -> Category
toEnum :: Int -> Category
$cfromEnum :: Category -> Int
fromEnum :: Category -> Int
$cenumFrom :: Category -> [Category]
enumFrom :: Category -> [Category]
$cenumFromThen :: Category -> Category -> [Category]
enumFromThen :: Category -> Category -> [Category]
$cenumFromTo :: Category -> Category -> [Category]
enumFromTo :: Category -> Category -> [Category]
$cenumFromThenTo :: Category -> Category -> Category -> [Category]
enumFromThenTo :: Category -> Category -> Category -> [Category]
Enum)

instance Read Category where
    readsPrec :: Int -> ReadS Category
readsPrec Int
_ String
s = [(Category
it, String
"") | Category
it <- [Category
forall a. Bounded a => a
minBound .. Category
forall a. Bounded a => a
maxBound], (Char -> Char) -> ShowS
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Char -> Char
toLower (Category -> String
forall a. Show a => a -> String
show Category
it) String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== (Char -> Char) -> ShowS
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Char -> Char
toLower String
s]

data Form
    = Cardinal
    | Ordinal
    deriving stock (Form -> Form -> Bool
(Form -> Form -> Bool) -> (Form -> Form -> Bool) -> Eq Form
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: Form -> Form -> Bool
== :: Form -> Form -> Bool
$c/= :: Form -> Form -> Bool
/= :: Form -> Form -> Bool
Eq, Int -> Form -> ShowS
[Form] -> ShowS
Form -> String
(Int -> Form -> ShowS)
-> (Form -> String) -> ([Form] -> ShowS) -> Show Form
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Form -> ShowS
showsPrec :: Int -> Form -> ShowS
$cshow :: Form -> String
show :: Form -> String
$cshowList :: [Form] -> ShowS
showList :: [Form] -> ShowS
Show, Form
Form -> Form -> Bounded Form
forall a. a -> a -> Bounded a
$cminBound :: Form
minBound :: Form
$cmaxBound :: Form
maxBound :: Form
Bounded, Int -> Form
Form -> Int
Form -> [Form]
Form -> Form
Form -> Form -> [Form]
Form -> Form -> Form -> [Form]
(Form -> Form)
-> (Form -> Form)
-> (Int -> Form)
-> (Form -> Int)
-> (Form -> [Form])
-> (Form -> Form -> [Form])
-> (Form -> Form -> [Form])
-> (Form -> Form -> Form -> [Form])
-> Enum Form
forall a.
(a -> a)
-> (a -> a)
-> (Int -> a)
-> (a -> Int)
-> (a -> [a])
-> (a -> a -> [a])
-> (a -> a -> [a])
-> (a -> a -> a -> [a])
-> Enum a
$csucc :: Form -> Form
succ :: Form -> Form
$cpred :: Form -> Form
pred :: Form -> Form
$ctoEnum :: Int -> Form
toEnum :: Int -> Form
$cfromEnum :: Form -> Int
fromEnum :: Form -> Int
$cenumFrom :: Form -> [Form]
enumFrom :: Form -> [Form]
$cenumFromThen :: Form -> Form -> [Form]
enumFromThen :: Form -> Form -> [Form]
$cenumFromTo :: Form -> Form -> [Form]
enumFromTo :: Form -> Form -> [Form]
$cenumFromThenTo :: Form -> Form -> Form -> [Form]
enumFromThenTo :: Form -> Form -> Form -> [Form]
Enum)

instance Read Form where
    readsPrec :: Int -> ReadS Form
readsPrec Int
_ String
s = [(Form
it, String
"") | Form
it <- [Form
forall a. Bounded a => a
minBound .. Form
forall a. Bounded a => a
maxBound], (Char -> Char) -> ShowS
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Char -> Char
toLower (Form -> String
forall a. Show a => a -> String
show Form
it) String -> String -> Bool
forall a. Eq a => a -> a -> Bool
== (Char -> Char) -> ShowS
forall a b. (a -> b) -> [a] -> [b]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Char -> Char
toLower String
s]