{-# LANGUAGE DeriveAnyClass #-}
{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE OverloadedStrings #-}
{-# LANGUAGE TemplateHaskell #-}
{-# LANGUAGE NoImplicitPrelude #-}
module Data.Geospatial.Internal.GeoFeature
(
GeoFeature (..),
bbox,
geometry,
properties,
featureId,
reWrapGeometry,
)
where
import Control.Applicative ((<$>), (<*>))
import Control.DeepSeq
import Control.Lens (makeLenses)
import Control.Monad (mzero)
import Data.Aeson
( FromJSON (..),
ToJSON (..),
Value (..),
object,
(.:),
(.:?),
(.=),
)
import Data.Geospatial.Internal.BasicTypes
import Data.Geospatial.Internal.Geometry
import Data.Geospatial.Internal.Geometry.Aeson
import Data.List ((++))
import Data.Maybe (Maybe)
import Data.Text (Text)
import GHC.Generics (Generic)
import Prelude (Eq (..), Show, ($))
data GeoFeature a = GeoFeature
{ forall a. GeoFeature a -> Maybe BoundingBoxWithoutCRS
_bbox :: Maybe BoundingBoxWithoutCRS,
forall a. GeoFeature a -> GeospatialGeometry
_geometry :: GeospatialGeometry,
forall a. GeoFeature a -> a
_properties :: a,
forall a. GeoFeature a -> Maybe FeatureID
_featureId :: Maybe FeatureID
}
deriving (Int -> GeoFeature a -> ShowS
[GeoFeature a] -> ShowS
GeoFeature a -> String
(Int -> GeoFeature a -> ShowS)
-> (GeoFeature a -> String)
-> ([GeoFeature a] -> ShowS)
-> Show (GeoFeature a)
forall a. Show a => Int -> GeoFeature a -> ShowS
forall a. Show a => [GeoFeature a] -> ShowS
forall a. Show a => GeoFeature a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Show a => Int -> GeoFeature a -> ShowS
showsPrec :: Int -> GeoFeature a -> ShowS
$cshow :: forall a. Show a => GeoFeature a -> String
show :: GeoFeature a -> String
$cshowList :: forall a. Show a => [GeoFeature a] -> ShowS
showList :: [GeoFeature a] -> ShowS
Show, GeoFeature a -> GeoFeature a -> Bool
(GeoFeature a -> GeoFeature a -> Bool)
-> (GeoFeature a -> GeoFeature a -> Bool) -> Eq (GeoFeature a)
forall a. Eq a => GeoFeature a -> GeoFeature a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. Eq a => GeoFeature a -> GeoFeature a -> Bool
== :: GeoFeature a -> GeoFeature a -> Bool
$c/= :: forall a. Eq a => GeoFeature a -> GeoFeature a -> Bool
/= :: GeoFeature a -> GeoFeature a -> Bool
Eq, (forall x. GeoFeature a -> Rep (GeoFeature a) x)
-> (forall x. Rep (GeoFeature a) x -> GeoFeature a)
-> Generic (GeoFeature a)
forall x. Rep (GeoFeature a) x -> GeoFeature a
forall x. GeoFeature a -> Rep (GeoFeature a) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall a x. Rep (GeoFeature a) x -> GeoFeature a
forall a x. GeoFeature a -> Rep (GeoFeature a) x
$cfrom :: forall a x. GeoFeature a -> Rep (GeoFeature a) x
from :: forall x. GeoFeature a -> Rep (GeoFeature a) x
$cto :: forall a x. Rep (GeoFeature a) x -> GeoFeature a
to :: forall x. Rep (GeoFeature a) x -> GeoFeature a
Generic, GeoFeature a -> ()
(GeoFeature a -> ()) -> NFData (GeoFeature a)
forall a. NFData a => GeoFeature a -> ()
forall a. (a -> ()) -> NFData a
$crnf :: forall a. NFData a => GeoFeature a -> ()
rnf :: GeoFeature a -> ()
NFData)
reWrapGeometry :: GeoFeature a -> GeospatialGeometry -> GeoFeature a
reWrapGeometry :: forall a. GeoFeature a -> GeospatialGeometry -> GeoFeature a
reWrapGeometry (GeoFeature Maybe BoundingBoxWithoutCRS
bbox GeospatialGeometry
_ a
props Maybe FeatureID
fId) GeospatialGeometry
geom = Maybe BoundingBoxWithoutCRS
-> GeospatialGeometry -> a -> Maybe FeatureID -> GeoFeature a
forall a.
Maybe BoundingBoxWithoutCRS
-> GeospatialGeometry -> a -> Maybe FeatureID -> GeoFeature a
GeoFeature Maybe BoundingBoxWithoutCRS
bbox GeospatialGeometry
geom a
props Maybe FeatureID
fId
makeLenses ''GeoFeature
instance (FromJSON a) => FromJSON (GeoFeature a) where
parseJSON :: Value -> Parser (GeoFeature a)
parseJSON (Object Object
obj) = do
objType <- Object
obj Object -> Key -> Parser Text
forall a. FromJSON a => Object -> Key -> Parser a
.: Key
"type"
if objType /= ("Feature" :: Text)
then mzero
else
GeoFeature
<$> obj .:? "bbox"
<*> obj .: "geometry"
<*> obj .: "properties"
<*> obj .:? "id"
parseJSON Value
_ = Parser (GeoFeature a)
forall a. Parser a
forall (m :: * -> *) a. MonadPlus m => m a
mzero
instance (ToJSON a) => ToJSON (GeoFeature a) where
toJSON :: GeoFeature a -> Value
toJSON (GeoFeature Maybe BoundingBoxWithoutCRS
bbox' GeospatialGeometry
geom a
props Maybe FeatureID
featureId') = [Pair] -> Value
object ([Pair] -> Value) -> [Pair] -> Value
forall a b. (a -> b) -> a -> b
$ [Pair]
baseAttributes [Pair] -> [Pair] -> [Pair]
forall a. [a] -> [a] -> [a]
++ Text -> Maybe BoundingBoxWithoutCRS -> [Pair]
forall a. ToJSON a => Text -> Maybe a -> [Pair]
optAttributes Text
"bbox" Maybe BoundingBoxWithoutCRS
bbox' [Pair] -> [Pair] -> [Pair]
forall a. [a] -> [a] -> [a]
++ Text -> Maybe FeatureID -> [Pair]
forall a. ToJSON a => Text -> Maybe a -> [Pair]
optAttributes Text
"id" Maybe FeatureID
featureId'
where
baseAttributes :: [Pair]
baseAttributes = [Key
"type" Key -> Text -> Pair
forall v. ToJSON v => Key -> v -> Pair
forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
.= (Text
"Feature" :: Text), Key
"properties" Key -> a -> Pair
forall v. ToJSON v => Key -> v -> Pair
forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
.= a
props, Key
"geometry" Key -> GeospatialGeometry -> Pair
forall v. ToJSON v => Key -> v -> Pair
forall e kv v. (KeyValue e kv, ToJSON v) => Key -> v -> kv
.= GeospatialGeometry
geom]