{-# LANGUAGE CPP #-}
{-# LANGUAGE DeriveDataTypeable #-}
{-# LANGUAGE DeriveFoldable #-}
{-# LANGUAGE DeriveFunctor #-}
{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE Safe #-}

-- |
-- Module      : Text.Numerals.Class
-- Description : A module that contains the typeclasses on which the rest of the module works.
-- Maintainer  : hapytexeu+gh@gmail.com
-- Stability   : experimental
-- Portability : POSIX
--
-- A module that defines the typeclasses that are used in the rest of the module. The 'NumToWord' class
-- is the typeclass that is used by all algorithmic conversion tools.
module Text.Numerals.Class
  ( -- * Typeclasses
    NumToWord (toCardinal, toOrdinal, toShortOrdinal, toWords, toTimeText, toTimeText'),
    ValueSplit (valueSplit),

    -- * Types of numbers
    NumberType (Cardinal, Ordinal, ShortOrdinal),

    -- * Segmenting a number
    NumberSegment (NumberSegment, segmentDivision, segmentValue, segmentText, segmentRemainder),
    MNumberSegment,

    -- * Segments of time
    ClockSegment (OClock, Past, QuarterPast, ToHalf, Half, PastHalf, QuarterTo, To),
    DayPart (Night, Morning, Afternoon, Evening),
    DaySegment (DaySegment, dayPart, dayHour),
    toDayPart,
    toDaySegment,
    toClockSegment,
    hourCorrection,

    -- * Convert the current time to words
    currentTimeText,
    currentTimeText',

    -- * Utility type synonyms
    NumberToWords,
    FreeNumberToWords,
    MergerFunction,
    FreeMergerFunction,
    ValueSplitter,
    FreeValueSplitter,
    NumberSegmenting,
    ClockText,
  )
where

import Control.DeepSeq (NFData, NFData1)
import Data.Data (Data)
import Data.Default.Class (Default (def))
#if __GLASGOW_HASKELL__ < 803
import Data.Semigroup((<>))
#endif
import Data.Text (Text)
import Data.Time.Clock (getCurrentTime, utctDayTime)
import Data.Time.LocalTime (TimeOfDay (TimeOfDay), TimeZone, timeToTimeOfDay, utcToLocalTimeOfDay)
import GHC.Generics (Generic, Generic1)
import Test.QuickCheck (choose)
import Test.QuickCheck.Arbitrary (Arbitrary (arbitrary, shrink), Arbitrary1 (liftArbitrary), arbitrary1, arbitraryBoundedEnum)
import Text.Numerals.Internal (_genText, _shrinkText)

-- | A type alias for a function that maps a number to a 'Text' object.
type NumberToWords i = i -> Text

-- | A type alias for a 'NumberToWords' function, with a free 'Integral'
-- variable.
type FreeNumberToWords = forall i. Integral i => NumberToWords i

-- | A type alias of a function that is used to merge the names of two numbers according
-- to gramatical rules. The type parameter is the type of the numbers to merge.
type MergerFunction i = i -> i -> Text -> Text -> Text

-- | A type alias of a 'MergerFunction' function with a free 'Integral' variable.
type FreeMergerFunction = forall i. Integral i => MergerFunction i

-- | A type alias of a function that maps a number to a 2-tuple that contains a
-- number and the word for that number. This number is normally the largest
-- number smaller than the given number. In case no name exists for a number
-- smaller than the given one 'Nothing' is returned.
type ValueSplitter i = i -> Maybe (i, Text)

-- | A type alias of a 'ValueSplitter' function, with a free 'Integral'
-- variable.
type FreeValueSplitter = forall i. Integral i => ValueSplitter i

-- | A type alias of a function that converts a number to a 'NumberSegment' for that number.
type NumberSegmenting i = i -> NumberSegment i

-- | A data type used to convert a number into segments. Each segment has an
-- optional division and remainder part, together with a value and the name of
-- that value in a language.
data NumberSegment i = NumberSegment
  { -- | The optional division part. 'Nothing' if the division is equal to one.
    forall i. NumberSegment i -> MNumberSegment i
segmentDivision :: MNumberSegment i,
    -- | The value of the given segment.
    forall i. NumberSegment i -> i
segmentValue :: i,
    -- | The name of the value of the given segment, in a specific language.
    forall i. NumberSegment i -> Text
segmentText :: Text,
    -- | The optional remainder part. 'Nothing' if the remainder is equal to zero.
    forall i. NumberSegment i -> MNumberSegment i
segmentRemainder :: MNumberSegment i
  }
  deriving (Typeable (NumberSegment i)
Typeable (NumberSegment i) =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> NumberSegment i -> c (NumberSegment i))
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (NumberSegment i))
-> (NumberSegment i -> Constr)
-> (NumberSegment i -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c (NumberSegment i)))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (NumberSegment i)))
-> ((forall b. Data b => b -> b)
    -> NumberSegment i -> NumberSegment i)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r)
-> (forall u.
    (forall d. Data d => d -> u) -> NumberSegment i -> [u])
-> (forall u.
    Int -> (forall d. Data d => d -> u) -> NumberSegment i -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> NumberSegment i -> m (NumberSegment i))
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> NumberSegment i -> m (NumberSegment i))
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> NumberSegment i -> m (NumberSegment i))
-> Data (NumberSegment i)
NumberSegment i -> Constr
NumberSegment i -> DataType
(forall b. Data b => b -> b) -> NumberSegment i -> NumberSegment i
forall i. Data i => Typeable (NumberSegment i)
forall i. Data i => NumberSegment i -> Constr
forall i. Data i => NumberSegment i -> DataType
forall i.
Data i =>
(forall b. Data b => b -> b) -> NumberSegment i -> NumberSegment i
forall i u.
Data i =>
Int -> (forall d. Data d => d -> u) -> NumberSegment i -> u
forall i u.
Data i =>
(forall d. Data d => d -> u) -> NumberSegment i -> [u]
forall i r r'.
Data i =>
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
forall i r r'.
Data i =>
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
forall i (m :: * -> *).
(Data i, Monad m) =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
forall i (m :: * -> *).
(Data i, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
forall i (c :: * -> *).
Data i =>
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (NumberSegment i)
forall i (c :: * -> *).
Data i =>
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberSegment i -> c (NumberSegment i)
forall i (t :: * -> *) (c :: * -> *).
(Data i, Typeable t) =>
(forall d. Data d => c (t d)) -> Maybe (c (NumberSegment i))
forall i (t :: * -> * -> *) (c :: * -> *).
(Data i, Typeable t) =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (NumberSegment i))
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u.
Int -> (forall d. Data d => d -> u) -> NumberSegment i -> u
forall u. (forall d. Data d => d -> u) -> NumberSegment i -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (NumberSegment i)
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberSegment i -> c (NumberSegment i)
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c (NumberSegment i))
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (NumberSegment i))
$cgfoldl :: forall i (c :: * -> *).
Data i =>
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberSegment i -> c (NumberSegment i)
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberSegment i -> c (NumberSegment i)
$cgunfold :: forall i (c :: * -> *).
Data i =>
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (NumberSegment i)
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (NumberSegment i)
$ctoConstr :: forall i. Data i => NumberSegment i -> Constr
toConstr :: NumberSegment i -> Constr
$cdataTypeOf :: forall i. Data i => NumberSegment i -> DataType
dataTypeOf :: NumberSegment i -> DataType
$cdataCast1 :: forall i (t :: * -> *) (c :: * -> *).
(Data i, Typeable t) =>
(forall d. Data d => c (t d)) -> Maybe (c (NumberSegment i))
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c (NumberSegment i))
$cdataCast2 :: forall i (t :: * -> * -> *) (c :: * -> *).
(Data i, Typeable t) =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (NumberSegment i))
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (NumberSegment i))
$cgmapT :: forall i.
Data i =>
(forall b. Data b => b -> b) -> NumberSegment i -> NumberSegment i
gmapT :: (forall b. Data b => b -> b) -> NumberSegment i -> NumberSegment i
$cgmapQl :: forall i r r'.
Data i =>
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
$cgmapQr :: forall i r r'.
Data i =>
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberSegment i -> r
$cgmapQ :: forall i u.
Data i =>
(forall d. Data d => d -> u) -> NumberSegment i -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> NumberSegment i -> [u]
$cgmapQi :: forall i u.
Data i =>
Int -> (forall d. Data d => d -> u) -> NumberSegment i -> u
gmapQi :: forall u.
Int -> (forall d. Data d => d -> u) -> NumberSegment i -> u
$cgmapM :: forall i (m :: * -> *).
(Data i, Monad m) =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
$cgmapMp :: forall i (m :: * -> *).
(Data i, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
$cgmapMo :: forall i (m :: * -> *).
(Data i, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> NumberSegment i -> m (NumberSegment i)
Data, NumberSegment i -> NumberSegment i -> Bool
(NumberSegment i -> NumberSegment i -> Bool)
-> (NumberSegment i -> NumberSegment i -> Bool)
-> Eq (NumberSegment i)
forall i. Eq i => NumberSegment i -> NumberSegment i -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall i. Eq i => NumberSegment i -> NumberSegment i -> Bool
== :: NumberSegment i -> NumberSegment i -> Bool
$c/= :: forall i. Eq i => NumberSegment i -> NumberSegment i -> Bool
/= :: NumberSegment i -> NumberSegment i -> Bool
Eq, (forall m. Monoid m => NumberSegment m -> m)
-> (forall m a. Monoid m => (a -> m) -> NumberSegment a -> m)
-> (forall m a. Monoid m => (a -> m) -> NumberSegment a -> m)
-> (forall a b. (a -> b -> b) -> b -> NumberSegment a -> b)
-> (forall a b. (a -> b -> b) -> b -> NumberSegment a -> b)
-> (forall b a. (b -> a -> b) -> b -> NumberSegment a -> b)
-> (forall b a. (b -> a -> b) -> b -> NumberSegment a -> b)
-> (forall a. (a -> a -> a) -> NumberSegment a -> a)
-> (forall a. (a -> a -> a) -> NumberSegment a -> a)
-> (forall a. NumberSegment a -> [a])
-> (forall a. NumberSegment a -> Bool)
-> (forall a. NumberSegment a -> Int)
-> (forall a. Eq a => a -> NumberSegment a -> Bool)
-> (forall a. Ord a => NumberSegment a -> a)
-> (forall a. Ord a => NumberSegment a -> a)
-> (forall a. Num a => NumberSegment a -> a)
-> (forall a. Num a => NumberSegment a -> a)
-> Foldable NumberSegment
forall a. Eq a => a -> NumberSegment a -> Bool
forall a. Num a => NumberSegment a -> a
forall a. Ord a => NumberSegment a -> a
forall m. Monoid m => NumberSegment m -> m
forall a. NumberSegment a -> Bool
forall a. NumberSegment a -> Int
forall a. NumberSegment a -> [a]
forall a. (a -> a -> a) -> NumberSegment a -> a
forall m a. Monoid m => (a -> m) -> NumberSegment a -> m
forall b a. (b -> a -> b) -> b -> NumberSegment a -> b
forall a b. (a -> b -> b) -> b -> NumberSegment a -> b
forall (t :: * -> *).
(forall m. Monoid m => t m -> m)
-> (forall m a. Monoid m => (a -> m) -> t a -> m)
-> (forall m a. Monoid m => (a -> m) -> t a -> m)
-> (forall a b. (a -> b -> b) -> b -> t a -> b)
-> (forall a b. (a -> b -> b) -> b -> t a -> b)
-> (forall b a. (b -> a -> b) -> b -> t a -> b)
-> (forall b a. (b -> a -> b) -> b -> t a -> b)
-> (forall a. (a -> a -> a) -> t a -> a)
-> (forall a. (a -> a -> a) -> t a -> a)
-> (forall a. t a -> [a])
-> (forall a. t a -> Bool)
-> (forall a. t a -> Int)
-> (forall a. Eq a => a -> t a -> Bool)
-> (forall a. Ord a => t a -> a)
-> (forall a. Ord a => t a -> a)
-> (forall a. Num a => t a -> a)
-> (forall a. Num a => t a -> a)
-> Foldable t
$cfold :: forall m. Monoid m => NumberSegment m -> m
fold :: forall m. Monoid m => NumberSegment m -> m
$cfoldMap :: forall m a. Monoid m => (a -> m) -> NumberSegment a -> m
foldMap :: forall m a. Monoid m => (a -> m) -> NumberSegment a -> m
$cfoldMap' :: forall m a. Monoid m => (a -> m) -> NumberSegment a -> m
foldMap' :: forall m a. Monoid m => (a -> m) -> NumberSegment a -> m
$cfoldr :: forall a b. (a -> b -> b) -> b -> NumberSegment a -> b
foldr :: forall a b. (a -> b -> b) -> b -> NumberSegment a -> b
$cfoldr' :: forall a b. (a -> b -> b) -> b -> NumberSegment a -> b
foldr' :: forall a b. (a -> b -> b) -> b -> NumberSegment a -> b
$cfoldl :: forall b a. (b -> a -> b) -> b -> NumberSegment a -> b
foldl :: forall b a. (b -> a -> b) -> b -> NumberSegment a -> b
$cfoldl' :: forall b a. (b -> a -> b) -> b -> NumberSegment a -> b
foldl' :: forall b a. (b -> a -> b) -> b -> NumberSegment a -> b
$cfoldr1 :: forall a. (a -> a -> a) -> NumberSegment a -> a
foldr1 :: forall a. (a -> a -> a) -> NumberSegment a -> a
$cfoldl1 :: forall a. (a -> a -> a) -> NumberSegment a -> a
foldl1 :: forall a. (a -> a -> a) -> NumberSegment a -> a
$ctoList :: forall a. NumberSegment a -> [a]
toList :: forall a. NumberSegment a -> [a]
$cnull :: forall a. NumberSegment a -> Bool
null :: forall a. NumberSegment a -> Bool
$clength :: forall a. NumberSegment a -> Int
length :: forall a. NumberSegment a -> Int
$celem :: forall a. Eq a => a -> NumberSegment a -> Bool
elem :: forall a. Eq a => a -> NumberSegment a -> Bool
$cmaximum :: forall a. Ord a => NumberSegment a -> a
maximum :: forall a. Ord a => NumberSegment a -> a
$cminimum :: forall a. Ord a => NumberSegment a -> a
minimum :: forall a. Ord a => NumberSegment a -> a
$csum :: forall a. Num a => NumberSegment a -> a
sum :: forall a. Num a => NumberSegment a -> a
$cproduct :: forall a. Num a => NumberSegment a -> a
product :: forall a. Num a => NumberSegment a -> a
Foldable, (forall a b. (a -> b) -> NumberSegment a -> NumberSegment b)
-> (forall a b. a -> NumberSegment b -> NumberSegment a)
-> Functor NumberSegment
forall a b. a -> NumberSegment b -> NumberSegment a
forall a b. (a -> b) -> NumberSegment a -> NumberSegment b
forall (f :: * -> *).
(forall a b. (a -> b) -> f a -> f b)
-> (forall a b. a -> f b -> f a) -> Functor f
$cfmap :: forall a b. (a -> b) -> NumberSegment a -> NumberSegment b
fmap :: forall a b. (a -> b) -> NumberSegment a -> NumberSegment b
$c<$ :: forall a b. a -> NumberSegment b -> NumberSegment a
<$ :: forall a b. a -> NumberSegment b -> NumberSegment a
Functor, (forall x. NumberSegment i -> Rep (NumberSegment i) x)
-> (forall x. Rep (NumberSegment i) x -> NumberSegment i)
-> Generic (NumberSegment i)
forall x. Rep (NumberSegment i) x -> NumberSegment i
forall x. NumberSegment i -> Rep (NumberSegment i) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall i x. Rep (NumberSegment i) x -> NumberSegment i
forall i x. NumberSegment i -> Rep (NumberSegment i) x
$cfrom :: forall i x. NumberSegment i -> Rep (NumberSegment i) x
from :: forall x. NumberSegment i -> Rep (NumberSegment i) x
$cto :: forall i x. Rep (NumberSegment i) x -> NumberSegment i
to :: forall x. Rep (NumberSegment i) x -> NumberSegment i
Generic, (forall a. NumberSegment a -> Rep1 NumberSegment a)
-> (forall a. Rep1 NumberSegment a -> NumberSegment a)
-> Generic1 NumberSegment
forall a. Rep1 NumberSegment a -> NumberSegment a
forall a. NumberSegment a -> Rep1 NumberSegment a
forall k (f :: k -> *).
(forall (a :: k). f a -> Rep1 f a)
-> (forall (a :: k). Rep1 f a -> f a) -> Generic1 f
$cfrom1 :: forall a. NumberSegment a -> Rep1 NumberSegment a
from1 :: forall a. NumberSegment a -> Rep1 NumberSegment a
$cto1 :: forall a. Rep1 NumberSegment a -> NumberSegment a
to1 :: forall a. Rep1 NumberSegment a -> NumberSegment a
Generic1, Eq (NumberSegment i)
Eq (NumberSegment i) =>
(NumberSegment i -> NumberSegment i -> Ordering)
-> (NumberSegment i -> NumberSegment i -> Bool)
-> (NumberSegment i -> NumberSegment i -> Bool)
-> (NumberSegment i -> NumberSegment i -> Bool)
-> (NumberSegment i -> NumberSegment i -> Bool)
-> (NumberSegment i -> NumberSegment i -> NumberSegment i)
-> (NumberSegment i -> NumberSegment i -> NumberSegment i)
-> Ord (NumberSegment i)
NumberSegment i -> NumberSegment i -> Bool
NumberSegment i -> NumberSegment i -> Ordering
NumberSegment i -> NumberSegment i -> NumberSegment i
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall i. Ord i => Eq (NumberSegment i)
forall i. Ord i => NumberSegment i -> NumberSegment i -> Bool
forall i. Ord i => NumberSegment i -> NumberSegment i -> Ordering
forall i.
Ord i =>
NumberSegment i -> NumberSegment i -> NumberSegment i
$ccompare :: forall i. Ord i => NumberSegment i -> NumberSegment i -> Ordering
compare :: NumberSegment i -> NumberSegment i -> Ordering
$c< :: forall i. Ord i => NumberSegment i -> NumberSegment i -> Bool
< :: NumberSegment i -> NumberSegment i -> Bool
$c<= :: forall i. Ord i => NumberSegment i -> NumberSegment i -> Bool
<= :: NumberSegment i -> NumberSegment i -> Bool
$c> :: forall i. Ord i => NumberSegment i -> NumberSegment i -> Bool
> :: NumberSegment i -> NumberSegment i -> Bool
$c>= :: forall i. Ord i => NumberSegment i -> NumberSegment i -> Bool
>= :: NumberSegment i -> NumberSegment i -> Bool
$cmax :: forall i.
Ord i =>
NumberSegment i -> NumberSegment i -> NumberSegment i
max :: NumberSegment i -> NumberSegment i -> NumberSegment i
$cmin :: forall i.
Ord i =>
NumberSegment i -> NumberSegment i -> NumberSegment i
min :: NumberSegment i -> NumberSegment i -> NumberSegment i
Ord, ReadPrec [NumberSegment i]
ReadPrec (NumberSegment i)
Int -> ReadS (NumberSegment i)
ReadS [NumberSegment i]
(Int -> ReadS (NumberSegment i))
-> ReadS [NumberSegment i]
-> ReadPrec (NumberSegment i)
-> ReadPrec [NumberSegment i]
-> Read (NumberSegment i)
forall i. Read i => ReadPrec [NumberSegment i]
forall i. Read i => ReadPrec (NumberSegment i)
forall i. Read i => Int -> ReadS (NumberSegment i)
forall i. Read i => ReadS [NumberSegment i]
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: forall i. Read i => Int -> ReadS (NumberSegment i)
readsPrec :: Int -> ReadS (NumberSegment i)
$creadList :: forall i. Read i => ReadS [NumberSegment i]
readList :: ReadS [NumberSegment i]
$creadPrec :: forall i. Read i => ReadPrec (NumberSegment i)
readPrec :: ReadPrec (NumberSegment i)
$creadListPrec :: forall i. Read i => ReadPrec [NumberSegment i]
readListPrec :: ReadPrec [NumberSegment i]
Read, Int -> NumberSegment i -> ShowS
[NumberSegment i] -> ShowS
NumberSegment i -> String
(Int -> NumberSegment i -> ShowS)
-> (NumberSegment i -> String)
-> ([NumberSegment i] -> ShowS)
-> Show (NumberSegment i)
forall i. Show i => Int -> NumberSegment i -> ShowS
forall i. Show i => [NumberSegment i] -> ShowS
forall i. Show i => NumberSegment i -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall i. Show i => Int -> NumberSegment i -> ShowS
showsPrec :: Int -> NumberSegment i -> ShowS
$cshow :: forall i. Show i => NumberSegment i -> String
show :: NumberSegment i -> String
$cshowList :: forall i. Show i => [NumberSegment i] -> ShowS
showList :: [NumberSegment i] -> ShowS
Show)

instance NFData a => NFData (NumberSegment a)

instance NFData1 NumberSegment

instance Arbitrary1 NumberSegment where
  liftArbitrary :: forall a. Gen a -> Gen (NumberSegment a)
liftArbitrary Gen a
gen = Gen (NumberSegment a)
go
    where
      go :: Gen (NumberSegment a)
go = MNumberSegment a
-> a -> Text -> MNumberSegment a -> NumberSegment a
forall i.
MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
NumberSegment (MNumberSegment a
 -> a -> Text -> MNumberSegment a -> NumberSegment a)
-> Gen (MNumberSegment a)
-> Gen (a -> Text -> MNumberSegment a -> NumberSegment a)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Gen (NumberSegment a) -> Gen (MNumberSegment a)
forall a. Gen a -> Gen (Maybe a)
forall (f :: * -> *) a. Arbitrary1 f => Gen a -> Gen (f a)
liftArbitrary Gen (NumberSegment a)
go Gen (a -> Text -> MNumberSegment a -> NumberSegment a)
-> Gen a -> Gen (Text -> MNumberSegment a -> NumberSegment a)
forall a b. Gen (a -> b) -> Gen a -> Gen b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen a
gen Gen (Text -> MNumberSegment a -> NumberSegment a)
-> Gen Text -> Gen (MNumberSegment a -> NumberSegment a)
forall a b. Gen (a -> b) -> Gen a -> Gen b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen Text
_genText Gen (MNumberSegment a -> NumberSegment a)
-> Gen (MNumberSegment a) -> Gen (NumberSegment a)
forall a b. Gen (a -> b) -> Gen a -> Gen b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Gen (NumberSegment a) -> Gen (MNumberSegment a)
forall a. Gen a -> Gen (Maybe a)
forall (f :: * -> *) a. Arbitrary1 f => Gen a -> Gen (f a)
liftArbitrary Gen (NumberSegment a)
go

instance Arbitrary i => Arbitrary (NumberSegment i) where
  arbitrary :: Gen (NumberSegment i)
arbitrary = Gen (NumberSegment i)
forall (f :: * -> *) a. (Arbitrary1 f, Arbitrary a) => Gen (f a)
arbitrary1
  shrink :: NumberSegment i -> [NumberSegment i]
shrink (NumberSegment MNumberSegment i
dv i
val Text
txt MNumberSegment i
rm) =
    ((\MNumberSegment i
x -> MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
forall i.
MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
NumberSegment MNumberSegment i
x i
val Text
txt MNumberSegment i
rm) (MNumberSegment i -> NumberSegment i)
-> [MNumberSegment i] -> [NumberSegment i]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> MNumberSegment i -> [MNumberSegment i]
forall a. Arbitrary a => a -> [a]
shrink MNumberSegment i
dv)
      [NumberSegment i] -> [NumberSegment i] -> [NumberSegment i]
forall a. Semigroup a => a -> a -> a
<> ((\i
x -> MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
forall i.
MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
NumberSegment MNumberSegment i
dv i
x Text
txt MNumberSegment i
rm) (i -> NumberSegment i) -> [i] -> [NumberSegment i]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> i -> [i]
forall a. Arbitrary a => a -> [a]
shrink i
val)
      [NumberSegment i] -> [NumberSegment i] -> [NumberSegment i]
forall a. Semigroup a => a -> a -> a
<> ((\Text
x -> MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
forall i.
MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
NumberSegment MNumberSegment i
dv i
val Text
x MNumberSegment i
rm) (Text -> NumberSegment i) -> [Text] -> [NumberSegment i]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Text -> [Text]
_shrinkText Text
txt)
      [NumberSegment i] -> [NumberSegment i] -> [NumberSegment i]
forall a. Semigroup a => a -> a -> a
<> (MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
forall i.
MNumberSegment i
-> i -> Text -> MNumberSegment i -> NumberSegment i
NumberSegment MNumberSegment i
dv i
val Text
txt (MNumberSegment i -> NumberSegment i)
-> [MNumberSegment i] -> [NumberSegment i]
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> MNumberSegment i -> [MNumberSegment i]
forall a. Arbitrary a => a -> [a]
shrink MNumberSegment i
rm)

-- | A 'Maybe' variant of the 'NumberSegment' data type. This is used since the
-- division part can be one, or the remainder part can be zero.
type MNumberSegment i = Maybe (NumberSegment i)

-- | A data type that specifies the different types of numbers. These can be
-- used to specify the "target format". The 'Default' number type is 'Cardinal'.
data NumberType
  = -- | /Cardinal/ numbers like one, two, three, etc.
    Cardinal
  | -- | /Ordinal/ numbers like first, second, third, etc.
    Ordinal
  | -- | /Short ordinal/ numbers like 1st, 2nd, 3rd, etc.
    ShortOrdinal
  deriving (NumberType
NumberType -> NumberType -> Bounded NumberType
forall a. a -> a -> Bounded a
$cminBound :: NumberType
minBound :: NumberType
$cmaxBound :: NumberType
maxBound :: NumberType
Bounded, Typeable NumberType
Typeable NumberType =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> NumberType -> c NumberType)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c NumberType)
-> (NumberType -> Constr)
-> (NumberType -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c NumberType))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c NumberType))
-> ((forall b. Data b => b -> b) -> NumberType -> NumberType)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> NumberType -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> NumberType -> r)
-> (forall u. (forall d. Data d => d -> u) -> NumberType -> [u])
-> (forall u.
    Int -> (forall d. Data d => d -> u) -> NumberType -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> NumberType -> m NumberType)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> NumberType -> m NumberType)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> NumberType -> m NumberType)
