wkt-geom-0.0.5: src/Data/Internal/Wkt/Line.hs
module Data.Internal.Wkt.Line
( line
, lineString
, multiLineString
, emptyLine
, emptyMultiLine
, commandPoint
) where
import Control.Applicative ((<|>))
import qualified Data.Geospatial as Geospatial
import qualified Data.LineString as LineString
import qualified Data.Sequence as Sequence
import qualified Text.Trifecta as Trifecta
import qualified Data.Internal.Wkt.Common as Wkt
import qualified Data.Internal.Wkt.Point as Point
lineString :: Trifecta.Parser Geospatial.GeoLine
lineString = do
_ <- Trifecta.string "linestring"
_ <- Trifecta.spaces
(Trifecta.string "empty" >> pure emptyLine) <|> nonEmptyLines
nonEmptyLines :: Trifecta.Parser Geospatial.GeoLine
nonEmptyLines =
(Trifecta.string "zm" >> Geospatial.GeoLine <$> line Point.justPointsXYZM)
<|> (Trifecta.string "z" >> Geospatial.GeoLine <$> line Point.justPointsXYZ)
<|> Geospatial.GeoLine <$> line Point.justPointsXY
multiLineString :: Trifecta.Parser Geospatial.GeoMultiLine
multiLineString = do
_ <- Trifecta.string "multilinestring"
_ <- Trifecta.spaces
x <- Wkt.emptySet <|> nonEmptyMultiLines
pure $ Geospatial.GeoMultiLine x
nonEmptyMultiLines :: Trifecta.Parser (Sequence.Seq (LineString.LineString Geospatial.GeoPositionWithoutCRS))
nonEmptyMultiLines =
(Trifecta.string "zm" >> manyLines Point.justPointsXYZM)
<|> (Trifecta.string "z" >> manyLines Point.justPointsXYZ)
<|> manyLines Point.justPointsXY
manyLines :: Trifecta.Parser Geospatial.GeoPositionWithoutCRS -> Trifecta.Parser (Sequence.Seq (LineString.LineString Geospatial.GeoPositionWithoutCRS))
manyLines pointParser = do
_ <- Trifecta.spaces >> Trifecta.char '('
x <- line pointParser
xs <- Trifecta.many (Trifecta.char ',' >> Trifecta.spaces >> line pointParser)
_ <- Trifecta.char ')' >> Trifecta.spaces
pure $ x Sequence.:<| Sequence.fromList xs
line :: Trifecta.Parser Geospatial.GeoPositionWithoutCRS -> Trifecta.Parser (LineString.LineString Geospatial.GeoPositionWithoutCRS)
line pointParser = do
_ <- Trifecta.spaces >> Trifecta.char '(' >> Trifecta.spaces
first <- pointParser
second <- commandPoint pointParser
rest <- Trifecta.many (commandPoint pointParser)
_ <- Trifecta.char ')' >> Trifecta.spaces
pure $ LineString.makeLineString first second (Sequence.fromList rest)
commandPoint :: Trifecta.Parser Geospatial.GeoPositionWithoutCRS -> Trifecta.Parser Geospatial.GeoPositionWithoutCRS
commandPoint pointParser = do
_ <- Trifecta.char ','
_ <- Trifecta.spaces
pointParser
emptyLine :: Geospatial.GeoLine
emptyLine = Geospatial.GeoLine $ LineString.makeLineString Geospatial.GeoEmpty Geospatial.GeoEmpty Sequence.empty
emptyMultiLine :: Geospatial.GeoMultiLine
emptyMultiLine = Geospatial.mergeGeoLines Sequence.empty