-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | A Python str.format() like formatter -- -- Please see the http://hackage.haskell.org/package/vformat @package vformat @version 0.10.0.0 -- | This library is inspired by Python's str.format and Haskell's -- Text.Printf, and most of the features are copied from these two -- libraries. module Text.Format -- | Format a variable number of arguments with Python-style format string -- --
-- >>> format "{:s}, {:d}, {:.4f}" "hello" 123 pi
-- "hello, 123, 3.1416"
--
-- >>> format "{1:s}, {0:d}, {2:.4f}" 123 "hello" pi
-- "hello, 123, 3.1416"
--
-- >>> format "{:s} {:d} {pi:.4f}" "hello" 123 ("pi" := pi)
-- "hello, 123, 3.1416"
--
--
-- See Format to learn more about format string syntax.
--
-- See FormatArg to learn how to derive FormatArg for your own
-- data types.
format :: FormatType r => Format -> r
-- | A variant of format, it takes only one positional argument
--
--
-- >>> :set -XDeriveGeneric
--
-- >>> import GHC.Generics
--
-- >>> data Triple = Triple String Int Double deriving Generic
--
-- >>> instance FormatArg Triple
--
-- >>> format "{0!0:s} {0!1:d} {0!2:.4f}" $ Triple "hello" 123 pi
-- "hello, 123, 3.1416"
--
-- >>> format1 "{0:s} {1:d} {2:.4f}" $ Triple "hello" 123 pi
-- "hello, 123, 3.1416"
--
format1 :: FormatArg a => Format1 -> a -> String
-- | Typeclass of formatable values.
--
-- The formatArg method takes a value, a key and a field format
-- descriptor and either fails due to a ArgError or produce a
-- string as the result. There is a default formatArg for
-- Generic instances.
--
-- There are two reasons may cause formatting fail
--
--
-- {-# LANGUAGE DeriveGeneric #-}
-- {-# LANGUAGE OverloadedStrings #-}
--
-- import Control.Exception
-- import GHC.Generics
-- import Text.Format
--
-- instance FormatArg () where
-- formatArg x k fmt@(ArgFmt{fmtSpecs="U"}) =
-- let fmt' = fmt{fmtSpecs = ""}
-- in formatArg (show x) k fmt'
-- formatArg _ _ _ = Left ArgFmtError
--
-- data Color = Red | Yellow | Blue deriving Generic
--
-- instance FormatArg Color
--
-- data Triple = Triple String Int Double deriving Generic
--
-- instance FormatArg Triple
--
-- data Student = Student { no :: Int
-- , name :: String
-- , age :: Int
-- } deriving Generic
--
-- instance FormatArg Student
--
-- main :: IO ()
-- main = do
-- putStrLn $ format "A unit {:U}" ()
-- putStrLn $ format "I like {}." Blue
-- putStrLn $ format "Triple {0!0} {0!1} {0!2}" $ Triple "Hello" 123 pi
-- putStrLn $ format1 "Student: {no} {name} {age}" $ Student 1 "neo" 30
--
class FormatArg a
formatArg :: FormatArg a => a -> Formatter
formatArg :: (FormatArg a, Generic a, GFormatArg (Rep a)) => a -> Formatter
-- | A typeclass provides the variable arguments magic for format
class FormatType t
sfmt :: FormatType t => Format -> Map ArgKey Formatter -> t
type Formatter = ArgKey -> ArgFmt -> Either SomeException String
-- | A data type indicates a format string
--
-- Format string contains "replacement fields" surrounded by curly braces
-- {}. Anything that is not contained in braces is considered literal
-- text, which is copied unchanged to the output. If you need to include
-- a brace character in the literal text, it can be escaped by doubling
-- {{ and }}.
--
--
-- format :: {chars | ("{" [key][":"fmt] "}")}
-- key :: <see ArgKey>
-- fmt :: <see ArgFmt>
--
--
--
-- Note: This library use a description language to describe syntax, see
-- next section.
--
-- Note: A key can be omitted only if there is no explict index key
-- before it, it will be automatically caculated and inserted to the
-- format string according to its position in the omitted key sequence.
--
-- Examples
--
--
-- >>> "I like {coffee}, I drink it everyday." :: Format
--
-- >>> "{no:<20} {name:<20} {age}" :: Format
--
-- >>> "{{\"no\": {no}, \"name\": \"{name}\"}}" :: Format
--
--
--
-- identifier identifier of an expr
-- <description> use human language as an expr
-- :: use right hand expr to describe identifier
-- () a required field, may be omitted
-- [] an optional field
-- {} repeat any times of the field
-- | logical or, choice between left and right
-- "" literal text
--
--
--
-- Built-in exprs
--
--
-- char :: <any character>
-- chars :: {char}
-- int :: <integer without sign>
--
--
data Format
-- | A variant of Format, it transforms all argument's key to
-- Nest (Index 0) key
data Format1
-- | A data type indicates key of format argument
--
--
-- key :: [(int | chars) {"!" (int | chars)}]
--
--
--
-- Note: See Format to learn more about syntax description
-- language
--
-- Examples
--
-- -- >>> read "0" :: ArgKey -- -- >>> read "country" :: ArgKey -- -- >>> read "coun!!try" :: ArgKey -- -- >>> read "country!name" :: ArgKey -- -- >>> read "country!cities!10!name" :: ArgKey --data ArgKey -- | Refers to a positional argument or index in a list like argument. Index :: Int -> ArgKey -- | Refers to a named argument or a record name of an argument. Name :: String -> ArgKey -- | Refers to a attribute (index or name) of an argument. Nest :: ArgKey -> ArgKey -> ArgKey -- | A data type indicates how to format an argument. -- --
-- fmt :: [[pad] align][sign]["#"]["0"][width][sep]["." precision][specs]
-- pad :: char
-- align :: "<" | ">" | "^" | "="
-- sign :: "+" | "-" | " "
-- width :: int | ("{" key "}")
-- sep :: "_" | ","
-- precision :: int | ("{" key "}")
-- specs :: chars
-- key :: <see ArgKey>
--
--
--
-- -- >>> read "*<30s" :: ArgFmt -- -- >>> read "<10.20s" :: ArgFmt -- -- >>> read "0=10_.20d" :: ArgFmt -- -- >>> read "#010_.20b" :: ArgFmt ---- --
-- s -- default s -- ---- --
-- b binary format integer -- c char point (Char will be trasformed by ord first) -- d decimal format integer -- o octal format integer -- x hex format integer (use lower-case letters) -- X hex format integer (use upper-case letters) -- default d -- ---- --
-- e exponent notation, see showEFloat -- E same as "e", but use upper-case E as separator -- f fixed-point notation see showFFloat -- F same as "f", but converts nan to NAN and inf to INF -- g general format, see showGFloat -- G same as "g", but use upper-case E as separator and -- converts nan to NAN and inf to INF -- % percentage, same as "f" except multiplies 100 first and -- followed by a percent sign -- default g -- ---- -- See FormatArg to learn how to define specs for your own types. data ArgFmt ArgFmt :: FmtAlign -> Char -> FmtSign -> Bool -> Bool -> Either Int ArgKey -> FmtNumSep -> Either Int ArgKey -> String -> String -> ArgFmt [fmtAlign] :: ArgFmt -> FmtAlign [fmtPad] :: ArgFmt -> Char [fmtSign] :: ArgFmt -> FmtSign [fmtAlternate] :: ArgFmt -> Bool [fmtSignAware] :: ArgFmt -> Bool [fmtWidth] :: ArgFmt -> Either Int ArgKey [fmtNumSep] :: ArgFmt -> FmtNumSep [fmtPrecision] :: ArgFmt -> Either Int ArgKey [fmtSpecs] :: ArgFmt -> String -- | When reading from a string, different strings may produce the same -- ArgFmt, this field keeps the original string here in case it is -- use later. [fmtRaw] :: ArgFmt -> String -- | Pretty showing ArgFmt -- -- Note: Don't create ArgFmt manually, read from a string, -- see ArgFmt. prettyArgFmt :: ArgFmt -> String -- | A data type indicates how to align arguments data FmtAlign -- | Not specified, equivalent to AlignLeft unless number's sign -- aware enabled. AlignNone :: FmtAlign -- | Forces the argument to be left-aligned within the available space. AlignLeft :: FmtAlign -- | Forces the field to be right-aligned within the available space. AlignRight :: FmtAlign -- | Forces the field to be centered within the available space. AlignCenter :: FmtAlign -- | Number specified, forces the padding to be placed after the sign (if -- any) but before the digits. AlignSign :: FmtAlign -- | A data type indicates how to show number's sign data FmtSign -- | Not specified, equivalent to SignMinus for signed numbers. SignNone :: FmtSign -- | Sign should be used for both positive as well as negative numbers. SignPlus :: FmtSign -- | Sign should be used only for negative numbers SignMinus :: FmtSign -- | A leading space should be used on positive numbers, and a minus sign -- on negative numbers. SignSpace :: FmtSign -- | A data type indicates number separator -- -- e.g. 20,200,101 20_200_202 data FmtNumSep -- | Don't separate number NumSepNone :: FmtNumSep -- | Use dash as number separator NumSepDash :: FmtNumSep -- | Use comma as number separator NumSepComma :: FmtNumSep -- | A type represents the top-level named key argument. data (:=) a (:=) :: String -> a -> (:=) a infixr 6 := infixr 6 := -- | A data type indicates an arg error data ArgError -- | Can not find argument for the given key ArgKeyError :: ArgError -- | The field format descriptor does not match the argument ArgFmtError :: ArgError -- | Calls vferror to indicate an arg key error for a given type. errorArgKey :: String -> a -- | Calls vferror to indicate an arg format error for a given type. errorArgFmt :: String -> a -- | Raises an error with a vformat-specific prefix on the message string. vferror :: String -> a