-> Data NumberType
NumberType -> Constr
NumberType -> DataType
(forall b. Data b => b -> b) -> NumberType -> NumberType
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> NumberType -> u
forall u. (forall d. Data d => d -> u) -> NumberType -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c NumberType
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberType -> c NumberType
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c NumberType)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c NumberType)
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberType -> c NumberType
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> NumberType -> c NumberType
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c NumberType
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c NumberType
$ctoConstr :: NumberType -> Constr
toConstr :: NumberType -> Constr
$cdataTypeOf :: NumberType -> DataType
dataTypeOf :: NumberType -> DataType
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c NumberType)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c NumberType)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c NumberType)
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c NumberType)
$cgmapT :: (forall b. Data b => b -> b) -> NumberType -> NumberType
gmapT :: (forall b. Data b => b -> b) -> NumberType -> NumberType
$cgmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
$cgmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> NumberType -> r
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> NumberType -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> NumberType -> [u]
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> NumberType -> u
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> NumberType -> u
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> NumberType -> m NumberType
Data, Int -> NumberType
NumberType -> Int
NumberType -> [NumberType]
NumberType -> NumberType
NumberType -> NumberType -> [NumberType]
NumberType -> NumberType -> NumberType -> [NumberType]
(NumberType -> NumberType)
-> (NumberType -> NumberType)
-> (Int -> NumberType)
-> (NumberType -> Int)
-> (NumberType -> [NumberType])
-> (NumberType -> NumberType -> [NumberType])
-> (NumberType -> NumberType -> [NumberType])
-> (NumberType -> NumberType -> NumberType -> [NumberType])
-> Enum NumberType
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 :: NumberType -> NumberType
succ :: NumberType -> NumberType
$cpred :: NumberType -> NumberType
pred :: NumberType -> NumberType
$ctoEnum :: Int -> NumberType
toEnum :: Int -> NumberType
$cfromEnum :: NumberType -> Int
fromEnum :: NumberType -> Int
$cenumFrom :: NumberType -> [NumberType]
enumFrom :: NumberType -> [NumberType]
$cenumFromThen :: NumberType -> NumberType -> [NumberType]
enumFromThen :: NumberType -> NumberType -> [NumberType]
$cenumFromTo :: NumberType -> NumberType -> [NumberType]
enumFromTo :: NumberType -> NumberType -> [NumberType]
$cenumFromThenTo :: NumberType -> NumberType -> NumberType -> [NumberType]
enumFromThenTo :: NumberType -> NumberType -> NumberType -> [NumberType]
Enum, NumberType -> NumberType -> Bool
(NumberType -> NumberType -> Bool)
-> (NumberType -> NumberType -> Bool) -> Eq NumberType
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: NumberType -> NumberType -> Bool
== :: NumberType -> NumberType -> Bool
$c/= :: NumberType -> NumberType -> Bool
/= :: NumberType -> NumberType -> Bool
Eq, (forall x. NumberType -> Rep NumberType x)
-> (forall x. Rep NumberType x -> NumberType) -> Generic NumberType
forall x. Rep NumberType x -> NumberType
forall x. NumberType -> Rep NumberType x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. NumberType -> Rep NumberType x
from :: forall x. NumberType -> Rep NumberType x
$cto :: forall x. Rep NumberType x -> NumberType
to :: forall x. Rep NumberType x -> NumberType
Generic, Eq NumberType
Eq NumberType =>
(NumberType -> NumberType -> Ordering)
-> (NumberType -> NumberType -> Bool)
-> (NumberType -> NumberType -> Bool)
-> (NumberType -> NumberType -> Bool)
-> (NumberType -> NumberType -> Bool)
-> (NumberType -> NumberType -> NumberType)
-> (NumberType -> NumberType -> NumberType)
-> Ord NumberType
NumberType -> NumberType -> Bool
NumberType -> NumberType -> Ordering
NumberType -> NumberType -> NumberType
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: NumberType -> NumberType -> Ordering
compare :: NumberType -> NumberType -> Ordering
$c< :: NumberType -> NumberType -> Bool
< :: NumberType -> NumberType -> Bool
$c<= :: NumberType -> NumberType -> Bool
<= :: NumberType -> NumberType -> Bool
$c> :: NumberType -> NumberType -> Bool
> :: NumberType -> NumberType -> Bool
$c>= :: NumberType -> NumberType -> Bool
>= :: NumberType -> NumberType -> Bool
$cmax :: NumberType -> NumberType -> NumberType
max :: NumberType -> NumberType -> NumberType
$cmin :: NumberType -> NumberType -> NumberType
min :: NumberType -> NumberType -> NumberType
Ord, ReadPrec [NumberType]
ReadPrec NumberType
Int -> ReadS NumberType
ReadS [NumberType]
(Int -> ReadS NumberType)
-> ReadS [NumberType]
-> ReadPrec NumberType
-> ReadPrec [NumberType]
-> Read NumberType
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS NumberType
readsPrec :: Int -> ReadS NumberType
$creadList :: ReadS [NumberType]
readList :: ReadS [NumberType]
$creadPrec :: ReadPrec NumberType
readPrec :: ReadPrec NumberType
$creadListPrec :: ReadPrec [NumberType]
readListPrec :: ReadPrec [NumberType]
Read, Int -> NumberType -> ShowS
[NumberType] -> ShowS
NumberType -> String
(Int -> NumberType -> ShowS)
-> (NumberType -> String)
-> ([NumberType] -> ShowS)
-> Show NumberType
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> NumberType -> ShowS
showsPrec :: Int -> NumberType -> ShowS
$cshow :: NumberType -> String
show :: NumberType -> String
$cshowList :: [NumberType] -> ShowS
showList :: [NumberType] -> ShowS
Show)

