-- Hoogle documentation, generated by Haddock
-- See Hoogle, http://www.haskell.org/hoogle/


-- | Two-dimensional box pretty printing, with colors
--   
--   Prints boxes in two dimensions, with colors. Boxes are automatically
--   padded with necessary whitespace.
--   
--   For more information, please see the Haddock documentation and
--   
--   <a>http://www.github.com/massysett/rainbox</a>
@package rainbox
@version 0.18.0.10


-- | Contains the innards of <tt>Rainbox</tt>. You shouldn't need anything
--   in here. Some functions here are partial or have undefined results if
--   their inputs don't respect particular invariants.
module Rainbox.Core

-- | Alignment. Used in conjunction with <a>Horizontal</a> and
--   <a>Vertical</a>, this determines how a payload aligns with the axis of
--   a <a>Box</a>.
data Alignment a
Center :: Alignment a
NonCenter :: a -> Alignment a

-- | <a>mempty</a> is <a>center</a>. <a>mappend</a> takes the rightmost
--   non-<a>center</a> value.

-- | Determines how a payload aligns with a horizontal axis.
data Horizontal
Top :: Horizontal
Bottom :: Horizontal

-- | Determines how a payload aligns with a vertical axis.
data Vertical
Port :: Vertical
Starboard :: Vertical

-- | Place this payload so that it is centered on the vertical axis or
--   horizontal axis.
center :: Alignment a

-- | Center horizontally; like <a>center</a>, but monomorphic.
centerH :: Alignment Horizontal

-- | Center vertically; like <a>center</a>, but monomorphic.
centerV :: Alignment Vertical

-- | Place this payload's left edge on the vertical axis.
left :: Alignment Vertical

-- | Place this payload's right edge on the vertical axis.
right :: Alignment Vertical

-- | Place this payload's top edge on the horizontal axis.
top :: Alignment Horizontal

-- | Place this payload's bottom edge on the horizontal axis.
bottom :: Alignment Horizontal

-- | A count of rows.
newtype Height
Height :: Int -> Height

-- | A count of columns.
newtype Width
Width :: Int -> Width
class HasHeight a
height :: HasHeight a => a -> Int
class HasWidth a
width :: HasWidth a => a -> Int

-- | A <a>Core</a> is either a single <a>Chunk</a> or, if the box is blank,
--   is merely a height and a width.
newtype Core
Core :: (Either (Chunk Text) (Height, Width)) -> Core

-- | An intermediate type used in rendering; it consists either of text
--   <a>Chunk</a> or of a number of spaces coupled with a background color.
newtype Rod
Rod :: (Either (Int, Radiant) (Chunk Text)) -> Rod

-- | A list of screen rows; each screen row is a <a>Seq</a> of <a>Rod</a>.
--   
--   A <a>RodRows</a> with width but no height does nothing if rendered
--   alone, but it can affect the width of other <a>RodRows</a> if combined
--   with them.
data RodRows

-- | Each outer <a>Seq</a> represents a single screen row. Each <a>Seq</a>
--   has a height of 1.
--   
--   The outer <a>Seq</a> must have a length of at least 1, even if the
--   inner <a>Seq</a> is empty. If the outer <a>Seq</a> has a length of
--   zero, undefined behavior occurs. For a <a>RodRows</a> with no height
--   and no width, use <a>RodRowsNoHeight</a>.
RodRowsWithHeight :: (Seq (Seq Rod)) -> RodRows

-- | A <a>RodRows</a> that has no height. If the <a>Int</a> is less than 1,
--   the <a>RodRows</a> has no width and no height. Otherwise, the
--   <a>RodRows</a> has no height but has the given width.
RodRowsNoHeight :: Int -> RodRows

-- | Convert a <a>Core</a> to a <a>Seq</a> of <a>Rod</a> for rendering.
rodRowsFromCore :: Radiant -> Core -> RodRows

-- | Converts a <a>RodRows</a> to a nested <a>Seq</a> of <a>Chunk</a> in
--   preparation for rendering. Newlines are added to the end of each line.
chunksFromRodRows :: RodRows -> Seq (Seq (Chunk Text))

-- | A <a>Payload</a> holds a <a>RodRows</a>, which determines the number
--   and content of the screen rows. The <a>Payload</a> also has an
--   <a>Alignment</a>, which specifies how the payload aligns with the
--   axis. Whether the <a>Alignment</a> is <a>Horizontal</a> or
--   <a>Vertical</a> determines the orientation of the <a>Payload</a>. The
--   <a>Payload</a> also contains a background color, which is type
--   <a>Radiant</a>. The background color extends continuously from the
--   <a>Payload</a> in both directions that are perpendicular to the axis.
data Payload a
Payload :: (Alignment a) -> Radiant -> (Either RodRows Core) -> Payload a

-- | Adds padding to the top and bottom of each Payload. A Payload with a
--   Core is converted to a RodRows and has padding added; a Payload with a
--   RodRows has necessary padding added to the top and bottom. The number
--   of elements in the resulting Seq is the same as the number of elements
--   in the input Seq; no merging is performed.
addVerticalPadding :: Box Horizontal -> Seq RodRows

