-- | Forms that configure themselves based on type -- -- The Combined module both renders to 'Html' and also parses input. module SimpleForm.Combined ( Widget, DefaultWidget(..), Validation(..), DefaultValidation(..), -- * Options InputOptions(..), Label(..), -- * Wrappers ShowRead(..), unShowRead, SelectEnum(..), unSelectEnum, -- * Widgets button, hidden, checkbox, file, -- ** Text-like text, textarea, password, search, email, uri, tel, -- ** Numbers number, integral, boundedNumber, boundedIntegral, -- ** Dates and times date, time, datetime, datetime_local, -- ** Collections GroupedCollection', Collection', select, multi_select, radio_buttons, buttons, checkboxes, -- * Helpers selectEnum, enum, group_, multiEnum, humanize ) where import Data.Time (FormatTime, ParseTime) import Text.Email.Validate (EmailAddress) import Network.URI (URI) import Data.Text (Text) import qualified Data.Text as T import SimpleForm (DefaultWidget, Widget, InputOptions(..), Label(..), ShowRead(..), unShowRead, SelectEnum(..), unSelectEnum, humanize) import SimpleForm.Validation (DefaultValidation, Validation(..), selectEnum, GroupedCollection', Collection', group_) import qualified SimpleForm import qualified SimpleForm.Validation as Validation -- Orphan instances, but for our own classes instance DefaultWidget EmailAddress where wdef = SimpleForm.email . fmap (T.pack . show) instance DefaultWidget URI where wdef = SimpleForm.email . fmap (T.pack . show) -- | Feed a collection 'Widget' and 'Validation' from an enumerable type enum :: (Show a, Read a, Bounded a, Enum a) => (GroupedCollection' a -> (Widget Text, Validation a)) -> (Widget a, Validation a) enum f = (w . fmap (T.pack . show), v) where (w,v) = f (group_ selectEnum) -- | Feed a multi-select collection 'Widget' and 'Validation' from an enumerable type multiEnum :: (Show a, Read a, Bounded a, Enum a) => (GroupedCollection' a -> (Widget [Text], Validation [a])) -> (Widget [a], Validation [a]) multiEnum f = (w . fmap (fmap (T.pack . show)), v) where (w,v) = f (group_ selectEnum) text :: (Widget Text, Validation Text) text = (SimpleForm.text, Validation.text) password :: (Widget Text, Validation Text) password = (SimpleForm.password, Validation.text) search :: (Widget Text, Validation Text) search = (SimpleForm.search, Validation.text) email :: (Widget EmailAddress, Validation EmailAddress) email = (SimpleForm.email . fmap (T.pack . show), Validation.email) uri :: (Widget URI, Validation URI) uri = (SimpleForm.uri . fmap (T.pack . show), Validation.uri) tel :: (Widget Text, Validation Text) tel = (SimpleForm.tel, Validation.text) number :: (Num a, Show a, Read a) => (Widget a, Validation a) number = (SimpleForm.number, Validation.read) integral :: (Integral a, Show a, Read a) => (Widget a, Validation a) integral = (SimpleForm.integral, Validation.read) boundedNumber :: (Bounded a, Num a, Show a, Read a) => (Widget a, Validation a) boundedNumber = (SimpleForm.boundedNumber, Validation.read) boundedIntegral :: (Bounded a, Integral a, Show a, Read a) => (Widget a, Validation a) boundedIntegral = (SimpleForm.boundedIntegral, Validation.read) textarea :: (Widget Text, Validation Text) textarea = (SimpleForm.textarea, Validation.text) button :: (Widget Text, Validation Text) button = (SimpleForm.textarea, Validation.text) hidden :: (Widget Text, Validation Text) hidden = (SimpleForm.hidden, Validation.text) file :: (Widget Text, Validation Text) file = (SimpleForm.file, Validation.text) checkbox :: (Widget Bool, Validation Bool) checkbox = (SimpleForm.checkbox, Validation.bool) date :: (FormatTime a, ParseTime a) => (Widget a, Validation a) date = (SimpleForm.date, Validation.date) time :: (FormatTime a, ParseTime a) => (Widget a, Validation a) time = (SimpleForm.time, Validation.time) datetime :: (FormatTime a, ParseTime a) => (Widget a, Validation a) datetime = (SimpleForm.datetime, Validation.datetime) datetime_local :: (FormatTime a, ParseTime a) => (Widget a, Validation a) datetime_local = (SimpleForm.datetime_local, Validation.datetime_local) select :: GroupedCollection' a -> (Widget Text, Validation a) select collection = ( SimpleForm.select (Validation.viewGroupedCollection collection), Validation.includes collection ) multi_select :: GroupedCollection' a -> (Widget [Text], Validation [a]) multi_select collection = ( SimpleForm.multi_select (Validation.viewGroupedCollection collection), Validation.multi_includes collection ) radio_buttons :: GroupedCollection' a -> (Widget Text, Validation a) radio_buttons collection = ( SimpleForm.radio_buttons (Validation.viewGroupedCollection collection), Validation.includes collection ) buttons :: GroupedCollection' a -> (Widget Text, Validation a) buttons collection = ( SimpleForm.buttons (Validation.viewGroupedCollection collection), Validation.includes collection ) checkboxes :: GroupedCollection' a -> (Widget [Text], Validation [a]) checkboxes collection = ( SimpleForm.checkboxes (Validation.viewGroupedCollection collection), Validation.multi_includes collection )