instance Arbitrary NumberType where
  arbitrary :: Gen NumberType
arbitrary = Gen NumberType
forall a. (Bounded a, Enum a) => Gen a
arbitraryBoundedEnum

instance NFData NumberType

-- | The type of a function that converts time to its description. The first
-- two parameters are used to make conversion more convenient.
type ClockText =
  -- | The 'ClockSegment' that describes the state of minutes within an hour.
  ClockSegment ->
  -- | The 'DaySegment' that describes the state of hours within a day.
  DaySegment ->
  -- | The number of hours.
  Int ->
  -- | The number of minutes.
  Int ->
  -- | A 'Text' object that describes the given time.
  Text

-- | A data type that describes the state of the minutes within an hour.
data ClockSegment
  = -- | The number of minutes is zero.
    OClock
  | -- | The parameter is the number of minutes past the hour, this is between @1@ and @14@.
    Past Int
  | -- | It is a quarter past the hour.
    QuarterPast
  | -- | The parameter is the number of minutes until half, this is between @1@ and @14@.
    ToHalf Int
  | -- | It is half past an hour.
    Half
  | -- | The parameter is the number of minutes past half, this is between @1@ and @14@.
    PastHalf Int
  | -- | It is a quarter to an hour.
    QuarterTo
  | -- | The parameter is the number of minutes to the next hour, this is between @1@ and @14@.
    To Int
  deriving (Typeable ClockSegment
Typeable ClockSegment =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> ClockSegment -> c ClockSegment)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c ClockSegment)
-> (ClockSegment -> Constr)
-> (ClockSegment -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c ClockSegment))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c ClockSegment))
-> ((forall b. Data b => b -> b) -> ClockSegment -> ClockSegment)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> ClockSegment -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> ClockSegment -> r)
-> (forall u. (forall d. Data d => d -> u) -> ClockSegment -> [u])
-> (forall u.
    Int -> (forall d. Data d => d -> u) -> ClockSegment -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment)