-- | Merges multiple horizontal RodRows into a single RodRows. All RodRows
--   must already have been the same height; if they are not the same
--   height, undefined behavior occurs.
horizontalMerge :: Seq RodRows -> RodRows

-- | Split a number into two parts, so that the sum of the two parts is
--   equal to the original number.
split :: Int -> (Int, Int)

-- | Adds padding to the left and right of each Payload. A Payload with a
--   Core is converted to a RodRows and has padding added; a Payload with a
--   RodRows has necessary padding added to the left and right. The number
--   of elements in the resulting Seq is the same as the number of elements
--   in the input Seq; no merging is performed.
addHorizontalPadding :: Box Vertical -> Seq RodRows

-- | Merge multiple vertical RodRows into a single RodRows. Each RodRows
--   should already be the same width.
verticalMerge :: Seq RodRows -> RodRows

-- | A <a>Box</a> is the central building block. It consists of zero or
--   more payloads; each payload has the same orientation, which is either
--   <a>Horizontal</a> or <a>Vertical</a>. This orientation also determines
--   the orientation of the entire <a>Box</a>.
--   
--   A <a>Box</a> is a <a>Monoid</a> so you can combine them using the
--   usual monoid functions. For a <a>Box</a> <a>Vertical</a>, the leftmost
--   values added with <a>mappend</a> are at the top of the <a>Box</a>; for
--   a <a>Box</a> <a>Horizontal</a>, the leftmost values added with
--   <a>mappend</a> are on the left side of the <a>Box</a>.
newtype Box a
Box :: (Seq (Payload a)) -> Box a

-- | This typeclass is responsible for transforming a <a>Box</a> into
--   Rainbow <a>Chunk</a> so they can be printed to your screen. This
--   requires adding appropriate whitespace with the right colors, as well
--   as adding newlines in the right places.
class Orientation a
rodRows :: Orientation a => Box a -> RodRows

-- | Builds a one-dimensional box of the given size; its single dimension
--   is parallel to the axis. When added to a box, it will insert blank
--   space of the given length. For a <a>Box</a> <a>Horizontal</a>, this
--   produces a horizontal line; for a <a>Box</a> <a>Vertical</a>, a
--   vertical line.
spacer :: Orientation a => Radiant -> Int -> Box a

-- | Builds a one-dimensional box of the given size; its single dimension
--   is perpendicular to the axis. This can be used to make a <a>Box</a>
--   <a>Vertical</a> wider or a <a>Box</a> <a>Horizontal</a> taller.
spreader :: Orientation a => Alignment a -> Int -> Box a

-- | Things that are oriented around a vertical axis.
class LeftRight a

-- | Length to the left of the vertical axis.
port :: LeftRight a => a -> Int

-- | Length to the right of the vertical axis.
starboard :: LeftRight a => a -> Int

-- | Things that are oriented around a horizontal axis.
class UpDown a

-- | Number of lines above the horizontal axis.
above :: UpDown a => a -> Int

-- | Number of lines below the horizontal axis.
below :: UpDown a => a -> Int

-- | Construct a box from a single <a>Chunk</a>.
fromChunk :: Alignment a -> Radiant -> Chunk Text -> Box a

-- | Construct a blank box. Useful for adding in background spacers. For
--   functions that build one-dimensional boxes, see <a>spacer</a> and
--   <a>spreader</a>.
blank :: Alignment a -> Radiant -> Height -> Width -> Box a

-- | Wrap a <a>Box</a> in another <a>Box</a>. Useful for changing a
--   <a>Horizontal</a> <a>Box</a> to a <a>Vertical</a> one, or simply for
--   putting a <a>Box</a> inside another one to control size and background
--   color.
wrap :: Orientation a => Alignment b -> Radiant -> Box a -> Box b

-- | Convert a box to a <a>Seq</a> of <a>Chunk</a> in preparation for
--   rendering. Use <a>toList</a> to convert the <a>Seq</a> of <a>Chunk</a>
--   to a list so that you can print it using the functions in
--   <a>Rainbow</a>.
render :: Orientation a => Box a -> Seq (Chunk Text)

-- | A single cell in a spreadsheet-like grid.
data Cell
Cell :: Seq (Seq (Chunk Text)) -> Alignment Horizontal -> Alignment Vertical -> Radiant -> Cell

-- | The cell can have multiple rows of text; there is one <a>Seq</a> for
--   each row of text.
[_rows] :: Cell -> Seq (Seq (Chunk Text))

-- | How this <a>Cell</a> should align compared to other <a>Cell</a> in its
--   row.
[_horizontal] :: Cell -> Alignment Horizontal

-- | How this <a>Cell</a> should align compared to other <a>Cell</a> in its
--   column.
[_vertical] :: Cell -> Alignment Vertical

-- | Background color for this cell. The background in the individual
--   <a>Chunk</a> in the <tt>cellRows</tt> are not affected by
--   <tt>cellBackground</tt>; instead, <tt>cellBackground</tt> determines
--   the color of necessary padding that will be added so that the cells
--   make a uniform table.
[_background] :: Cell -> Radiant
background :: Functor f => (Radiant -> f Radiant) -> Cell -> f Cell
vertical :: Functor f => (Alignment Vertical -> f Alignment Vertical) -> Cell -> f Cell
horizontal :: Functor f => (Alignment Horizontal -> f Alignment Horizontal) -> Cell -> f Cell
rows :: Functor f => (Seq Seq Chunk Text -> f Seq Seq Chunk Text) -> Cell -> f Cell

