{-# OPTIONS_HADDOCK hide #-} -- | Breaks a text up into a list of texts at newline chars. The maximum -- length or word count of a element of the list is given by parameters. -- So the element may contain multiple newlines. module Language.Hanspell.TextLines ( linesByLength , linesByWordCount ) where import Data.List -- | Line-wrapped break up to character count. linesByLength :: Int -> String -> [String] linesByLength maxChars = map unlines . reverse . map reverse . merge . foldl' mergeLine (maxChars,0,[],[]) . lines where mergeLine :: (Int,Int,[String],[[String]]) -> String -> (Int,Int,[String],[[String]]) mergeLine (maxChars,headsLength,heads,merged) aLine = if lineLength + headsLength > maxChars && not (null heads) then (maxChars,lineLength,[aLine],heads:merged) else (maxChars,lineLength + headsLength,aLine:heads,merged) where lineLength = length aLine + 1 -- | Line-wrapped break up to word count. linesByWordCount :: Int -> String -> [String] linesByWordCount maxWords = map unlines . reverse . map reverse . merge . foldl' mergeLine (maxWords,0,[],[]) . lines where mergeLine :: (Int,Int,[String],[[String]]) -> String -> (Int,Int,[String],[[String]]) mergeLine (maxWords,headsWords,heads,merged) aLine = if xWords + headsWords > maxWords && not (null heads) then (maxWords,xWords,[aLine],heads:merged) else (maxWords,xWords + headsWords,aLine:heads,merged) where xWords = length (words aLine) -- Add the heads left to the merged heads list merge (_,_,heads,merged) = if null heads then merged else heads:merged