-> Data ClockSegment
ClockSegment -> Constr
ClockSegment -> DataType
(forall b. Data b => b -> b) -> ClockSegment -> ClockSegment
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> ClockSegment -> u
forall u. (forall d. Data d => d -> u) -> ClockSegment -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ClockSegment
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ClockSegment -> c ClockSegment
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ClockSegment)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c ClockSegment)
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ClockSegment -> c ClockSegment
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ClockSegment -> c ClockSegment
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ClockSegment
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c ClockSegment
$ctoConstr :: ClockSegment -> Constr
toConstr :: ClockSegment -> Constr
$cdataTypeOf :: ClockSegment -> DataType
dataTypeOf :: ClockSegment -> DataType
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ClockSegment)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c ClockSegment)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c ClockSegment)
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c ClockSegment)
$cgmapT :: (forall b. Data b => b -> b) -> ClockSegment -> ClockSegment
gmapT :: (forall b. Data b => b -> b) -> ClockSegment -> ClockSegment
$cgmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
$cgmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ClockSegment -> r
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> ClockSegment -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> ClockSegment -> [u]
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ClockSegment -> u
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> ClockSegment -> u
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> ClockSegment -> m ClockSegment
Data, ClockSegment -> ClockSegment -> Bool
(ClockSegment -> ClockSegment -> Bool)
-> (ClockSegment -> ClockSegment -> Bool) -> Eq ClockSegment
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: ClockSegment -> ClockSegment -> Bool
== :: ClockSegment -> ClockSegment -> Bool
$c/= :: ClockSegment -> ClockSegment -> Bool
/= :: ClockSegment -> ClockSegment -> Bool
Eq, (forall x. ClockSegment -> Rep ClockSegment x)
-> (forall x. Rep ClockSegment x -> ClockSegment)
-> Generic ClockSegment
forall x. Rep ClockSegment x -> ClockSegment
forall x. ClockSegment -> Rep ClockSegment x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. ClockSegment -> Rep ClockSegment x
from :: forall x. ClockSegment -> Rep ClockSegment x
$cto :: forall x. Rep ClockSegment x -> ClockSegment
to :: forall x. Rep ClockSegment x -> ClockSegment
Generic, Eq ClockSegment
Eq ClockSegment =>
(ClockSegment -> ClockSegment -> Ordering)
-> (ClockSegment -> ClockSegment -> Bool)
-> (ClockSegment -> ClockSegment -> Bool)
-> (ClockSegment -> ClockSegment -> Bool)
-> (ClockSegment -> ClockSegment -> Bool)
-> (ClockSegment -> ClockSegment -> ClockSegment)
-> (ClockSegment -> ClockSegment -> ClockSegment)
-> Ord ClockSegment
ClockSegment -> ClockSegment -> Bool
ClockSegment -> ClockSegment -> Ordering
ClockSegment -> ClockSegment -> ClockSegment
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: ClockSegment -> ClockSegment -> Ordering
compare :: ClockSegment -> ClockSegment -> Ordering
$c< :: ClockSegment -> ClockSegment -> Bool
< :: ClockSegment -> ClockSegment -> Bool
$c<= :: ClockSegment -> ClockSegment -> Bool
<= :: ClockSegment -> ClockSegment -> Bool
$c> :: ClockSegment -> ClockSegment -> Bool
> :: ClockSegment -> ClockSegment -> Bool
$c>= :: ClockSegment -> ClockSegment -> Bool
>= :: ClockSegment -> ClockSegment -> Bool
$cmax :: ClockSegment -> ClockSegment -> ClockSegment
max :: ClockSegment -> ClockSegment -> ClockSegment
$cmin :: ClockSegment -> ClockSegment -> ClockSegment
min :: ClockSegment -> ClockSegment -> ClockSegment
Ord, ReadPrec [ClockSegment]
ReadPrec ClockSegment
Int -> ReadS ClockSegment
ReadS [ClockSegment]
(Int -> ReadS ClockSegment)
-> ReadS [ClockSegment]
-> ReadPrec ClockSegment
-> ReadPrec [ClockSegment]
-> Read ClockSegment
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS ClockSegment
readsPrec :: Int -> ReadS ClockSegment
$creadList :: ReadS [ClockSegment]
readList :: ReadS [ClockSegment]
$creadPrec :: ReadPrec ClockSegment
readPrec :: ReadPrec ClockSegment
$creadListPrec :: ReadPrec [ClockSegment]
readListPrec :: ReadPrec [ClockSegment]
Read, Int -> ClockSegment -> ShowS
[ClockSegment] -> ShowS
ClockSegment -> String
(Int -> ClockSegment -> ShowS)
-> (ClockSegment -> String)
-> ([ClockSegment] -> ShowS)
-> Show ClockSegment
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> ClockSegment -> ShowS
showsPrec :: Int -> ClockSegment -> ShowS
$cshow :: ClockSegment -> String
show :: ClockSegment -> String
$cshowList :: [ClockSegment] -> ShowS
showList :: [ClockSegment] -> ShowS
Show)