-- | <a>mappend</a> combines two <a>Cell</a> horizontally so they are
--   side-by-side, left-to-right. The <a>_horizontal</a>, <a>_vertical</a>,
--   and <a>_background</a> fields are combined using their respective
--   <a>Monoid</a> instances. <a>mempty</a> uses the respective
--   <a>mempty</a> value for each field.

-- | Creates a blank <a>Cell</a> with the given background color and width;
--   useful for adding separators between columns.
separator :: Radiant -> Int -> Cell

-- | Create a table where each inner <a>Seq</a> is a row of cells, from
--   left to right. If necessary, blank cells are added to the end of a row
--   to ensure that each row has the same number of cells as the longest
--   row.
tableByRows :: Seq (Seq Cell) -> Box Vertical
rowToBoxV :: Box Horizontal -> Box Vertical
cellToBoxV :: Cell -> (Box Vertical, Alignment Horizontal, Radiant)
toBoxH :: (Box Vertical, Alignment Horizontal, Radiant) -> Box Horizontal
addWidthMap :: Seq (Seq (Box Vertical, b, c)) -> (Map Int (Int, Int), Seq (Seq (Box Vertical, b, c)))
padBoxV :: Map Int (Int, Int) -> Seq (Seq (Box Vertical, a, b)) -> Seq (Seq (Box Vertical, a, b))
widestCellMap :: Seq (Seq (Box Vertical)) -> Map Int (Int, Int)

-- | Create a table where each inner <a>Seq</a> is a column of cells, from
--   top to bottom. If necessary, blank cells are added to the end of a
--   column to ensure that each column has the same number of cells as the
--   longest column.
tableByColumns :: Seq (Seq Cell) -> Box Horizontal
rowToBoxH :: Box Vertical -> Box Horizontal
cellToBoxH :: Cell -> (Box Horizontal, Alignment Vertical, Radiant)
addHeightMap :: Seq (Seq (Box Horizontal, b, c)) -> (Map Int (Int, Int), Seq (Seq (Box Horizontal, b, c)))
tallestCellMap :: Seq (Seq (Box Horizontal)) -> Map Int (Int, Int)
padBoxH :: Map Int (Int, Int) -> Seq (Seq (Box Horizontal, a, b)) -> Seq (Seq (Box Horizontal, a, b))
toBoxV :: (Box Horizontal, Alignment Vertical, Radiant) -> Box Vertical

-- | Ensures that each inner <a>Seq</a> is the same length by adding the
--   given empty element where needed.
equalize :: a -> Seq (Seq a) -> Seq (Seq a)
mconcatSeq :: Monoid a => Seq a -> a

