module Data.Rope.Body
( Body
, Offset(..)
, Chunk(..)
, measureBody
, consBody
, snocBody
, packBody
) where
import Prelude hiding (null, length)
import Data.FingerTree (FingerTree,(<|),(|>),Measured,measure,empty, singleton)
import Data.Data
import Data.Monoid
import Data.ByteString (ByteString, null, length)
newtype Offset = Offset { getOffset :: Int } deriving (Eq,Ord,Num,Show,Read,Enum,Data,Typeable)
instance Monoid Offset where
mempty = 0
mappend = (+)
newtype Chunk = Chunk { unchunk :: ByteString } deriving (Eq,Ord,Show,Read,Data,Typeable)
instance Measured Offset Chunk where
measure = Offset . length . unchunk
type Body = FingerTree Offset Chunk
measureBody :: Measured Offset a => FingerTree Offset a -> Int
measureBody = getOffset . measure
consBody :: ByteString -> Body -> Body
b `consBody` t | null b = t
| otherwise = Chunk b <| t
snocBody :: Body -> ByteString -> Body
t `snocBody` b | null b = t
| otherwise = t |> Chunk b
packBody :: ByteString -> FingerTree Offset Chunk
packBody b | null b = empty
| otherwise = singleton (Chunk b)