instance NFData ClockSegment

instance Arbitrary ClockSegment where
  arbitrary :: Gen ClockSegment
arbitrary = Int -> ClockSegment
toClockSegment (Int -> ClockSegment) -> Gen Int -> Gen ClockSegment
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Int, Int) -> Gen Int
forall a. Random a => (a, a) -> Gen a
choose (Int
0, Int
59)

-- | A data type that describes the state of the hours within a day.
data DayPart
  = -- | It is night, this means that it is between @0:00@ and @5:59@.
    Night
  | -- | It is morning, this means that it is between @6:00@ and @11:59@.
    Morning
  | -- | It is afternoon, this means it is between @12:00@ and @17:59@.
    Afternoon
  | -- | It is evening, this means it is between @18:00@ and @23:59@.
    Evening
  deriving (DayPart
DayPart -> DayPart -> Bounded DayPart
forall a. a -> a -> Bounded a
$cminBound :: DayPart
minBound :: DayPart
$cmaxBound :: DayPart
maxBound :: DayPart
Bounded, Typeable DayPart
Typeable DayPart =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> DayPart -> c DayPart)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c DayPart)
-> (DayPart -> Constr)
-> (DayPart -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c DayPart))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DayPart))
-> ((forall b. Data b => b -> b) -> DayPart -> DayPart)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> DayPart -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> DayPart -> r)
-> (forall u. (forall d. Data d => d -> u) -> DayPart -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> DayPart -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> DayPart -> m DayPart)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> DayPart -> m DayPart)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> DayPart -> m DayPart)
-> Data DayPart
DayPart -> Constr
DayPart -> DataType
(forall b. Data b => b -> b) -> DayPart -> DayPart
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> DayPart -> u
forall u. (forall d. Data d => d -> u) -> DayPart -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DayPart
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DayPart -> c DayPart
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DayPart)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DayPart)
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DayPart -> c DayPart
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DayPart -> c DayPart
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DayPart
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DayPart
$ctoConstr :: DayPart -> Constr
toConstr :: DayPart -> Constr
$cdataTypeOf :: DayPart -> DataType
dataTypeOf :: DayPart -> DataType
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DayPart)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DayPart)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DayPart)
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DayPart)
$cgmapT :: (forall b. Data b => b -> b) -> DayPart -> DayPart
gmapT :: (forall b. Data b => b -> b) -> DayPart -> DayPart
$cgmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
$cgmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DayPart -> r
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> DayPart -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> DayPart -> [u]
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> DayPart -> u
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> DayPart -> u
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DayPart -> m DayPart
Data, Int -> DayPart
DayPart -> Int
DayPart -> [DayPart]
DayPart -> DayPart
DayPart -> DayPart -> [DayPart]
DayPart -> DayPart -> DayPart -> [DayPart]
(DayPart -> DayPart)
-> (DayPart -> DayPart)
-> (Int -> DayPart)
-> (DayPart -> Int)
-> (DayPart -> [DayPart])
-> (DayPart -> DayPart -> [DayPart])
-> (DayPart -> DayPart -> [DayPart])
-> (DayPart -> DayPart -> DayPart -> [DayPart])
-> Enum DayPart
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 :: DayPart -> DayPart
succ :: DayPart -> DayPart
$cpred :: DayPart -> DayPart
pred :: DayPart -> DayPart
$ctoEnum :: Int -> DayPart
toEnum :: Int -> DayPart
$cfromEnum :: DayPart -> Int
fromEnum :: DayPart -> Int
$cenumFrom :: DayPart -> [DayPart]
enumFrom :: DayPart -> [DayPart]
$cenumFromThen :: DayPart -> DayPart -> [DayPart]
enumFromThen :: DayPart -> DayPart -> [DayPart]
$cenumFromTo :: DayPart -> DayPart -> [DayPart]
enumFromTo :: DayPart -> DayPart -> [DayPart]
$cenumFromThenTo :: DayPart -> DayPart -> DayPart -> [DayPart]
enumFromThenTo :: DayPart -> DayPart -> DayPart -> [DayPart]
Enum, DayPart -> DayPart -> Bool
(DayPart -> DayPart -> Bool)
-> (DayPart -> DayPart -> Bool) -> Eq DayPart
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: DayPart -> DayPart -> Bool
== :: DayPart -> DayPart -> Bool
$c/= :: DayPart -> DayPart -> Bool
/= :: DayPart -> DayPart -> Bool
Eq, (forall x. DayPart -> Rep DayPart x)
-> (forall x. Rep DayPart x -> DayPart) -> Generic DayPart
forall x. Rep DayPart x -> DayPart
forall x. DayPart -> Rep DayPart x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. DayPart -> Rep DayPart x
from :: forall x. DayPart -> Rep DayPart x
$cto :: forall x. Rep DayPart x -> DayPart
to :: forall x. Rep DayPart x -> DayPart
Generic, Eq DayPart
Eq DayPart =>
(DayPart -> DayPart -> Ordering)
-> (DayPart -> DayPart -> Bool)
-> (DayPart -> DayPart -> Bool)
-> (DayPart -> DayPart -> Bool)
-> (DayPart -> DayPart -> Bool)
-> (DayPart -> DayPart -> DayPart)
-> (DayPart -> DayPart -> DayPart)
-> Ord DayPart
DayPart -> DayPart -> Bool
DayPart -> DayPart -> Ordering
DayPart -> DayPart -> DayPart
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: DayPart -> DayPart -> Ordering
compare :: DayPart -> DayPart -> Ordering
$c< :: DayPart -> DayPart -> Bool
< :: DayPart -> DayPart -> Bool
$c<= :: DayPart -> DayPart -> Bool
<= :: DayPart -> DayPart -> Bool
$c> :: DayPart -> DayPart -> Bool
> :: DayPart -> DayPart -> Bool
$c>= :: DayPart -> DayPart -> Bool
>= :: DayPart -> DayPart -> Bool
$cmax :: DayPart -> DayPart -> DayPart
max :: DayPart -> DayPart -> DayPart
$cmin :: DayPart -> DayPart -> DayPart
min :: DayPart -> DayPart -> DayPart
Ord, ReadPrec [DayPart]
ReadPrec DayPart
Int -> ReadS DayPart
ReadS [DayPart]
(Int -> ReadS DayPart)
-> ReadS [DayPart]
-> ReadPrec DayPart
-> ReadPrec [DayPart]
-> Read DayPart
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS DayPart
readsPrec :: Int -> ReadS DayPart
$creadList :: ReadS [DayPart]
readList :: ReadS [DayPart]
$creadPrec :: ReadPrec DayPart
readPrec :: ReadPrec DayPart
$creadListPrec :: ReadPrec [DayPart]
readListPrec :: ReadPrec [DayPart]
Read, Int -> DayPart -> ShowS
[DayPart] -> ShowS
DayPart -> String
(Int -> DayPart -> ShowS)
-> (DayPart -> String) -> ([DayPart] -> ShowS) -> Show DayPart
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DayPart -> ShowS
showsPrec :: Int -> DayPart -> ShowS
$cshow :: DayPart -> String
show :: DayPart -> String
$cshowList :: [DayPart] -> ShowS
showList :: [DayPart] -> ShowS
Show)