-- | Like <a>intersperse</a> in <a>Data.List</a>, but works on <a>Seq</a>.
intersperse :: a -> Seq a -> Seq a
instance GHC.Base.Monoid Rainbox.Core.Cell
instance GHC.Show.Show Rainbox.Core.Cell
instance GHC.Classes.Ord Rainbox.Core.Cell
instance GHC.Classes.Eq Rainbox.Core.Cell
instance GHC.Show.Show a => GHC.Show.Show (Rainbox.Core.Box a)
instance GHC.Classes.Ord a => GHC.Classes.Ord (Rainbox.Core.Box a)
instance GHC.Classes.Eq a => GHC.Classes.Eq (Rainbox.Core.Box a)
instance GHC.Show.Show a => GHC.Show.Show (Rainbox.Core.Payload a)
instance GHC.Classes.Ord a => GHC.Classes.Ord (Rainbox.Core.Payload a)
instance GHC.Classes.Eq a => GHC.Classes.Eq (Rainbox.Core.Payload a)
instance GHC.Show.Show Rainbox.Core.RodRows
instance GHC.Classes.Ord Rainbox.Core.RodRows
instance GHC.Classes.Eq Rainbox.Core.RodRows
instance GHC.Show.Show Rainbox.Core.Rod
instance GHC.Classes.Ord Rainbox.Core.Rod
instance GHC.Classes.Eq Rainbox.Core.Rod
instance GHC.Show.Show Rainbox.Core.Core
instance GHC.Classes.Ord Rainbox.Core.Core
instance GHC.Classes.Eq Rainbox.Core.Core
instance GHC.Show.Show Rainbox.Core.Width
instance GHC.Classes.Ord Rainbox.Core.Width
instance GHC.Classes.Eq Rainbox.Core.Width
instance GHC.Show.Show Rainbox.Core.Height
instance GHC.Classes.Ord Rainbox.Core.Height
instance GHC.Classes.Eq Rainbox.Core.Height
instance GHC.Show.Show Rainbox.Core.Vertical
instance GHC.Classes.Ord Rainbox.Core.Vertical
instance GHC.Classes.Eq Rainbox.Core.Vertical
instance GHC.Show.Show Rainbox.Core.Horizontal
instance GHC.Classes.Ord Rainbox.Core.Horizontal
instance GHC.Classes.Eq Rainbox.Core.Horizontal
instance Data.Traversable.Traversable Rainbox.Core.Alignment
instance Data.Foldable.Foldable Rainbox.Core.Alignment
instance GHC.Base.Functor Rainbox.Core.Alignment
instance GHC.Show.Show a => GHC.Show.Show (Rainbox.Core.Alignment a)
instance GHC.Classes.Ord a => GHC.Classes.Ord (Rainbox.Core.Alignment a)
instance GHC.Classes.Eq a => GHC.Classes.Eq (Rainbox.Core.Alignment a)
instance Rainbox.Core.UpDown (Rainbox.Core.Payload Rainbox.Core.Horizontal)
instance Rainbox.Core.UpDown (Rainbox.Core.Box Rainbox.Core.Horizontal)
instance Rainbox.Core.HasHeight (Rainbox.Core.Box Rainbox.Core.Horizontal)
instance Rainbox.Core.LeftRight (Rainbox.Core.Payload Rainbox.Core.Vertical)
instance Rainbox.Core.LeftRight (Rainbox.Core.Box Rainbox.Core.Vertical)
instance Rainbox.Core.HasWidth (Rainbox.Core.Box Rainbox.Core.Vertical)
instance Rainbox.Core.Orientation Rainbox.Core.Vertical
instance Rainbox.Core.Orientation Rainbox.Core.Horizontal
instance GHC.Base.Monoid (Rainbox.Core.Box a)
instance Rainbox.Core.HasHeight (Rainbox.Core.Box Rainbox.Core.Vertical)
instance Rainbox.Core.HasWidth (Rainbox.Core.Box Rainbox.Core.Horizontal)
instance Rainbox.Core.HasWidth (Rainbox.Core.Payload a)
instance Rainbox.Core.HasHeight (Rainbox.Core.Payload a)
instance Rainbox.Core.HasHeight Rainbox.Core.RodRows
instance Rainbox.Core.HasWidth Rainbox.Core.RodRows
instance Rainbox.Core.HasWidth Rainbox.Core.Rod
instance Rainbox.Core.HasWidth Rainbox.Core.Core
instance Rainbox.Core.HasHeight Rainbox.Core.Core
instance Rainbox.Core.HasWidth Rainbox.Core.Width
instance Rainbox.Core.HasWidth (Rainbow.Types.Chunk Data.Text.Internal.Text)
instance (Rainbox.Core.HasWidth a, Rainbox.Core.HasWidth b) => Rainbox.Core.HasWidth (Data.Either.Either a b)
instance Rainbox.Core.HasHeight Rainbox.Core.Height
instance Rainbox.Core.HasHeight (Rainbow.Types.Chunk a)
instance (Rainbox.Core.HasHeight a, Rainbox.Core.HasHeight b) => Rainbox.Core.HasHeight (Data.Either.Either a b)
instance GHC.Base.Monoid (Rainbox.Core.Alignment a)