instance Arbitrary DayPart where
  arbitrary :: Gen DayPart
arbitrary = Gen DayPart
forall a. (Bounded a, Enum a) => Gen a
arbitraryBoundedEnum

instance NFData DayPart

-- | A data type that describes the part of the day, and the number of hours on
-- a 12-hour clock.
data DaySegment = DaySegment
  { -- | The part of the day.
    DaySegment -> DayPart
dayPart :: DayPart,
    -- | The number of hours, between @1@ and @12@ (both inclusive).
    DaySegment -> Int
dayHour :: Int
  }
  deriving (Typeable DaySegment
Typeable DaySegment =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> DaySegment -> c DaySegment)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c DaySegment)
-> (DaySegment -> Constr)
-> (DaySegment -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c DaySegment))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c DaySegment))
-> ((forall b. Data b => b -> b) -> DaySegment -> DaySegment)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> DaySegment -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> DaySegment -> r)
-> (forall u. (forall d. Data d => d -> u) -> DaySegment -> [u])
-> (forall u.
    Int -> (forall d. Data d => d -> u) -> DaySegment -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> DaySegment -> m DaySegment)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> DaySegment -> m DaySegment)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> DaySegment -> m DaySegment)
-> Data DaySegment
DaySegment -> Constr
DaySegment -> DataType
(forall b. Data b => b -> b) -> DaySegment -> DaySegment
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> DaySegment -> u
forall u. (forall d. Data d => d -> u) -> DaySegment -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DaySegment
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DaySegment -> c DaySegment
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DaySegment)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DaySegment)
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DaySegment -> c DaySegment
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> DaySegment -> c DaySegment
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DaySegment
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c DaySegment
$ctoConstr :: DaySegment -> Constr
toConstr :: DaySegment -> Constr
$cdataTypeOf :: DaySegment -> DataType
dataTypeOf :: DaySegment -> DataType
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DaySegment)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c DaySegment)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DaySegment)
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c DaySegment)
$cgmapT :: (forall b. Data b => b -> b) -> DaySegment -> DaySegment
gmapT :: (forall b. Data b => b -> b) -> DaySegment -> DaySegment
$cgmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
$cgmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> DaySegment -> r
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> DaySegment -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> DaySegment -> [u]
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> DaySegment -> u
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> DaySegment -> u
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> DaySegment -> m DaySegment
Data, DaySegment -> DaySegment -> Bool
(DaySegment -> DaySegment -> Bool)
-> (DaySegment -> DaySegment -> Bool) -> Eq DaySegment
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: DaySegment -> DaySegment -> Bool
== :: DaySegment -> DaySegment -> Bool
$c/= :: DaySegment -> DaySegment -> Bool
/= :: DaySegment -> DaySegment -> Bool
Eq, (forall x. DaySegment -> Rep DaySegment x)
-> (forall x. Rep DaySegment x -> DaySegment) -> Generic DaySegment
forall x. Rep DaySegment x -> DaySegment
forall x. DaySegment -> Rep DaySegment x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. DaySegment -> Rep DaySegment x
from :: forall x. DaySegment -> Rep DaySegment x
$cto :: forall x. Rep DaySegment x -> DaySegment
to :: forall x. Rep DaySegment x -> DaySegment
Generic, Eq DaySegment
Eq DaySegment =>
(DaySegment -> DaySegment -> Ordering)
-> (DaySegment -> DaySegment -> Bool)
-> (DaySegment -> DaySegment -> Bool)
-> (DaySegment -> DaySegment -> Bool)
-> (DaySegment -> DaySegment -> Bool)
-> (DaySegment -> DaySegment -> DaySegment)
-> (DaySegment -> DaySegment -> DaySegment)
-> Ord DaySegment
DaySegment -> DaySegment -> Bool
DaySegment -> DaySegment -> Ordering
DaySegment -> DaySegment -> DaySegment
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: DaySegment -> DaySegment -> Ordering
compare :: DaySegment -> DaySegment -> Ordering
$c< :: DaySegment -> DaySegment -> Bool
< :: DaySegment -> DaySegment -> Bool
$c<= :: DaySegment -> DaySegment -> Bool
<= :: DaySegment -> DaySegment -> Bool
$c> :: DaySegment -> DaySegment -> Bool
> :: DaySegment -> DaySegment -> Bool
$c>= :: DaySegment -> DaySegment -> Bool
>= :: DaySegment -> DaySegment -> Bool
$cmax :: DaySegment -> DaySegment -> DaySegment
max :: DaySegment -> DaySegment -> DaySegment
$cmin :: DaySegment -> DaySegment -> DaySegment
min :: DaySegment -> DaySegment -> DaySegment
Ord, ReadPrec [DaySegment]
ReadPrec DaySegment
Int -> ReadS DaySegment
ReadS [DaySegment]
(Int -> ReadS DaySegment)
-> ReadS [DaySegment]
-> ReadPrec DaySegment
-> ReadPrec [DaySegment]
-> Read DaySegment
forall a.
(Int -> ReadS a)
-> ReadS [a] -> ReadPrec a -> ReadPrec [a] -> Read a
$creadsPrec :: Int -> ReadS DaySegment
readsPrec :: Int -> ReadS DaySegment
$creadList :: ReadS [DaySegment]
readList :: ReadS [DaySegment]
$creadPrec :: ReadPrec DaySegment
readPrec :: ReadPrec DaySegment
$creadListPrec :: ReadPrec [DaySegment]
readListPrec :: ReadPrec [DaySegment]
Read, Int -> DaySegment -> ShowS
[DaySegment] -> ShowS
DaySegment -> String
(Int -> DaySegment -> ShowS)
-> (DaySegment -> String)
-> ([DaySegment] -> ShowS)
-> Show DaySegment
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> DaySegment -> ShowS
showsPrec :: Int -> DaySegment -> ShowS
$cshow :: DaySegment -> String
show :: DaySegment -> String
$cshowList :: [DaySegment] -> ShowS
showList :: [DaySegment] -> ShowS
Show)

instance Arbitrary DaySegment where
  arbitrary :: Gen DaySegment
arbitrary = Int -> DaySegment
toDaySegment (Int -> DaySegment) -> Gen Int -> Gen DaySegment
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Int, Int) -> Gen Int
forall a. Random a => (a, a) -> Gen a
choose (Int
0, Int
23)

instance NFData DaySegment

-- | Convert the given number of minutes to the corresponding 'ClockSegment'.
toClockSegment ::
  -- | The number of minutes.
  Int ->
  -- | The corresponding 'ClockSegment'.
  ClockSegment
toClockSegment :: Int -> ClockSegment
toClockSegment Int
0 = ClockSegment
OClock
toClockSegment Int
15 = ClockSegment
QuarterPast
toClockSegment Int
30 = ClockSegment
Half
toClockSegment Int
45 = ClockSegment
QuarterTo
toClockSegment Int
n
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
15 = Int -> ClockSegment
Past Int
n
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
30 = Int -> ClockSegment
ToHalf (Int
30 Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
n)
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
45 = Int -> ClockSegment
PastHalf (Int
n Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
30)
  | Bool
otherwise = Int -> ClockSegment
To (Int
60 Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
n)

-- | Convert the given number of hours to the corresponding 'DayPart'.
toDayPart ::
  -- | The given number of hours.
  Int ->
  -- | The corresponding 'DayPart'.
  DayPart
toDayPart :: Int -> DayPart
toDayPart Int
n
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
5 = DayPart
Night
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
11 = DayPart
Morning
  | Int
n Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
<= Int
17 = DayPart
Afternoon
  | Bool
otherwise = DayPart
Evening

-- | Convert the given number of hours to the corresponding 'DaySegment'.
toDaySegment ::
  -- | The given number of hours.
  Int ->
  -- | The corresponding 'DaySegment'.
  DaySegment
toDaySegment :: Int -> DaySegment
toDaySegment Int
n = DayPart -> Int -> DaySegment
DaySegment (Int -> DayPart
toDayPart Int
n) (Int -> Int
hourCorrection Int
n)