-- | Typically to use Rainbox you will want these <tt>import</tt>s:
--   
--   <pre>
--   import qualified Data.Sequence as Seq
--   import Rainbow
--   import Rainbox
--   
--   -- and, for GHC before 7.10:
--   import Data.Monoid
--   </pre>
--   
--   Rainbox does not re-export anything from <a>Data.Sequence</a> or
--   <a>Rainbow</a> because I don't know if you want all those things
--   dumped into the same namespace.
--   
--   <a>Rainbox.Tutorial</a> wil get you started. <a>Rainbox.Core</a>
--   contains the implementation details, which you should not need to pay
--   attention to (if you do need to use <a>Rainbox.Core</a> for ordinary
--   usage of the library, that's a bug; please report it.)
module Rainbox

-- | Alignment. Used in conjunction with <a>Horizontal</a> and
--   <a>Vertical</a>, this determines how a payload aligns with the axis of
--   a <a>Box</a>.
data Alignment a

-- | Determines how a payload aligns with a horizontal axis.
data Horizontal

-- | Determines how a payload aligns with a vertical axis.
data Vertical

-- | Place this payload so that it is centered on the vertical axis or
--   horizontal axis.
center :: Alignment a

-- | Place this payload's left edge on the vertical axis.
left :: Alignment Vertical

-- | Place this payload's right edge on the vertical axis.
right :: Alignment Vertical

-- | Place this payload's top edge on the horizontal axis.
top :: Alignment Horizontal

-- | Place this payload's bottom edge on the horizontal axis.
bottom :: Alignment Horizontal

-- | Center horizontally; like <a>center</a>, but monomorphic.
centerH :: Alignment Horizontal

-- | Center vertically; like <a>center</a>, but monomorphic.
centerV :: Alignment Vertical

-- | A <a>Box</a> is the central building block. It consists of zero or
--   more payloads; each payload has the same orientation, which is either
--   <a>Horizontal</a> or <a>Vertical</a>. This orientation also determines
--   the orientation of the entire <a>Box</a>.
--   
--   A <a>Box</a> is a <a>Monoid</a> so you can combine them using the
--   usual monoid functions. For a <a>Box</a> <a>Vertical</a>, the leftmost
--   values added with <a>mappend</a> are at the top of the <a>Box</a>; for
--   a <a>Box</a> <a>Horizontal</a>, the leftmost values added with
--   <a>mappend</a> are on the left side of the <a>Box</a>.
data Box a

-- | This typeclass is responsible for transforming a <a>Box</a> into
--   Rainbow <a>Chunk</a> so they can be printed to your screen. This
--   requires adding appropriate whitespace with the right colors, as well
--   as adding newlines in the right places.
class Orientation a

-- | Builds a one-dimensional box of the given size; its single dimension
--   is parallel to the axis. When added to a box, it will insert blank
--   space of the given length. For a <a>Box</a> <a>Horizontal</a>, this
--   produces a horizontal line; for a <a>Box</a> <a>Vertical</a>, a
--   vertical line.
spacer :: Orientation a => Radiant -> Int -> Box a

-- | Builds a one-dimensional box of the given size; its single dimension
--   is perpendicular to the axis. This can be used to make a <a>Box</a>
--   <a>Vertical</a> wider or a <a>Box</a> <a>Horizontal</a> taller.
spreader :: Orientation a => Alignment a -> Int -> Box a

-- | Construct a box from a single <a>Chunk</a>.
fromChunk :: Alignment a -> Radiant -> Chunk Text -> Box a

-- | Construct a blank box. Useful for adding in background spacers. For
--   functions that build one-dimensional boxes, see <a>spacer</a> and
--   <a>spreader</a>.
blank :: Alignment a -> Radiant -> Height -> Width -> Box a

-- | Wrap a <a>Box</a> in another <a>Box</a>. Useful for changing a
--   <a>Horizontal</a> <a>Box</a> to a <a>Vertical</a> one, or simply for
--   putting a <a>Box</a> inside another one to control size and background
--   color.
wrap :: Orientation a => Alignment b -> Radiant -> Box a -> Box b

-- | Convert a box to a <a>Seq</a> of <a>Chunk</a> in preparation for
--   rendering. Use <a>toList</a> to convert the <a>Seq</a> of <a>Chunk</a>
--   to a list so that you can print it using the functions in
--   <a>Rainbow</a>.
render :: Orientation a => Box a -> Seq (Chunk Text)

-- | A single cell in a spreadsheet-like grid.
data Cell
Cell :: Seq (Seq (Chunk Text)) -> Alignment Horizontal -> Alignment Vertical -> Radiant -> Cell

-- | The cell can have multiple rows of text; there is one <a>Seq</a> for
--   each row of text.
[_rows] :: Cell -> Seq (Seq (Chunk Text))

-- | How this <a>Cell</a> should align compared to other <a>Cell</a> in its
--   row.
[_horizontal] :: Cell -> Alignment Horizontal

-- | How this <a>Cell</a> should align compared to other <a>Cell</a> in its
--   column.
[_vertical] :: Cell -> Alignment Vertical

-- | Background color for this cell. The background in the individual
--   <a>Chunk</a> in the <tt>cellRows</tt> are not affected by
--   <tt>cellBackground</tt>; instead, <tt>cellBackground</tt> determines
--   the color of necessary padding that will be added so that the cells
--   make a uniform table.
[_background] :: Cell -> Radiant
rows :: Functor f => (Seq Seq Chunk Text -> f Seq Seq Chunk Text) -> Cell -> f Cell
horizontal :: Functor f => (Alignment Horizontal -> f Alignment Horizontal) -> Cell -> f Cell
vertical :: Functor f => (Alignment Vertical -> f Alignment Vertical) -> Cell -> f Cell
background :: Functor f => (Radiant -> f Radiant) -> Cell -> f Cell

-- | Create a table where each inner <a>Seq</a> is a row of cells, from
--   left to right. If necessary, blank cells are added to the end of a row
--   to ensure that each row has the same number of cells as the longest
--   row.
tableByRows :: Seq (Seq Cell) -> Box Vertical

-- | Create a table where each inner <a>Seq</a> is a column of cells, from
--   top to bottom. If necessary, blank cells are added to the end of a
--   column to ensure that each column has the same number of cells as the
--   longest column.
tableByColumns :: Seq (Seq Cell) -> Box Horizontal

-- | Creates a blank <a>Cell</a> with the given background color and width;
--   useful for adding separators between columns.
separator :: Radiant -> Int -> Cell

-- | Like <a>intersperse</a> in <a>Data.List</a>, but works on <a>Seq</a>.
intersperse :: a -> Seq a -> Seq a


-- | The Rainbox tutorial
--   
--   Rainbox helps you create arrangements of (possibly) colorful text
--   boxes. This module contains a tutorial. Typically the <a>Rainbox</a>
--   module contains all you need. There is also a <a>Rainbox.Core</a>
--   module which contains all the innards of Rainbox, but ordinarily you
--   won't need it.
--   
--   The basic building block of Rainbox is known as a <tt>core</tt>. A
--   core is either a single <tt>Chunk</tt> or a blank box of arbitrary
--   size. A core made of a single <tt>Chunk</tt> should not contain any
--   newlines. Leave newline handling up to Rainbox. However, Rainbox will
--   not check to ensure that your <tt>Chunk</tt> does not contain any
--   newline characters. If it does contain newlines, your boxes will not
--   look right. Also, Rainbox needs to know how wide your <tt>Chunk</tt>
--   are, in columns. To measure width, Rainbox simply counts the number of
--   characters in the <tt>Chunk</tt>. Therefore, if you need accented
--   characters, be sure to use a single character, not composed
--   characters. That is, to get á, use U+00E1, not U+00B4 and U+0061.
--   
--   Many things in Rainbox have height and width. Both the height and
--   width of an object can be zero, but never less than zero. A
--   <tt>core</tt> made from a <tt>Chunk</tt> always has a height of 1, and
--   its width is equal to the number of characters in the <a>Text</a>s
--   that make up the <tt>Chunk</tt>. A <tt>core</tt> made from a blank box
--   has the height and width that you give it, though neither its height
--   nor its width is ever smaller than zero.
--   
--   The next biggest building block after the <tt>core</tt> is
--   <tt>payload</tt>. There are two different types of payloads: vertical
--   payloads and horizontal ones. A vertical payload aligns itself next to
--   other vertical payloads on a vertical axis, creating a chain of
--   payloads. The vertical payload also has an alignment. The alignment
--   determines whether the payload lines up along the axis on its left
--   side, right side, or in the center of the payload.
--   
--   The vertical payload also has a background color, which has type
--   <tt>Radiant</tt>. Think of the background color as extending
--   infinitely from both the left and right side of the vertical payload.
--   When the vertical payload is combined with other vertical payloads
--   into a <tt>Box</tt> <tt>Vertical</tt>, this background color is used
--   as necessary so that the <tt>Box</tt> <tt>Vertical</tt> forms a
--   rectangle.
--   
--   The horizontal payload is similar to the vertical payload, but the
--   axis is horizontal rather than vertical. The alignment determines
--   whether the payload aligns the axis along the top, center, or bottom
--   of the payload. A horizontal payload also contains a background color;
--   it extends infinitely from both the top and bottom of the horizontal
--   payload.
--   
--   Finally, the biggest building block of Rainbox is the box. There are
--   two types of boxes: a <tt>Box</tt> <tt>Horizontal</tt>, which holds
--   zero or more horizontal payloads, and a <tt>Box</tt>
--   <tt>Vertical</tt>, which holds zero or more vertical payloads. Each
--   kind of box is a <a>Monoid</a>, so you can combine it using the usual
--   monoid functions. So, to give a visual, a <tt>Box</tt>
--   <tt>Vertical</tt> with five payloads might look like this:
--   
--   <pre>
--   -- function: <a>box1</a>
--   
--              V Vertical axis
--   
--              +----+
--              | v1 |
--              |    |
--              +----+--------+
--              |     v2      |
--              |             |
--     +--------+-------------+
--     |        |
--     |  v3    |
--     |        |
--     |        |
--     +--------+----------+
--              |    v4    |
--         +----+----+-----+
--         | v5      |
--         |         |
--         +---------+
--   </pre>
--   
--   Each payload is marked in the middle with <tt>v1</tt>, <tt>v2</tt>,
--   etc. Note how each payload has a different size. <tt>v1</tt> and
--   <tt>v2</tt>, and <tt>v4</tt> have a <tt>left</tt> alignment, as their
--   left edge is lined up with the vertical axis. <tt>v3</tt> has a
--   <tt>right</tt> alignment. <tt>v5</tt> has a <tt>center</tt> alignment.
--   Think of each payload has having a background color extending
--   infinitely off of its left and right sides. These five payloads put
--   together make a <tt>Box</tt> <tt>Vertical</tt>. Since <tt>Box</tt>
--   <tt>Vertical</tt> is a monoid, you can combine various <tt>Box</tt>
--   <tt>Vertical</tt>. Indeed, the pictured <tt>Box</tt> <tt>Vertical</tt>
--   can be built only by combining smaller <tt>Box</tt> <tt>Vertical</tt>,
--   as when you create payloads they are always given to you as a single
--   payload wrapped in a <tt>Box</tt> <tt>Vertical</tt>.
--   
--   Now, you want to render your <tt>Box</tt> <tt>Vertical</tt>. You use
--   the <tt>render</tt> function, which makes a sequence of Rainbow
--   <tt>Chunk</tt>. This turns your <tt>Box</tt> <tt>Vertical</tt> into a
--   nice rectangle for on-screen rendering:
--   
--   <pre>
--   -- function: <a>renderBox1</a>
--   
--     +--------+----+--------+
--     |        | v1 |        |
--     |        |    |        |
--     +--------+----+--------+
--     |        |     v2      |
--     |        |             |
--     +--------+-------------+
--     |        |             |
--     |  v3    |             |
--     |        |             |
--     |        |             |
--     +--------+----------+--+
--     |        |    v4    |  |
--     +---+----+----+-----+--+
--     |   | v5      |        |
--     |   |         |        |
--     +---+---------+--------+
--   </pre>
--   
--   The spaces to the left and right of each payload are filled in with
--   the appropriate background color, which is the background color of the
--   adjoining payload.
--   
--   What if you want to place the <tt>Box</tt> <tt>Vertical</tt> alongside
--   another box? If you want to put it next to another <tt>Box</tt>
--   <tt>Vertical</tt>, just use <a>mappend</a> or <a>&lt;&gt;</a>. But
--   what if you want to put it next to a <tt>Box</tt> <tt>Horizontal</tt>?
--   Let's suppose you have a <tt>Box</tt> <tt>Horizontal</tt> that looks
--   like this:
--   
--   <pre>
--   -- function: <a>box2</a>
--   
--                           +----+
--                           | h1 |
--                           |    |
--   Horizontal Axis &gt;       +----+----------+
--                                |          |
--                                |   h2     |
--                                |          |
--                                +----------+
--   </pre>
--   
--   The <tt>h1</tt> payload has alignment <tt>bottom</tt>, because its
--   bottom edge is lined up along the horizontal axis. The <tt>h2</tt>
--   payload has alignment <tt>top</tt>. You want to connect this
--   <tt>Box</tt> <tt>Horizontal</tt> with the <tt>Box</tt>
--   <tt>Vertical</tt> made above. You can't connect them directly because
--   they are different types. You can, however, take a complete
--   <tt>Box</tt> and wrap it inside another <tt>Box</tt>. This allows you
--   to wrap a <tt>Box</tt> <tt>Vertical</tt> inside of a <tt>Box</tt>
--   <tt>Horizontal</tt>, and vice versa, or even wrap a <tt>Box</tt>
--   <tt>Horizontal</tt> inside of another <tt>Box</tt>
--   <tt>Horizontal</tt>. You do this with the <tt>wrap</tt> function,
--   which is applied to the alignment for the new box, its background
--   color, and the box you want to wrap. ao, let's say you take the
--   <tt>Box</tt> <tt>Vertical</tt> created above and wrap it inside a
--   <tt>Box</tt> <tt>Horizontal</tt> with <tt>top</tt> alignment and a
--   background color, and then you combine it with the <tt>Box</tt>
--   <tt>Horizontal</tt> created above. The result:
--   
--   <pre>
--   -- function: <a>box3</a>
--   
--                            +----+
--                            | h1 |
--                            |    |
--     +--------+----+--------+----+----------+
--     |        | v1 |        |    |          |
--     |        |    |        |    |    h2    |
--     +--------+----+--------+    |          |
--     |        |     v2      |    +----------+
--     |        |             |
--     +--------+-------------+
--     |        |             |
--     |  v3    |             |
--     |        |             |
--     |        |             |
--     +--------+----------+--+
--     |        |    v4    |  |
--     +---+----+----+-----+--+
--     |   | v5      |        |
--     |   |         |        |
--     +---+---------+--------+
--   </pre>
--   
--   The old <tt>Box</tt> <tt>Vertical</tt>, which is now wrapped in a
--   <tt>Box</tt> <tt>Horizontal</tt>, now has a background color which
--   extends infinitely from the top and bottom of the box. It is now just
--   a payload inside of the <tt>Box</tt> <tt>Horizontal</tt>. The other
--   two payloads in the <tt>Box</tt> <tt>Horizontal</tt>, <tt>h1</tt> and
--   <tt>h2</tt>, also have background colors extending from their tops and
--   bottoms.
--   
--   So, when you render this <tt>Box</tt> <tt>Horizontal</tt> with
--   <tt>render</tt>, you get this:
--   
--   <pre>
--   -- function: <a>renderBox3</a>
--   
--     +----------------------+----+----------+
--     |                      | h1 |          |
--     |                      |    |          |
--     +--------+----+--------+----+----------+
--     |        | v1 |        |    |          |
--     |        |    |        |    |    h2    |
--     +--------+----+--------+    |          |
--     |        |     v2      |    +----------+
--     |        |             |    |          |
--     +--------+-------------+    |          |
--     |        |             |    |          |
--     |  v3    |             |    |          |
--     |        |             |    |          |
--     |        |             |    |          |
--     +--------+----------+--+    |          |
--     |        |    v4    |  |    |          |
--     +---+----+----+-----+--+    |          |
--     |   | v5      |        |    |          |
--     |   |         |        |    |          |
--     +---+---------+--------+----+----------+
--   </pre>
--   
--   The area above the old <tt>Box</tt> <tt>Vertical</tt> has the
--   background color that we used in the application of <tt>convert</tt>.
--   The area below the <tt>h1</tt> payload has its background color, and
--   the area above and below the <tt>h2</tt> payload has its background
--   color.
--   
--   What if you just want to create an empty space? You can create entire
--   blank boxes with <tt>blank</tt>, but often it is enough to use
--   <tt>spacer</tt>, which gives you a one-dimensional <tt>Box</tt>
--   <tt>Horizontal</tt> or <tt>Box</tt> <tt>Vertical</tt>. If you are
--   creating a <tt>Box</tt> <tt>Horizontal</tt>, <tt>spacer</tt> gives you
--   a box with width, but no height; for a <tt>Box</tt> <tt>Vertical</tt>,
--   you get a box with height, but no width. So, to return to the example
--   <tt>Box</tt> <tt>Horizontal</tt>, let's say you want to add a blank
--   space a few columns wide on the right side. You <a>mappend</a> a
--   <tt>Box</tt> <tt>Horizontal</tt> created with <tt>spacer</tt> to get
--   this:
--   
--   <pre>
--   -- function: <a>box4</a>
--   
--                           +----+
--                           | h1 |
--                           |    |
--   Horizontal Axis &gt;       +----+----------+--+
--                                |          |
--                                |   h2     |
--                                |          |
--                                +----------+
--   </pre>
--   
--   On the right side you now have a payload with width, but no height.
--   But it does have a background color. So when you <tt>render</tt> the
--   box, you get this:
--   
--   <pre>
--   -- function: <a>renderBox4</a>
--   
--                           +----+----------+--+
--                           | h1 |          |  |
--                           |    |          |  |
--                           +----+----------+  |
--                           |    |          |  |
--                           |    |   h2     |  |
--                           |    |          |  |
--                           +----+----------+--+
--   </pre>
--   
--   You can also use <tt>spreader</tt> to make a <tt>Box</tt>
--   <tt>Horizontal</tt> taller or a <tt>Box</tt> <tt>Vertical</tt> wider.
--   <tt>spreader</tt> creates a one-dimensional <tt>Box</tt> that is
--   perpendicular to the axis. Pay attention to the alignment of the
--   <tt>spreader</tt> as this will determine how your box expands. Let's
--   say I want to take the <tt>Box</tt> that contains the <tt>h1</tt> and
--   <tt>h2</tt> payloads as created above, but I also want to make sure
--   the box is at least 12 rows tall. To do this, <a>mappend</a> a
--   <tt>spreader</tt> that is 12 rows tall. The result upon
--   <tt>render</tt>ing is:
--   
--   <pre>
--                           
--   -- functions: <a>box5</a> <a>renderBox5</a>
--   
--                           +----+----------+--+
--                           |    |          |  |
--                           +----+          |  |
--                           | h1 |          |  |
--                           |    |          |  |
--                           +----+----------+  |
--                           |    |          |  |
--                           |    |   h2     |  |
--                           |    |          |  |
--                           |    +----------+  |
--                           |    |          |  |
--                           +----+----------+--+
--   </pre>
--   
--   Those are the basics of the Rainbox model, which should be enough to
--   get you started. Also helpful are the <tt>tableByRows</tt> and
--   <tt>tableByColumns</tt> functions, which will help you build a simple
--   grid that resembles a spreadsheet; see its documentation for hints to
--   get started with that. You will also find an example using the
--   <tt>tableByRows</tt>, as well as code to produce all of the examples
--   shown above, in the source code below.
--   
--   <h2>Why the use of <a>Seq</a> everywhere, rather than lists?</h2>
--   
--   Rainbox uses <a>Seq</a> from <a>Data.Sequence</a> because lists can be
--   infinite. Practically every function in Rainbox will not accept
--   infinite inputs, because Rainbox needs to know exactly how long and
--   wide various payloads and boxes are in order to line them up
--   correctly. Use of the <a>Seq</a> most accurately reflects the fact
--   that Rainbox does not work on infinite inputs.
module Rainbox.Tutorial

-- | Create a <tt>Box</tt> for the given text. The default foreground and
--   background colors of the terminal are used for the <a>Text</a>; the
--   given background is used as the background color for any added
--   padding.
textBox :: Radiant -> Text -> Box a

-- | Centers the given <tt>Box</tt> within a larger <tt>Box</tt> that has
--   the given height and width and background color. The larger
--   <tt>Box</tt> has the given <tt>Alignment</tt>.
within :: Orientation a => Alignment a -> Int -> Int -> Radiant -> Box a -> Box a

-- | Puts the given text in the center of a box. The resulting box is
--   center aligned.
textWithin :: Orientation a => Alignment a -> Int -> Int -> Radiant -> Radiant -> Text -> Box a
box1 :: Box Vertical
renderBox1 :: IO ()
box2 :: Box Horizontal
renderBox2 :: IO ()
box3 :: Box Horizontal
renderBox3 :: IO ()
box4 :: Box Horizontal
renderBox4 :: IO ()
box5 :: Box Horizontal
renderBox5 :: IO ()
data Line
Red :: Line
Blue :: Line
Orange :: Line
Green :: Line
Yellow :: Line
Silver :: Line
data Station
Station :: Text -> [Line] -> [Text] -> Bool -> Station
[name] :: Station -> Text
[metroLines] :: Station -> [Line]
[address] :: Station -> [Text]
[underground] :: Station -> Bool
nameCell :: Radiant -> Text -> Cell
linesCell :: Radiant -> [Line] -> Cell
lineRow :: Radiant -> Line -> Seq (Chunk Text)
addressCell :: Radiant -> [Text] -> Cell
undergroundCell :: Radiant -> Bool -> Cell
stations :: [Station]
coloredBack :: Radiant

-- | Converts a <a>Station</a> to a list of <tt>Cell</tt>.
stationRow :: Radiant -> Station -> [Cell]
allStationRows :: [[Cell]]
verticalStationTable :: Box Vertical
renderVerticalStationTable :: IO ()
stationColumn :: Station -> [Cell]
allStationColumns :: [[Cell]]
horizontalStationTable :: Box Horizontal
renderHorizontalStationTable :: IO ()
instance GHC.Enum.Enum Rainbox.Tutorial.Line
instance GHC.Show.Show Rainbox.Tutorial.Line
instance GHC.Classes.Ord Rainbox.Tutorial.Line
instance GHC.Classes.Eq Rainbox.Tutorial.Line