-- | Correct the hour to a 12 number segment.
-- The input can be any Int number, whereas the
-- result will be in the @1 .. 12@ range.
hourCorrection ::
  -- | The value for the number of hours.
  Int ->
  -- | The hours in the @1 .. 12@ range.
  Int
hourCorrection :: Int -> Int
hourCorrection Int
h = ((Int
h Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1) Int -> Int -> Int
forall a. Integral a => a -> a -> a
`mod` Int
12) Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
1

instance Default NumberType where
  def :: NumberType
def = NumberType
Cardinal

-- | A type class used for num to word algorithms. It maps an 'Integral' type
-- @i@ to 'Text'.
class NumToWord a where
  -- | Convert the given number to a 'Text' object that is the given number in
  -- words in /cardinal/ form.
  toCardinal ::
    Integral i =>
    -- | The conversion algorithm that transforms the number into words.
    a ->
    -- | The number to transform into a /cardinal/ form.
    i ->
    -- | The number in words in a /cardinal/ form.
    Text
  toCardinal = NumberType -> a -> i -> Text
forall i. Integral i => NumberType -> a -> i -> Text
forall a i.
(NumToWord a, Integral i) =>
NumberType -> a -> i -> Text
toWords NumberType
Cardinal

  -- | Convert the given number to a 'Text' object that is the given number in
  -- words in /cardinal/ form.
  toOrdinal ::
    Integral i =>
    -- | The conversion algorithm that transforms the number into words.
    a ->
    -- | The number to transform into a /ordinal/ form.
    i ->
    -- | The number in words in a /ordinal/ form.
    Text
  toOrdinal = NumberType -> a -> i -> Text
forall i. Integral i => NumberType -> a -> i -> Text
forall a i.
(NumToWord a, Integral i) =>
NumberType -> a -> i -> Text
toWords NumberType
Ordinal

  -- | Convert the given number to a 'Text' object that is the given number
  -- in words in /short cardinal/ form.
  toShortOrdinal ::
    Integral i =>
    -- | The conversion algorithm that transforms the number into words.
    a ->
    -- | The number to transform into a /ordinal/ form.
    i ->
    -- | The number in words in a /ordinal/ form.
    Text
  toShortOrdinal = NumberType -> a -> i -> Text
forall i. Integral i => NumberType -> a -> i -> Text
forall a i.
(NumToWord a, Integral i) =>
NumberType -> a -> i -> Text
toWords NumberType
Ordinal

  -- | Convert the given number to a 'Text' object that is the given number in
  -- words in the given 'NumberType'.
  toWords ::
    Integral i =>
    -- | The given format to convert the number to.
    NumberType ->
    -- | The conversion algorithm that transforms the number into words.
    a ->
    -- | The number to transform into the given form.
    i ->
    -- | The number in words in the given form.
    Text
  toWords NumberType
Cardinal = a -> i -> Text
forall i. Integral i => a -> i -> Text
forall a i. (NumToWord a, Integral i) => a -> i -> Text
toCardinal
  toWords NumberType
Ordinal = a -> i -> Text
forall i. Integral i => a -> i -> Text
forall a i. (NumToWord a, Integral i) => a -> i -> Text
toOrdinal
  toWords NumberType
ShortOrdinal = a -> i -> Text
forall i. Integral i => a -> i -> Text
forall a i. (NumToWord a, Integral i) => a -> i -> Text
toShortOrdinal

  -- | Convert the given time of the day to text describing that time.
  toTimeText ::
    -- | The conversion algorithm to transform numbers into words.
    a ->
    -- | The time of the day to convert to words.
    TimeOfDay ->
    -- | The time as /text/.
    Text
  toTimeText a
gen (TimeOfDay Int
h Int
m Pico
_) = a -> Int -> Int -> Text
forall a. NumToWord a => a -> Int -> Int -> Text
toTimeText' a
gen Int
h Int
m

  -- | Convert the given hours and minutes to text that describes the time.
  toTimeText' ::
    -- | The conversion algorithm to transform numbers into words.
    a ->
    -- | The number of hours, between 0 and 23 (both inclusive)
    Int ->
    -- | The number of minutes, beween 0 and 59 (both inclusive)
    Int ->
    -- | The time as /text/.
    Text
  toTimeText' a
gen Int
h Int
m = a -> TimeOfDay -> Text
forall a. NumToWord a => a -> TimeOfDay -> Text
toTimeText a
gen (Int -> Int -> Pico -> TimeOfDay
TimeOfDay Int
h Int
m Pico
0)

  {-# MINIMAL ((toCardinal, toOrdinal, toShortOrdinal) | toWords), (toTimeText | toTimeText') #-}

-- | Convert the current time in the given 'TimeZone' to the time in words with the given 'NumToWord'
-- algorithm.
currentTimeText ::
  NumToWord a =>
  -- | The given 'TimeZone'.
  TimeZone ->
  -- | The 'NumToWord' algorithm that converts time to words.
  a ->
  -- | An 'IO' that will generate a 'Text' object that describes the current time in words.
  IO Text
currentTimeText :: forall a. NumToWord a => TimeZone -> a -> IO Text
currentTimeText TimeZone
tz a
alg = a -> TimeOfDay -> Text
forall a. NumToWord a => a -> TimeOfDay -> Text
toTimeText a
alg (TimeOfDay -> Text) -> (UTCTime -> TimeOfDay) -> UTCTime -> Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Integer, TimeOfDay) -> TimeOfDay
forall a b. (a, b) -> b
snd ((Integer, TimeOfDay) -> TimeOfDay)
-> (UTCTime -> (Integer, TimeOfDay)) -> UTCTime -> TimeOfDay
forall b c a. (b -> c) -> (a -> b) -> a -> c
. TimeZone -> TimeOfDay -> (Integer, TimeOfDay)
utcToLocalTimeOfDay TimeZone
tz (TimeOfDay -> (Integer, TimeOfDay))
-> (UTCTime -> TimeOfDay) -> UTCTime -> (Integer, TimeOfDay)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DiffTime -> TimeOfDay
timeToTimeOfDay (DiffTime -> TimeOfDay)
-> (UTCTime -> DiffTime) -> UTCTime -> TimeOfDay
forall b c a. (b -> c) -> (a -> b) -> a -> c
. UTCTime -> DiffTime
utctDayTime (UTCTime -> Text) -> IO UTCTime -> IO Text
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> IO UTCTime
getCurrentTime

-- | Convert the current time to the time in words with the given 'NumToWord'
-- algorithm as UTC time.
currentTimeText' ::
  NumToWord a =>
  -- | The 'NumToWord' algorithm that converts time to words.
  a ->
  -- | An 'IO' that will generate a 'Text' object that describes the current time in words.
  IO Text
currentTimeText' :: forall a. NumToWord a => a -> IO Text
currentTimeText' a
alg = a -> TimeOfDay -> Text
forall a. NumToWord a => a -> TimeOfDay -> Text
toTimeText a
alg (TimeOfDay -> Text) -> (UTCTime -> TimeOfDay) -> UTCTime -> Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. DiffTime -> TimeOfDay
timeToTimeOfDay (DiffTime -> TimeOfDay)
-> (UTCTime -> DiffTime) -> UTCTime -> TimeOfDay
forall b c a. (b -> c) -> (a -> b) -> a -> c
. UTCTime -> DiffTime
utctDayTime (UTCTime -> Text) -> IO UTCTime -> IO Text
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> IO UTCTime
getCurrentTime

-- | A type class used to split a value, based on the name of a number in a
-- specific language. The value that is used to split, is often, depending on
-- the language, the largest value smaller than the given number.
class ValueSplit a where
  -- | A function that takes an 'Integral' value, and based on the object
  -- splits it with a value and the name of the number in a specific language.
  valueSplit :: a -> FreeValueSplitter