{-# language DeriveTraversable #-}
{-# language DeriveDataTypeable #-}
{-# language DeriveGeneric #-}
{-# language DeriveAnyClass #-}
{-# language TypeFamilies #-}
{-# language ViewPatterns #-}

module CodeWorld.Tasks.Picture (
  ReifyPicture(..),
  Picture(..),
  share,
  toInterface,
  innerPicture,
  hasInnerPicture,
  rectangle,
  thickRectangle,
  solidRectangle,
  circle,
  thickCircle,
  solidCircle,
  arc,
  sector,
  thickArc,
  curve,
  thickCurve,
  closedCurve,
  thickClosedCurve,
  solidClosedCurve,
  polyline,
  thickPolyline,
  polygon,
  thickPolygon,
  solidPolygon,
  lettering,
  styledLettering,
  colored,
  coloured,
  translated,
  scaled,
  dilated,
  rotated,
  reflected,
  clipped,
  pictures,
  (&),
  coordinatePlane,
  codeWorldLogo,
  blank,
  isIn,
  ) where


import Control.DeepSeq                  (NFData)
import Data.Data                        (Data, Typeable)
import Data.Foldable                    (toList)
import Data.IntMap                      (IntMap, Key)
import Data.List.Extra                  (headDef)
import Data.Reify                       (Graph(..), MuRef(..), reifyGraph)
import Data.Text                        (Text)
import Data.Tuple.Extra                 (both)
import Data.Generics.Uniplate.Data      (children)
import GHC.Generics                     (Generic)
import qualified Data.IntMap            as IM
import qualified Data.Text              as T

import qualified CodeWorld.Tasks.API    as API
import CodeWorld.Tasks.Color            (Color)
import CodeWorld.Tasks.Types            (Font, TextStyle)
import CodeWorld.Tasks.VectorSpace (
  Point,
  dilatedPoint,
  vectorDifference,
  rotatedPoint,
  crossProduct,
  dotProduct,
  scaledPoint,
  reflectedPoint,
  vectorLength
  )


{-|
Basic syntax tree type of the CodeWorld API.
Each API function has a corresponding constructor.

The type variable is necessary for CSE detection via [Reify](https://hackage.haskell.org/package/data-reify).
The method replaces subexpressions with number ids, so we need to be flexible in the wrapped type.
-}
data ReifyPicture a
  = Rectangle Double Double
  | ThickRectangle Double Double Double
  | SolidRectangle Double Double
  | Circle Double
  | ThickCircle Double Double
  | SolidCircle Double
  | Polygon [Point]
  | SolidPolygon [Point]
  | ThickPolygon Double [Point]
  | Polyline [Point]
  | ThickPolyline Double [Point]
  | Sector Double Double Double
  | Arc Double Double Double
  | ThickArc Double Double Double Double
  | Curve [Point]
  | ThickCurve Double [Point]
  | ClosedCurve [Point]
  | SolidClosedCurve [Point]
  | ThickClosedCurve Double [Point]
  | Lettering Text
  | StyledLettering TextStyle Font Text
  | Color Color a
  | Translate Double Double a
  | Scale Double Double a
  | Dilate Double a
  | Rotate Double a
  | Reflect Double a
  | Clip Double Double a
  | Pictures [a]
  | And a a
  | CoordinatePlane
  | 
  | Blank
  deriving (Int -> ReifyPicture a -> ShowS
[ReifyPicture a] -> ShowS
ReifyPicture a -> String
(Int -> ReifyPicture a -> ShowS)
-> (ReifyPicture a -> String)
-> ([ReifyPicture a] -> ShowS)
-> Show (ReifyPicture a)
forall a. Show a => Int -> ReifyPicture a -> ShowS
forall a. Show a => [ReifyPicture a] -> ShowS
forall a. Show a => ReifyPicture a -> String
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: forall a. Show a => Int -> ReifyPicture a -> ShowS
showsPrec :: Int -> ReifyPicture a -> ShowS
$cshow :: forall a. Show a => ReifyPicture a -> String
show :: ReifyPicture a -> String
$cshowList :: forall a. Show a => [ReifyPicture a] -> ShowS
showList :: [ReifyPicture a] -> ShowS
Show, (forall m. Monoid m => ReifyPicture m -> m)
-> (forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m)
-> (forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m)
-> (forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b)
-> (forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b)
-> (forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b)
-> (forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b)
-> (forall a. (a -> a -> a) -> ReifyPicture a -> a)
-> (forall a. (a -> a -> a) -> ReifyPicture a -> a)
-> (forall a. ReifyPicture a -> [a])
-> (forall a. ReifyPicture a -> Bool)
-> (forall a. ReifyPicture a -> Int)
-> (forall a. Eq a => a -> ReifyPicture a -> Bool)
-> (forall a. Ord a => ReifyPicture a -> a)
-> (forall a. Ord a => ReifyPicture a -> a)
-> (forall a. Num a => ReifyPicture a -> a)
-> (forall a. Num a => ReifyPicture a -> a)
-> Foldable ReifyPicture
forall a. Eq a => a -> ReifyPicture a -> Bool
forall a. Num a => ReifyPicture a -> a
forall a. Ord a => ReifyPicture a -> a
forall m. Monoid m => ReifyPicture m -> m
forall a. ReifyPicture a -> Bool
forall a. ReifyPicture a -> Int
forall a. ReifyPicture a -> [a]
forall a. (a -> a -> a) -> ReifyPicture a -> a
forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m
forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b
forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b
forall (t :: * -> *).
(forall m. Monoid m => t m -> m)
-> (forall m a. Monoid m => (a -> m) -> t a -> m)
-> (forall m a. Monoid m => (a -> m) -> t a -> m)
-> (forall a b. (a -> b -> b) -> b -> t a -> b)
-> (forall a b. (a -> b -> b) -> b -> t a -> b)
-> (forall b a. (b -> a -> b) -> b -> t a -> b)
-> (forall b a. (b -> a -> b) -> b -> t a -> b)
-> (forall a. (a -> a -> a) -> t a -> a)
-> (forall a. (a -> a -> a) -> t a -> a)
-> (forall a. t a -> [a])
-> (forall a. t a -> Bool)
-> (forall a. t a -> Int)
-> (forall a. Eq a => a -> t a -> Bool)
-> (forall a. Ord a => t a -> a)
-> (forall a. Ord a => t a -> a)
-> (forall a. Num a => t a -> a)
-> (forall a. Num a => t a -> a)
-> Foldable t
$cfold :: forall m. Monoid m => ReifyPicture m -> m
fold :: forall m. Monoid m => ReifyPicture m -> m
$cfoldMap :: forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m
foldMap :: forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m
$cfoldMap' :: forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m
foldMap' :: forall m a. Monoid m => (a -> m) -> ReifyPicture a -> m
$cfoldr :: forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b
foldr :: forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b
$cfoldr' :: forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b
foldr' :: forall a b. (a -> b -> b) -> b -> ReifyPicture a -> b
$cfoldl :: forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b
foldl :: forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b
$cfoldl' :: forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b
foldl' :: forall b a. (b -> a -> b) -> b -> ReifyPicture a -> b
$cfoldr1 :: forall a. (a -> a -> a) -> ReifyPicture a -> a
foldr1 :: forall a. (a -> a -> a) -> ReifyPicture a -> a
$cfoldl1 :: forall a. (a -> a -> a) -> ReifyPicture a -> a
foldl1 :: forall a. (a -> a -> a) -> ReifyPicture a -> a
$ctoList :: forall a. ReifyPicture a -> [a]
toList :: forall a. ReifyPicture a -> [a]
$cnull :: forall a. ReifyPicture a -> Bool
null :: forall a. ReifyPicture a -> Bool
$clength :: forall a. ReifyPicture a -> Int
length :: forall a. ReifyPicture a -> Int
$celem :: forall a. Eq a => a -> ReifyPicture a -> Bool
elem :: forall a. Eq a => a -> ReifyPicture a -> Bool
$cmaximum :: forall a. Ord a => ReifyPicture a -> a
maximum :: forall a. Ord a => ReifyPicture a -> a
$cminimum :: forall a. Ord a => ReifyPicture a -> a
minimum :: forall a. Ord a => ReifyPicture a -> a
$csum :: forall a. Num a => ReifyPicture a -> a
sum :: forall a. Num a => ReifyPicture a -> a
$cproduct :: forall a. Num a => ReifyPicture a -> a
product :: forall a. Num a => ReifyPicture a -> a
Foldable, ReifyPicture a -> ReifyPicture a -> Bool
(ReifyPicture a -> ReifyPicture a -> Bool)
-> (ReifyPicture a -> ReifyPicture a -> Bool)
-> Eq (ReifyPicture a)
forall a. Eq a => ReifyPicture a -> ReifyPicture a -> Bool
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: forall a. Eq a => ReifyPicture a -> ReifyPicture a -> Bool
== :: ReifyPicture a -> ReifyPicture a -> Bool
$c/= :: forall a. Eq a => ReifyPicture a -> ReifyPicture a -> Bool
/= :: ReifyPicture a -> ReifyPicture a -> Bool
Eq, Eq (ReifyPicture a)
Eq (ReifyPicture a) =>
(ReifyPicture a -> ReifyPicture a -> Ordering)
-> (ReifyPicture a -> ReifyPicture a -> Bool)
-> (ReifyPicture a -> ReifyPicture a -> Bool)
-> (ReifyPicture a -> ReifyPicture a -> Bool)
-> (ReifyPicture a -> ReifyPicture a -> Bool)
-> (ReifyPicture a -> ReifyPicture a -> ReifyPicture a)
-> (ReifyPicture a -> ReifyPicture a -> ReifyPicture a)
-> Ord (ReifyPicture a)
ReifyPicture a -> ReifyPicture a -> Bool
ReifyPicture a -> ReifyPicture a -> Ordering
ReifyPicture a -> ReifyPicture a -> ReifyPicture a
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
forall a. Ord a => Eq (ReifyPicture a)
forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Bool
forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Ordering
forall a.
Ord a =>
ReifyPicture a -> ReifyPicture a -> ReifyPicture a
$ccompare :: forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Ordering
compare :: ReifyPicture a -> ReifyPicture a -> Ordering
$c< :: forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Bool
< :: ReifyPicture a -> ReifyPicture a -> Bool
$c<= :: forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Bool
<= :: ReifyPicture a -> ReifyPicture a -> Bool
$c> :: forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Bool
> :: ReifyPicture a -> ReifyPicture a -> Bool
$c>= :: forall a. Ord a => ReifyPicture a -> ReifyPicture a -> Bool
>= :: ReifyPicture a -> ReifyPicture a -> Bool
$cmax :: forall a.
Ord a =>
ReifyPicture a -> ReifyPicture a -> ReifyPicture a
max :: ReifyPicture a -> ReifyPicture a -> ReifyPicture a
$cmin :: forall a.
Ord a =>
ReifyPicture a -> ReifyPicture a -> ReifyPicture a
min :: ReifyPicture a -> ReifyPicture a -> ReifyPicture a
Ord, (forall x. ReifyPicture a -> Rep (ReifyPicture a) x)
-> (forall x. Rep (ReifyPicture a) x -> ReifyPicture a)
-> Generic (ReifyPicture a)
forall x. Rep (ReifyPicture a) x -> ReifyPicture a
forall x. ReifyPicture a -> Rep (ReifyPicture a) x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
forall a x. Rep (ReifyPicture a) x -> ReifyPicture a
forall a x. ReifyPicture a -> Rep (ReifyPicture a) x
$cfrom :: forall a x. ReifyPicture a -> Rep (ReifyPicture a) x
from :: forall x. ReifyPicture a -> Rep (ReifyPicture a) x
$cto :: forall a x. Rep (ReifyPicture a) x -> ReifyPicture a
to :: forall x. Rep (ReifyPicture a) x -> ReifyPicture a
Generic, ReifyPicture a -> ()
(ReifyPicture a -> ()) -> NFData (ReifyPicture a)
forall a. NFData a => ReifyPicture a -> ()
forall a. (a -> ()) -> NFData a
$crnf :: forall a. NFData a => ReifyPicture a -> ()
rnf :: ReifyPicture a -> ()
NFData, Typeable (ReifyPicture a)
Typeable (ReifyPicture a) =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> ReifyPicture a -> c (ReifyPicture a))
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c (ReifyPicture a))
-> (ReifyPicture a -> Constr)
-> (ReifyPicture a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c (ReifyPicture a)))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e))
    -> Maybe (c (ReifyPicture a)))
-> ((forall b. Data b => b -> b)
    -> ReifyPicture a -> ReifyPicture a)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r)
-> (forall u.
    (forall d. Data d => d -> u) -> ReifyPicture a -> [u])
-> (forall u.
    Int -> (forall d. Data d => d -> u) -> ReifyPicture a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d)
    -> ReifyPicture a -> m (ReifyPicture a))
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> ReifyPicture a -> m (ReifyPicture a))
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d)
    -> ReifyPicture a -> m (ReifyPicture a))
-> Data (ReifyPicture a)
ReifyPicture a -> Constr
ReifyPicture a -> DataType
(forall b. Data b => b -> b) -> ReifyPicture a -> ReifyPicture a
forall a. Data a => Typeable (ReifyPicture a)
forall a. Data a => ReifyPicture a -> Constr
forall a. Data a => ReifyPicture a -> DataType
forall a.
Data a =>
(forall b. Data b => b -> b) -> ReifyPicture a -> ReifyPicture a
forall a u.
Data a =>
Int -> (forall d. Data d => d -> u) -> ReifyPicture a -> u
forall a u.
Data a =>
(forall d. Data d => d -> u) -> ReifyPicture a -> [u]
forall a r r'.
Data a =>
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
forall a r r'.
Data a =>
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
forall a (m :: * -> *).
(Data a, Monad m) =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
forall a (m :: * -> *).
(Data a, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
forall a (c :: * -> *).
Data a =>
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (ReifyPicture a)
forall a (c :: * -> *).
Data a =>
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ReifyPicture a -> c (ReifyPicture a)
forall a (t :: * -> *) (c :: * -> *).
(Data a, Typeable t) =>
(forall d. Data d => c (t d)) -> Maybe (c (ReifyPicture a))
forall a (t :: * -> * -> *) (c :: * -> *).
(Data a, Typeable t) =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (ReifyPicture a))
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u.
Int -> (forall d. Data d => d -> u) -> ReifyPicture a -> u
forall u. (forall d. Data d => d -> u) -> ReifyPicture a -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (ReifyPicture a)
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ReifyPicture a -> c (ReifyPicture a)
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c (ReifyPicture a))
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (ReifyPicture a))
$cgfoldl :: forall a (c :: * -> *).
Data a =>
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ReifyPicture a -> c (ReifyPicture a)
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> ReifyPicture a -> c (ReifyPicture a)
$cgunfold :: forall a (c :: * -> *).
Data a =>
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (ReifyPicture a)
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c (ReifyPicture a)
$ctoConstr :: forall a. Data a => ReifyPicture a -> Constr
toConstr :: ReifyPicture a -> Constr
$cdataTypeOf :: forall a. Data a => ReifyPicture a -> DataType
dataTypeOf :: ReifyPicture a -> DataType
$cdataCast1 :: forall a (t :: * -> *) (c :: * -> *).
(Data a, Typeable t) =>
(forall d. Data d => c (t d)) -> Maybe (c (ReifyPicture a))
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c (ReifyPicture a))
$cdataCast2 :: forall a (t :: * -> * -> *) (c :: * -> *).
(Data a, Typeable t) =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (ReifyPicture a))
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e))
-> Maybe (c (ReifyPicture a))
$cgmapT :: forall a.
Data a =>
(forall b. Data b => b -> b) -> ReifyPicture a -> ReifyPicture a
gmapT :: (forall b. Data b => b -> b) -> ReifyPicture a -> ReifyPicture a
$cgmapQl :: forall a r r'.
Data a =>
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
$cgmapQr :: forall a r r'.
Data a =>
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> ReifyPicture a -> r
$cgmapQ :: forall a u.
Data a =>
(forall d. Data d => d -> u) -> ReifyPicture a -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> ReifyPicture a -> [u]
$cgmapQi :: forall a u.
Data a =>
Int -> (forall d. Data d => d -> u) -> ReifyPicture a -> u
gmapQi :: forall u.
Int -> (forall d. Data d => d -> u) -> ReifyPicture a -> u
$cgmapM :: forall a (m :: * -> *).
(Data a, Monad m) =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
$cgmapMp :: forall a (m :: * -> *).
(Data a, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
$cgmapMo :: forall a (m :: * -> *).
(Data a, MonadPlus m) =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d)
-> ReifyPicture a -> m (ReifyPicture a)
Data, Typeable)


{- |
Student facing, basic picture type.
A value of this type can be build using the CodeWorld API.

"CodeWorld.Test" also exports pattern synonyms for all contained constructors.
This allows for easier pattern matching in generic traversals.
-}
newtype Picture = PRec (ReifyPicture Picture)
  {- ^
  The recursive structure of the type is necessary
  for [Reify CSE detection](https://hackage.haskell.org/package/data-reify).
  -}
  deriving (Int -> Picture -> ShowS
[Picture] -> ShowS
Picture -> String
(Int -> Picture -> ShowS)
-> (Picture -> String) -> ([Picture] -> ShowS) -> Show Picture
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
$cshowsPrec :: Int -> Picture -> ShowS
showsPrec :: Int -> Picture -> ShowS
$cshow :: Picture -> String
show :: Picture -> String
$cshowList :: [Picture] -> ShowS
showList :: [Picture] -> ShowS
Show,Picture -> Picture -> Bool
(Picture -> Picture -> Bool)
-> (Picture -> Picture -> Bool) -> Eq Picture
forall a. (a -> a -> Bool) -> (a -> a -> Bool) -> Eq a
$c== :: Picture -> Picture -> Bool
== :: Picture -> Picture -> Bool
$c/= :: Picture -> Picture -> Bool
/= :: Picture -> Picture -> Bool
Eq,Eq Picture
Eq Picture =>
(Picture -> Picture -> Ordering)
-> (Picture -> Picture -> Bool)
-> (Picture -> Picture -> Bool)
-> (Picture -> Picture -> Bool)
-> (Picture -> Picture -> Bool)
-> (Picture -> Picture -> Picture)
-> (Picture -> Picture -> Picture)
-> Ord Picture
Picture -> Picture -> Bool
Picture -> Picture -> Ordering
Picture -> Picture -> Picture
forall a.
Eq a =>
(a -> a -> Ordering)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> Bool)
-> (a -> a -> a)
-> (a -> a -> a)
-> Ord a
$ccompare :: Picture -> Picture -> Ordering
compare :: Picture -> Picture -> Ordering
$c< :: Picture -> Picture -> Bool
< :: Picture -> Picture -> Bool
$c<= :: Picture -> Picture -> Bool
<= :: Picture -> Picture -> Bool
$c> :: Picture -> Picture -> Bool
> :: Picture -> Picture -> Bool
$c>= :: Picture -> Picture -> Bool
>= :: Picture -> Picture -> Bool
$cmax :: Picture -> Picture -> Picture
max :: Picture -> Picture -> Picture
$cmin :: Picture -> Picture -> Picture
min :: Picture -> Picture -> Picture
Ord,(forall x. Picture -> Rep Picture x)
-> (forall x. Rep Picture x -> Picture) -> Generic Picture
forall x. Rep Picture x -> Picture
forall x. Picture -> Rep Picture x
forall a.
(forall x. a -> Rep a x) -> (forall x. Rep a x -> a) -> Generic a
$cfrom :: forall x. Picture -> Rep Picture x
from :: forall x. Picture -> Rep Picture x
$cto :: forall x. Rep Picture x -> Picture
to :: forall x. Rep Picture x -> Picture
Generic,Picture -> ()
(Picture -> ()) -> NFData Picture
forall a. (a -> ()) -> NFData a
$crnf :: Picture -> ()
rnf :: Picture -> ()
NFData,Typeable Picture
Typeable Picture =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> Picture -> c Picture)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c Picture)
-> (Picture -> Constr)
-> (Picture -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c Picture))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c Picture))
-> ((forall b. Data b => b -> b) -> Picture -> Picture)
-> (forall r r'.
    (r -> r' -> r)
    -> r -> (forall d. Data d => d -> r') -> Picture -> r)
-> (forall r r'.
    (r' -> r -> r)
    -> r -> (forall d. Data d => d -> r') -> Picture -> r)
-> (forall u. (forall d. Data d => d -> u) -> Picture -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> Picture -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> Picture -> m Picture)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> Picture -> m Picture)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> Picture -> m Picture)
-> Data Picture
Picture -> Constr
Picture -> DataType
(forall b. Data b => b -> b) -> Picture -> Picture
forall a.
Typeable a =>
(forall (c :: * -> *).
 (forall d b. Data d => c (d -> b) -> d -> c b)
 -> (forall g. g -> c g) -> a -> c a)
-> (forall (c :: * -> *).
    (forall b r. Data b => c (b -> r) -> c r)
    -> (forall r. r -> c r) -> Constr -> c a)
-> (a -> Constr)
-> (a -> DataType)
-> (forall (t :: * -> *) (c :: * -> *).
    Typeable t =>
    (forall d. Data d => c (t d)) -> Maybe (c a))
-> (forall (t :: * -> * -> *) (c :: * -> *).
    Typeable t =>
    (forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c a))
-> ((forall b. Data b => b -> b) -> a -> a)
-> (forall r r'.
    (r -> r' -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall r r'.
    (r' -> r -> r) -> r -> (forall d. Data d => d -> r') -> a -> r)
-> (forall u. (forall d. Data d => d -> u) -> a -> [u])
-> (forall u. Int -> (forall d. Data d => d -> u) -> a -> u)
-> (forall (m :: * -> *).
    Monad m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> (forall (m :: * -> *).
    MonadPlus m =>
    (forall d. Data d => d -> m d) -> a -> m a)
-> Data a
forall u. Int -> (forall d. Data d => d -> u) -> Picture -> u
forall u. (forall d. Data d => d -> u) -> Picture -> [u]
forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c Picture
forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> Picture -> c Picture
forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c Picture)
forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c Picture)
$cgfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> Picture -> c Picture
gfoldl :: forall (c :: * -> *).
(forall d b. Data d => c (d -> b) -> d -> c b)
-> (forall g. g -> c g) -> Picture -> c Picture
$cgunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c Picture
gunfold :: forall (c :: * -> *).
(forall b r. Data b => c (b -> r) -> c r)
-> (forall r. r -> c r) -> Constr -> c Picture
$ctoConstr :: Picture -> Constr
toConstr :: Picture -> Constr
$cdataTypeOf :: Picture -> DataType
dataTypeOf :: Picture -> DataType
$cdataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c Picture)
dataCast1 :: forall (t :: * -> *) (c :: * -> *).
Typeable t =>
(forall d. Data d => c (t d)) -> Maybe (c Picture)
$cdataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c Picture)
dataCast2 :: forall (t :: * -> * -> *) (c :: * -> *).
Typeable t =>
(forall d e. (Data d, Data e) => c (t d e)) -> Maybe (c Picture)
$cgmapT :: (forall b. Data b => b -> b) -> Picture -> Picture
gmapT :: (forall b. Data b => b -> b) -> Picture -> Picture
$cgmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
gmapQl :: forall r r'.
(r -> r' -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
$cgmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
gmapQr :: forall r r'.
(r' -> r -> r)
-> r -> (forall d. Data d => d -> r') -> Picture -> r
$cgmapQ :: forall u. (forall d. Data d => d -> u) -> Picture -> [u]
gmapQ :: forall u. (forall d. Data d => d -> u) -> Picture -> [u]
$cgmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> Picture -> u
gmapQi :: forall u. Int -> (forall d. Data d => d -> u) -> Picture -> u
$cgmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
gmapM :: forall (m :: * -> *).
Monad m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
$cgmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
gmapMp :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
$cgmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
gmapMo :: forall (m :: * -> *).
MonadPlus m =>
(forall d. Data d => d -> m d) -> Picture -> m Picture
Data,Typeable)


{-|
Draw a hollow, thin rectangle with this length and height.
-}
rectangle :: Double -> Double -> Picture
rectangle :: Double -> Double -> Picture
rectangle Double
x = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> ReifyPicture a
Rectangle Double
x

{-|
Draw a hollow rectangle with this line width, length and height.
Specifying a negative line width causes a runtime error (mirrors behaviour in CodeWorld editor).
-}
thickRectangle :: Double -> Double -> Double -> Picture
thickRectangle :: Double -> Double -> Double -> Picture
thickRectangle (Double -> Double
validThickness -> Double
t) Double
x = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> Double -> ReifyPicture a
ThickRectangle Double
t Double
x

{-|
Draw a filled in rectangle with this length and height.
-}
solidRectangle :: Double -> Double -> Picture
solidRectangle :: Double -> Double -> Picture
solidRectangle Double
x = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> ReifyPicture a
SolidRectangle Double
x

{-|
Draw a hollow, thin circle with this radius.
-}
circle :: Double -> Picture
circle :: Double -> Picture
circle = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> ReifyPicture Picture
forall a. Double -> ReifyPicture a
Circle

{-|
Draw a hollow circle with this line width and radius.
Specifying a negative line width or a line width greater than the circles diameter
causes a runtime error (mirrors behaviour in CodeWorld editor).
-}
thickCircle :: Double -> Double -> Picture
thickCircle :: Double -> Double -> Picture
thickCircle (Double -> Double
validThickness -> Double
t) Double
r
  | Double
t Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Double
2 Double -> Double -> Double
forall a. Num a => a -> a -> a
* Double
r = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ReifyPicture Picture -> Picture
forall a b. (a -> b) -> a -> b
$ Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> ReifyPicture a
ThickCircle Double
t Double
r
  | Bool
otherwise  = String -> Picture
forall a. HasCallStack => String -> a
error String
"The line width of a thickCircle must not be greater than the diameter."

{-|
Draw a filled in circle with this radius.
-}
solidCircle :: Double -> Picture
solidCircle :: Double -> Picture
solidCircle = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> ReifyPicture Picture
forall a. Double -> ReifyPicture a
SolidCircle

{-|
Draw a thin, hollow circle segment with these start and end angles and radius.
-}
arc :: Double -> Double -> Double -> Picture
arc :: Double -> Double -> Double -> Picture
arc Double
a1 Double
a2 = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> Double -> ReifyPicture a
Arc Double
a1 Double
a2

{-|
Draw a filled in circle segment with these start and end angles and radius.
This would be @solidArc@ following the usual naming scheme.
-}
sector :: Double -> Double -> Double -> Picture
sector :: Double -> Double -> Double -> Picture
sector Double
a1 Double
a2 = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> Double -> ReifyPicture a
Sector Double
a1 Double
a2

{-|
Draw a hollow circle segment with this line width, these start and end angles and radius.
Specifying a negative line width causes a runtime error (mirrors behaviour in CodeWorld editor).
-}
thickArc :: Double -> Double -> Double -> Double -> Picture
thickArc :: Double -> Double -> Double -> Double -> Picture
thickArc (Double -> Double
validThickness -> Double
t) Double
a1 Double
a2 = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Double -> ReifyPicture Picture) -> Double -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Double -> Double -> ReifyPicture Picture
forall a. Double -> Double -> Double -> Double -> ReifyPicture a
ThickArc Double
t Double
a1 Double
a2

{-|
Draw a thin curve passing through the provided points via a number of Bézier splices.
-}
curve :: [Point] -> Picture
curve :: [Point] -> Picture
curve = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
Curve

{-|
Draw a curve with this line width passing through the provided points via a number of Bézier splices.
Specifying a negative line width causes a runtime error (mirrors behaviour in CodeWorld editor).
-}
thickCurve :: Double -> [Point] -> Picture
thickCurve :: Double -> [Point] -> Picture
thickCurve (Double -> Double
validThickness -> Double
t) = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> [Point] -> ReifyPicture Picture
forall a. Double -> [Point] -> ReifyPicture a
ThickCurve Double
t

{-|
Same as `curve` but adds another splice between the start and end points to close the shape.
-}
closedCurve :: [Point] -> Picture
closedCurve :: [Point] -> Picture
closedCurve = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
ClosedCurve

{-|
Same as `thickCurve` but adds another splice between the start and end points to close the shape.
-}
thickClosedCurve :: Double -> [Point] -> Picture
thickClosedCurve :: Double -> [Point] -> Picture
thickClosedCurve (Double -> Double
validThickness -> Double
t) = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> [Point] -> ReifyPicture Picture
forall a. Double -> [Point] -> ReifyPicture a
ThickClosedCurve Double
t

{-|
Draw a curve passing through the provided points via a number of Bézier splices.
Adds another splice between the start and end points to close the shape and completely fills the enclosed area.
-}
solidClosedCurve :: [Point] -> Picture
solidClosedCurve :: [Point] -> Picture
solidClosedCurve = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
SolidClosedCurve

{-|
Draw a sequence of thin line segments passing through the provided points.
-}
polyline :: [Point] -> Picture
polyline :: [Point] -> Picture
polyline = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
Polyline

{-|
Draw a sequence of line segments with this line width passing through the provided points.
Specifying a negative line width causes a runtime error (mirrors behaviour in CodeWorld editor).
-}
thickPolyline :: Double -> [Point] -> Picture
thickPolyline :: Double -> [Point] -> Picture
thickPolyline (Double -> Double
validThickness -> Double
t) = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> [Point] -> ReifyPicture Picture
forall a. Double -> [Point] -> ReifyPicture a
ThickPolyline Double
t

{-|
Same as `polyline` but adds another segment between the start and end points to close the shape.
-}
polygon :: [Point] -> Picture
polygon :: [Point] -> Picture
polygon = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
Polygon

{-|
Same as `thickPolyline` but adds another segment between the start and end points to close the shape.
-}
thickPolygon :: Double -> [Point] -> Picture
thickPolygon :: Double -> [Point] -> Picture
thickPolygon (Double -> Double
validThickness -> Double
t) = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> [Point] -> ReifyPicture Picture
forall a. Double -> [Point] -> ReifyPicture a
ThickPolygon Double
t

{-|
Draw a sequence of line segments with this line width passing through the provided points
and completely fill the enclosed area.
-}
solidPolygon :: [Point] -> Picture
solidPolygon :: [Point] -> Picture
solidPolygon = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Point] -> ReifyPicture Picture) -> [Point] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Point] -> ReifyPicture Picture
forall a. [Point] -> ReifyPicture a
SolidPolygon

{-|
Render this text into an image.
-}
lettering :: Text -> Picture
lettering :: Text -> Picture
lettering = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Text -> ReifyPicture Picture) -> Text -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Text -> ReifyPicture Picture
forall a. Text -> ReifyPicture a
Lettering

{-|
Render this text into an image using the provided `TextStyle` and `Font`.
-}
styledLettering :: TextStyle -> Font -> Text -> Picture
styledLettering :: TextStyle -> Font -> Text -> Picture
styledLettering TextStyle
ts Font
f = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Text -> ReifyPicture Picture) -> Text -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. TextStyle -> Font -> Text -> ReifyPicture Picture
forall a. TextStyle -> Font -> Text -> ReifyPicture a
StyledLettering TextStyle
ts Font
f

{-|
Apply this `Color` to the image.
-}
colored :: Color -> Picture -> Picture
colored :: Color -> Picture -> Picture
colored Color
c = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Color -> Picture -> ReifyPicture Picture
forall a. Color -> a -> ReifyPicture a
Color Color
c

{-|
Alias for `colored`.
-}
coloured :: Color -> Picture -> Picture
coloured :: Color -> Picture -> Picture
coloured = Color -> Picture -> Picture
colored

{-|
Move the image in x and y-direction.
-}
translated :: Double -> Double -> Picture -> Picture
translated :: Double -> Double -> Picture -> Picture
translated Double
x Double
y = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Picture -> ReifyPicture Picture
forall a. Double -> Double -> a -> ReifyPicture a
Translate Double
x Double
y

{-|
Scale the image in x and y-directions using these modifiers.
-}
scaled :: Double -> Double -> Picture -> Picture
scaled :: Double -> Double -> Picture -> Picture
scaled Double
x Double
y = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Picture -> ReifyPicture Picture
forall a. Double -> Double -> a -> ReifyPicture a
Scale Double
x Double
y

{-|
Scale the image in both directions using the same modifier.
-}
dilated :: Double -> Picture -> Picture
dilated :: Double -> Picture -> Picture
dilated Double
a = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Picture -> ReifyPicture Picture
forall a. Double -> a -> ReifyPicture a
Dilate Double
a

{-|
Rotate the image around the origin using this angle in radians.
-}
rotated :: Double -> Picture -> Picture
rotated :: Double -> Picture -> Picture
rotated Double
a = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Picture -> ReifyPicture Picture
forall a. Double -> a -> ReifyPicture a
Rotate Double
a

{-|
Reflect the image across a line through the origin with this angle to the x-axis.
-}
reflected :: Double -> Picture -> Picture
reflected :: Double -> Picture -> Picture
reflected Double
a = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Picture -> ReifyPicture Picture
forall a. Double -> a -> ReifyPicture a
Reflect Double
a

{-|
Clip the image in a rectangle with this length and height.
-}
clipped :: Double -> Double -> Picture -> Picture
clipped :: Double -> Double -> Picture -> Picture
clipped Double
x Double
y = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> (Picture -> ReifyPicture Picture) -> Picture -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Double -> Double -> Picture -> ReifyPicture Picture
forall a. Double -> Double -> a -> ReifyPicture a
Clip Double
x Double
y

{-|
Compose a list of `Picture`s.
Equivalent to @foldr (&) blank@.
-}
pictures :: [Picture] -> Picture
pictures :: [Picture] -> Picture
pictures = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ([Picture] -> ReifyPicture Picture) -> [Picture] -> Picture
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [Picture] -> ReifyPicture Picture
forall a. [a] -> ReifyPicture a
Pictures

{-|
Compose two `Picture`s.
The left argument will drawn on top of the right argument if they overlap.
-}
(&) :: Picture -> Picture -> Picture
Picture
a & :: Picture -> Picture -> Picture
& Picture
b = ReifyPicture Picture -> Picture
PRec (ReifyPicture Picture -> Picture)
-> ReifyPicture Picture -> Picture
forall a b. (a -> b) -> a -> b
$ Picture -> Picture -> ReifyPicture Picture
forall a. a -> a -> ReifyPicture a
And Picture
a Picture
b

{-|
A static image of a coordinate plane extending 5 units in all directions.
-}
coordinatePlane :: Picture
coordinatePlane :: Picture
coordinatePlane = ReifyPicture Picture -> Picture
PRec ReifyPicture Picture
forall a. ReifyPicture a
CoordinatePlane

{-|
A static image of the CodeWorld logo.
-}
codeWorldLogo :: Picture
 = ReifyPicture Picture -> Picture
PRec ReifyPicture Picture
forall a. ReifyPicture a
Logo

{-|
An empty `Picture`.
This is the identity element of `&`.
-}
blank :: Picture
blank :: Picture
blank = ReifyPicture Picture -> Picture
PRec ReifyPicture Picture
forall a. ReifyPicture a
Blank


instance MuRef Picture where
  type DeRef Picture = ReifyPicture
  mapDeRef :: forall (f :: * -> *) u.
Applicative f =>
(forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u)
-> Picture -> f (DeRef Picture u)
mapDeRef forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f (PRec ReifyPicture Picture
body) = case ReifyPicture Picture
body of
    Color Color
c Picture
p             -> Color -> u -> ReifyPicture u
forall a. Color -> a -> ReifyPicture a
Color Color
c (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Translate Double
x Double
y Picture
p       -> Double -> Double -> u -> ReifyPicture u
forall a. Double -> Double -> a -> ReifyPicture a
Translate Double
x Double
y (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Scale Double
x Double
y Picture
p           -> Double -> Double -> u -> ReifyPicture u
forall a. Double -> Double -> a -> ReifyPicture a
Scale Double
x Double
y (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Dilate Double
x Picture
p            -> Double -> u -> ReifyPicture u
forall a. Double -> a -> ReifyPicture a
Dilate Double
x (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Rotate Double
a Picture
p            -> Double -> u -> ReifyPicture u
forall a. Double -> a -> ReifyPicture a
Rotate Double
a (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Reflect Double
a Picture
p           -> Double -> u -> ReifyPicture u
forall a. Double -> a -> ReifyPicture a
Reflect Double
a (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    Clip Double
x Double
y Picture
p            -> Double -> Double -> u -> ReifyPicture u
forall a. Double -> Double -> a -> ReifyPicture a
Clip Double
x Double
y (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
p
    And Picture
a Picture
b               -> u -> u -> ReifyPicture u
forall a. a -> a -> ReifyPicture a
And (u -> u -> ReifyPicture u) -> f u -> f (u -> ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
a f (u -> ReifyPicture u) -> f u -> f (ReifyPicture u)
forall a b. f (a -> b) -> f a -> f b
forall (f :: * -> *) a b. Applicative f => f (a -> b) -> f a -> f b
<*> Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f Picture
b
    Pictures [Picture]
ps           -> [u] -> ReifyPicture u
forall a. [a] -> ReifyPicture a
Pictures ([u] -> ReifyPicture u) -> f [u] -> f (ReifyPicture u)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Picture -> f u) -> [Picture] -> f [u]
forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
forall (f :: * -> *) a b.
Applicative f =>
(a -> f b) -> [a] -> f [b]
traverse Picture -> f u
forall b. (MuRef b, DeRef Picture ~ DeRef b) => b -> f u
f [Picture]
ps
    ReifyPicture Picture
p                     -> DeRef Picture u -> f (DeRef Picture u)
forall a. a -> f a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (DeRef Picture u -> f (DeRef Picture u))
-> DeRef Picture u -> f (DeRef Picture u)
forall a b. (a -> b) -> a -> b
$ case ReifyPicture Picture
p of
      Rectangle Double
x Double
y         -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> ReifyPicture a
Rectangle Double
x Double
y
      ThickRectangle Double
t Double
x Double
y  -> Double -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> Double -> ReifyPicture a
ThickRectangle Double
t Double
x Double
y
      SolidRectangle Double
x Double
y    -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> ReifyPicture a
SolidRectangle Double
x Double
y
      Circle Double
r              -> Double -> ReifyPicture u
forall a. Double -> ReifyPicture a
Circle Double
r
      ThickCircle Double
t Double
r       -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> ReifyPicture a
ThickCircle Double
t Double
r
      SolidCircle Double
r         -> Double -> ReifyPicture u
forall a. Double -> ReifyPicture a
SolidCircle Double
r
      Lettering Text
t           -> Text -> ReifyPicture u
forall a. Text -> ReifyPicture a
Lettering Text
t
      StyledLettering TextStyle
s Font
w Text
t -> TextStyle -> Font -> Text -> ReifyPicture u
forall a. TextStyle -> Font -> Text -> ReifyPicture a
StyledLettering TextStyle
s Font
w Text
t
      Curve [Point]
xs              -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
Curve [Point]
xs
      ThickCurve Double
t [Point]
xs       -> Double -> [Point] -> ReifyPicture u
forall a. Double -> [Point] -> ReifyPicture a
ThickCurve Double
t [Point]
xs
      ClosedCurve [Point]
xs        -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
ClosedCurve [Point]
xs
      SolidClosedCurve [Point]
xs   -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
SolidClosedCurve [Point]
xs
      ThickClosedCurve Double
xs [Point]
t -> Double -> [Point] -> ReifyPicture u
forall a. Double -> [Point] -> ReifyPicture a
ThickClosedCurve Double
xs [Point]
t
      Polygon [Point]
xs            -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
Polygon [Point]
xs
      SolidPolygon [Point]
xs       -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
SolidPolygon [Point]
xs
      ThickPolygon Double
xs [Point]
t     -> Double -> [Point] -> ReifyPicture u
forall a. Double -> [Point] -> ReifyPicture a
ThickPolygon Double
xs [Point]
t
      Polyline [Point]
xs           -> [Point] -> ReifyPicture u
forall a. [Point] -> ReifyPicture a
Polyline [Point]
xs
      ThickPolyline Double
xs [Point]
t    -> Double -> [Point] -> ReifyPicture u
forall a. Double -> [Point] -> ReifyPicture a
ThickPolyline Double
xs [Point]
t
      Sector Double
a1 Double
a2 Double
r        -> Double -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> Double -> ReifyPicture a
Sector Double
a1 Double
a2 Double
r
      Arc Double
a1 Double
a2 Double
r           -> Double -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> Double -> ReifyPicture a
Arc Double
a1 Double
a2 Double
r
      ThickArc Double
t Double
a1 Double
a2 Double
r    -> Double -> Double -> Double -> Double -> ReifyPicture u
forall a. Double -> Double -> Double -> Double -> ReifyPicture a
ThickArc Double
t Double
a1 Double
a2 Double
r
      ReifyPicture Picture
CoordinatePlane       -> DeRef Picture u
ReifyPicture u
forall a. ReifyPicture a
CoordinatePlane
      ReifyPicture Picture
Logo                  -> DeRef Picture u
ReifyPicture u
forall a. ReifyPicture a
Logo
      ReifyPicture Picture
Blank                 -> DeRef Picture u
ReifyPicture u
forall a. ReifyPicture a
Blank


share :: Picture -> IO (IntMap (ReifyPicture Int), IntMap (ReifyPicture Int))
share :: Picture
-> IO (IntMap (ReifyPicture Int), IntMap (ReifyPicture Int))
share Picture
d = do
  Graph [(Int, ReifyPicture Int)]
nodes Int
s <- Picture -> IO (Graph (DeRef Picture))
forall s. MuRef s => s -> IO (Graph (DeRef s))
reifyGraph Picture
d
  let universe :: IntMap (ReifyPicture Int)
universe = [(Int, ReifyPicture Int)] -> IntMap (ReifyPicture Int)
forall a. [(Int, a)] -> IntMap a
IM.fromList [(Int, ReifyPicture Int)]
nodes
      refs :: IntMap Int
refs = (Int -> Int -> Int) -> Int -> Int -> IntMap Int -> IntMap Int
forall a. (a -> a -> a) -> Int -> a -> IntMap a -> IntMap a
IM.insertWith Int -> Int -> Int
forall a. Num a => a -> a -> a
(+) Int
s Int
1 (IntMap Int -> IntMap Int) -> IntMap Int -> IntMap Int
forall a b. (a -> b) -> a -> b
$ ((Int, ReifyPicture Int) -> IntMap Int -> IntMap Int)
-> IntMap Int -> [(Int, ReifyPicture Int)] -> IntMap Int
forall a b. (a -> b -> b) -> b -> [a] -> b
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
foldr ([Int] -> IntMap Int -> IntMap Int
mapInsertWith ([Int] -> IntMap Int -> IntMap Int)
-> ((Int, ReifyPicture Int) -> [Int])
-> (Int, ReifyPicture Int)
-> IntMap Int
-> IntMap Int
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ReifyPicture Int -> [Int]
forall a. ReifyPicture a -> [a]
forall (t :: * -> *) a. Foldable t => t a -> [a]
toList (ReifyPicture Int -> [Int])
-> ((Int, ReifyPicture Int) -> ReifyPicture Int)
-> (Int, ReifyPicture Int)
-> [Int]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Int, ReifyPicture Int) -> ReifyPicture Int
forall a b. (a, b) -> b
snd) IntMap Int
forall a. Monoid a => a
mempty [(Int, ReifyPicture Int)]
nodes
      multiRefs :: IntMap (ReifyPicture Int)
multiRefs = IntMap (ReifyPicture Int)
-> IntMap Int -> IntMap (ReifyPicture Int)
forall a b. IntMap a -> IntMap b -> IntMap a
IM.intersection IntMap (ReifyPicture Int)
universe (IntMap Int -> IntMap (ReifyPicture Int))
-> IntMap Int -> IntMap (ReifyPicture Int)
forall a b. (a -> b) -> a -> b
$ (Int -> Bool) -> IntMap Int -> IntMap Int
forall a. (a -> Bool) -> IntMap a -> IntMap a
IM.filter (Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
>Int
1) IntMap Int
refs
      lut :: IntMap (ReifyPicture Int)
lut = IntMap (ReifyPicture Int)
-> IntMap Int -> IntMap (ReifyPicture Int)
forall a b. IntMap a -> IntMap b -> IntMap a
IM.intersection IntMap (ReifyPicture Int)
universe IntMap Int
refs
  (IntMap (ReifyPicture Int), IntMap (ReifyPicture Int))
-> IO (IntMap (ReifyPicture Int), IntMap (ReifyPicture Int))
forall a. a -> IO a
forall (f :: * -> *) a. Applicative f => a -> f a
pure (IntMap (ReifyPicture Int)
multiRefs, IntMap (ReifyPicture Int)
lut)


mapInsertWith :: [Key] -> IntMap Int -> IntMap Int
mapInsertWith :: [Int] -> IntMap Int -> IntMap Int
mapInsertWith [Int]
b IntMap Int
m = (Int -> IntMap Int -> IntMap Int)
-> IntMap Int -> [Int] -> IntMap Int
forall a b. (a -> b -> b) -> b -> [a] -> b
forall (t :: * -> *) a b.
Foldable t =>
(a -> b -> b) -> b -> t a -> b
Prelude.foldr (\Int
x IntMap Int
acc-> (Int -> Int -> Int) -> Int -> Int -> IntMap Int -> IntMap Int
forall a. (a -> a -> a) -> Int -> a -> IntMap a -> IntMap a
IM.insertWith Int -> Int -> Int
forall a. Num a => a -> a -> a
(+) Int
x (Int
1 :: Int) IntMap Int
acc) IntMap Int
m [Int]
b


toInterface :: API.Drawable a => Picture -> a
toInterface :: forall a. Drawable a => Picture -> a
toInterface (PRec ReifyPicture Picture
p) = case ReifyPicture Picture
p of
  Rectangle Double
x Double
y -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> a
API.rectangle Double
x Double
y
  ThickRectangle Double
t Double
x Double
y -> Double -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> Double -> a
API.thickRectangle Double
t Double
x Double
y
  SolidRectangle Double
x Double
y -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> a
API.solidRectangle Double
x Double
y
  Circle Double
r -> Double -> a
forall a. Drawable a => Double -> a
API.circle Double
r
  ThickCircle Double
t Double
r -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> a
API.thickCircle Double
t Double
r
  SolidCircle Double
r -> Double -> a
forall a. Drawable a => Double -> a
API.solidCircle Double
r
  Polygon [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.polygon [Point]
ps
  SolidPolygon [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.solidPolygon [Point]
ps
  ThickPolygon Double
t [Point]
ps -> Double -> [Point] -> a
forall a. Drawable a => Double -> [Point] -> a
API.thickPolygon Double
t [Point]
ps
  ClosedCurve [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.closedCurve [Point]
ps
  SolidClosedCurve [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.solidClosedCurve [Point]
ps
  ThickClosedCurve Double
t [Point]
ps -> Double -> [Point] -> a
forall a. Drawable a => Double -> [Point] -> a
API.thickClosedCurve Double
t [Point]
ps
  Polyline [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.polyline [Point]
ps
  ThickPolyline Double
t [Point]
ps -> Double -> [Point] -> a
forall a. Drawable a => Double -> [Point] -> a
API.thickPolyline Double
t [Point]
ps
  Curve [Point]
ps -> [Point] -> a
forall a. Drawable a => [Point] -> a
API.curve [Point]
ps
  ThickCurve Double
t [Point]
ps -> Double -> [Point] -> a
forall a. Drawable a => Double -> [Point] -> a
API.thickCurve Double
t [Point]
ps
  Sector Double
a1 Double
a2 Double
r -> Double -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> Double -> a
API.sector Double
a1 Double
a2 Double
r
  Arc Double
a1 Double
a2 Double
r -> Double -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> Double -> a
API.arc Double
a1 Double
a2 Double
r
  ThickArc Double
t Double
a1 Double
a2 Double
r -> Double -> Double -> Double -> Double -> a
forall a. Drawable a => Double -> Double -> Double -> Double -> a
API.thickArc Double
t Double
a1 Double
a2 Double
r
  Lettering Text
t -> Text -> a
forall a. Drawable a => Text -> a
API.lettering Text
t
  StyledLettering TextStyle
ts Font
f Text
t -> TextStyle -> Font -> Text -> a
forall a. Drawable a => TextStyle -> Font -> Text -> a
API.styledLettering TextStyle
ts Font
f Text
t
  Color Color
c Picture
q -> Color -> a -> a
forall a. Drawable a => Color -> a -> a
API.colored Color
c (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Translate Double
x Double
y Picture
q -> Double -> Double -> a -> a
forall a. Drawable a => Double -> Double -> a -> a
API.translated Double
x Double
y (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Scale Double
x Double
y Picture
q -> Double -> Double -> a -> a
forall a. Drawable a => Double -> Double -> a -> a
API.scaled Double
x Double
y (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Dilate Double
fac Picture
q -> Double -> a -> a
forall a. Drawable a => Double -> a -> a
API.dilated Double
fac (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Rotate Double
a Picture
q -> Double -> a -> a
forall a. Drawable a => Double -> a -> a
API.rotated Double
a (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Reflect Double
a Picture
q -> Double -> a -> a
forall a. Drawable a => Double -> a -> a
API.reflected Double
a (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Clip Double
x Double
y Picture
q -> Double -> Double -> a -> a
forall a. Drawable a => Double -> Double -> a -> a
API.clipped Double
x Double
y (a -> a) -> a -> a
forall a b. (a -> b) -> a -> b
$ Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
q
  Pictures [Picture]
ps -> [a] -> a
forall a. Drawable a => [a] -> a
API.pictures ([a] -> a) -> [a] -> a
forall a b. (a -> b) -> a -> b
$ (Picture -> a) -> [Picture] -> [a]
forall a b. (a -> b) -> [a] -> [b]
map Picture -> a
forall a. Drawable a => Picture -> a
toInterface [Picture]
ps
  And Picture
p1 Picture
p2 -> Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
p1 a -> a -> a
forall a. Drawable a => a -> a -> a
API.& Picture -> a
forall a. Drawable a => Picture -> a
toInterface Picture
p2
  ReifyPicture Picture
CoordinatePlane -> a
forall a. Drawable a => a
API.coordinatePlane
  ReifyPicture Picture
Logo -> a
forall a. Drawable a => a
API.codeWorldLogo
  ReifyPicture Picture
Blank -> a
forall a. Drawable a => a
API.blank


{-
The next two functions should never be used on `And` or `Pictures` for this to make any sense.
This is currently the case, but could be problematic if this is used on non-reduced trees
where those constructors could appear somewhere inside the structure.
TODO: Change return type to [Picture] and adjust the tests.
-}

{- |
Returns the contained `Picture` if the argument is not a basic shape and the argument itself if it is.

__Warning: This is intended to be used on non-composite pictures only.__
`Pictures` and `And` will be treated as a basic picture (i.e. the function will behave like `id`)
if used as an argument.
-}
innerPicture :: Picture -> Picture
innerPicture :: Picture -> Picture
innerPicture p :: Picture
p@(PRec (Pictures {})) = Picture
p
innerPicture p :: Picture
p@(PRec (And {}))      = Picture
p
innerPicture Picture
p                      = Picture -> [Picture] -> Picture
forall a. a -> [a] -> a
headDef Picture
p ([Picture] -> Picture) -> [Picture] -> Picture
forall a b. (a -> b) -> a -> b
$ Picture -> [Picture]
forall on. Uniplate on => on -> [on]
children Picture
p

{- |
Returns `True` if the argument is not a basic shape.

__Warning: This is intended to be used on non-composite pictures only.__
`Pictures` and `And` will be treated as a basic picture (i.e. returning `False`) if used as an argument.
-}
hasInnerPicture :: Picture -> Bool
hasInnerPicture :: Picture -> Bool
hasInnerPicture (PRec (Pictures {})) = Bool
False
hasInnerPicture (PRec (And {}))      = Bool
False
hasInnerPicture Picture
p                    = Bool -> Bool
not (Bool -> Bool) -> Bool -> Bool
forall a b. (a -> b) -> a -> b
$ [Picture] -> Bool
forall a. [a] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null ([Picture] -> Bool) -> [Picture] -> Bool
forall a b. (a -> b) -> a -> b
$ Picture -> [Picture]
forall on. Uniplate on => on -> [on]
children Picture
p


{- |
Checks if the argument is contained completely inside a box.
The coordinates of the box are given as two points with the following format:

  1. (minimum x-value, maximum x-value)
  2. (minimum y-value, maximum y-value)
-}
isIn :: Picture -> (Point,Point) -> Bool
isIn :: Picture -> (Point, Point) -> Bool
isIn Picture
pic ((Double
lowerX, Double
upperX), (Double
lowerY, Double
upperY)) =
  Picture -> (Point, Point, Point, Point) -> Bool
handle Picture
pic ((Double
lowerX,Double
lowerY),(Double
lowerX,Double
upperY),(Double
upperX,Double
upperY),(Double
upperX,Double
lowerY))

handle :: Picture -> (Point,Point,Point,Point) -> Bool
handle :: Picture -> (Point, Point, Point, Point) -> Bool
handle (PRec ReifyPicture Picture
p) corners :: (Point, Point, Point, Point)
corners@(Point
a,Point
b,Point
c,Point
d) = case ReifyPicture Picture
p of
  Rectangle Double
x Double
y -> Double -> Double -> Bool
rectangleCheck Double
x Double
y
  ThickRectangle Double
t Double
x Double
y -> Double -> Double -> Bool
rectangleCheck (Double
xDouble -> Double -> Double
forall a. Num a => a -> a -> a
+Double
tDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2) (Double
yDouble -> Double -> Double
forall a. Num a => a -> a -> a
+Double
tDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2)
  SolidRectangle Double
x Double
y -> Double -> Double -> Bool
rectangleCheck Double
x Double
y
  Circle Double
r -> Double -> Bool
circleCheck Double
r
  ThickCircle Double
t Double
r -> Double -> Bool
circleCheck (Double
rDouble -> Double -> Double
forall a. Num a => a -> a -> a
+Double
tDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2)
  SolidCircle Double
r -> Double -> Bool
circleCheck Double
r
  Polygon [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  SolidPolygon [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  ThickPolygon Double
t [Point]
ps -> [Point] -> Bool
pointCheck ([Point] -> Bool) -> [Point] -> Bool
forall a b. (a -> b) -> a -> b
$ Double -> [Point] -> [Point]
forall {b}. Fractional b => b -> [(b, b)] -> [(b, b)]
thickenLine Double
t [Point]
ps
  ClosedCurve [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  SolidClosedCurve [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  ThickClosedCurve Double
t [Point]
ps -> [Point] -> Bool
pointCheck ([Point] -> Bool) -> [Point] -> Bool
forall a b. (a -> b) -> a -> b
$ Double -> [Point] -> [Point]
forall {b}. Fractional b => b -> [(b, b)] -> [(b, b)]
thickenLine Double
t [Point]
ps
  Polyline [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  ThickPolyline Double
t [Point]
ps -> [Point] -> Bool
pointCheck ([Point] -> Bool) -> [Point] -> Bool
forall a b. (a -> b) -> a -> b
$ Double -> [Point] -> [Point]
forall {b}. Fractional b => b -> [(b, b)] -> [(b, b)]
thickenLine Double
t [Point]
ps
  Curve [Point]
ps -> [Point] -> Bool
pointCheck [Point]
ps
  ThickCurve Double
t [Point]
ps -> [Point] -> Bool
pointCheck ([Point] -> Bool) -> [Point] -> Bool
forall a b. (a -> b) -> a -> b
$ Double -> [Point] -> [Point]
forall {b}. Fractional b => b -> [(b, b)] -> [(b, b)]
thickenLine Double
t [Point]
ps
  Sector Double
_ Double
_ Double
r -> Double -> Bool
circleCheck Double
r
  Arc Double
_ Double
_ Double
r -> Double -> Bool
circleCheck Double
r
  ThickArc Double
t Double
_ Double
_ Double
r -> Double -> Bool
circleCheck (Double
rDouble -> Double -> Double
forall a. Num a => a -> a -> a
+Double
tDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2)
  Lettering Text
t -> Text -> Bool
textCheck Text
t
  StyledLettering TextStyle
_ Font
_ Text
t ->  Text -> Bool
textCheck Text
t
  Color Color
_ Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point, Point, Point, Point)
corners
  Translate Double
x Double
y Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point -> Point)
-> (Point, Point, Point, Point) -> (Point, Point, Point, Point)
forall {t} {d}. (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 (Point -> Point -> Point
vectorDifference (Double
x,Double
y)) (Point, Point, Point, Point)
corners
  Scale Double
x Double
y Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point -> Point)
-> (Point, Point, Point, Point) -> (Point, Point, Point, Point)
forall {t} {d}. (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 (Double -> Double -> Point -> Point
scaledPoint (Double
1Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
x) (Double
1Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
y)) (Point, Point, Point, Point)
corners
  Dilate Double
fac Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point -> Point)
-> (Point, Point, Point, Point) -> (Point, Point, Point, Point)
forall {t} {d}. (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 (Double -> Point -> Point
dilatedPoint (Double
1Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
fac)) (Point, Point, Point, Point)
corners
  Rotate Double
angle Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point -> Point)
-> (Point, Point, Point, Point) -> (Point, Point, Point, Point)
forall {t} {d}. (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 (Double -> Point -> Point
rotatedPoint (-Double
angle)) (Point, Point, Point, Point)
corners
  Reflect Double
angle Picture
q -> Picture
q Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point -> Point)
-> (Point, Point, Point, Point) -> (Point, Point, Point, Point)
forall {t} {d}. (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 (Double -> Point -> Point
reflectedPoint Double
angle) (Point, Point, Point, Point)
corners
  Clip Double
x Double
y Picture
_ -> Double -> Double -> Bool
rectangleCheck Double
x Double
y
  Pictures [Picture]
ps -> (Picture -> Bool) -> [Picture] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all (Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point, Point, Point, Point)
corners) [Picture]
ps
  And Picture
p1 Picture
p2 -> Picture
p1 Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point, Point, Point, Point)
corners Bool -> Bool -> Bool
&& Picture
p2 Picture -> (Point, Point, Point, Point) -> Bool
`handle` (Point, Point, Point, Point)
corners
  ReifyPicture Picture
CoordinatePlane -> Double -> Double -> Bool
rectangleCheck Double
20 Double
20
  ReifyPicture Picture
Logo -> Double -> Double -> Bool
rectangleCheck Double
18 Double
7
  ReifyPicture Picture
Blank -> Bool
True
  where
    epsilon :: Double
epsilon = Double
0.005
    pointCheck :: [Point] -> Bool
pointCheck = (Point -> Bool) -> [Point] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all Point -> Bool
inRect
    thickenLine :: b -> [(b, b)] -> [(b, b)]
thickenLine b
t = ((b, b) -> (b, b)) -> [(b, b)] -> [(b, b)]
forall a b. (a -> b) -> [a] -> [b]
map ((b -> b) -> (b, b) -> (b, b)
forall a b. (a -> b) -> (a, a) -> (b, b)
both (b -> b -> b
forall a. Num a => a -> a -> a
+b
tb -> b -> b
forall a. Fractional a => a -> a -> a
/b
2))
    distance :: Point -> Point -> Double
distance Point
v1 Point
v2 =
      let diff :: Point
diff = Point -> Point -> Point
vectorDifference Point
v2 Point
v1
      in  Point -> Point -> Double
crossProduct Point
diff Point
v1 Double -> Double -> Double
forall a. Fractional a => a -> a -> a
/ Point -> Double
vectorLength Point
diff

    circleCheck :: Double -> Bool
circleCheck Double
r = Point -> Bool
inRect (Double
0,Double
0) Bool -> Bool -> Bool
&& ((Point, Point) -> Bool) -> [(Point, Point)] -> Bool
forall (t :: * -> *) a. Foldable t => (a -> Bool) -> t a -> Bool
all (\(Point
v1,Point
v2) -> Point -> Point -> Double
distance Point
v1 Point
v2 Double -> Double -> Double
forall a. Num a => a -> a -> a
+ Double
epsilon Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
>= Double
r) [(Point
a,Point
b),(Point
b,Point
c),(Point
c,Point
d),(Point
d,Point
a)]

    rectangleCheck :: Double -> Double -> Bool
rectangleCheck Double
x Double
y = [Point] -> Bool
pointCheck [(-(Double
xDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2),-(Double
yDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2)), (-(Double
xDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2),Double
yDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2), (Double
xDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2,Double
yDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2), (Double
xDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2,-(Double
yDouble -> Double -> Double
forall a. Fractional a => a -> a -> a
/Double
2))]
    textCheck :: Text -> Bool
textCheck Text
t = Double -> Double -> Bool
rectangleCheck (Int -> Double
forall a b. (Integral a, Num b) => a -> b
fromIntegral (Int -> Double) -> Int -> Double
forall a b. (a -> b) -> a -> b
$ Text -> Int
T.length Text
t) Double
1

    inRect :: Point -> Bool
inRect Point
point =
      let
        ab :: Point
ab = Point -> Point -> Point
vectorDifference Point
b Point
a
        ad :: Point
ad = Point -> Point -> Point
vectorDifference Point
d Point
a
        ap :: Point
ap = Point -> Point -> Point
vectorDifference Point
point Point
a
      in
        -Double
epsilon Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Point -> Point -> Double
dotProduct Point
ap Point
ab Bool -> Bool -> Bool
&& Point -> Point -> Double
dotProduct Point
ap Point
ab Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Point -> Point -> Double
dotProduct Point
ab Point
ab Double -> Double -> Double
forall a. Num a => a -> a -> a
+ Double
epsilon Bool -> Bool -> Bool
&&
        -Double
epsilon Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Point -> Point -> Double
dotProduct Point
ap Point
ad Bool -> Bool -> Bool
&& Point -> Point -> Double
dotProduct Point
ap Point
ad Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
<= Point -> Point -> Double
dotProduct Point
ad Point
ad Double -> Double -> Double
forall a. Num a => a -> a -> a
+ Double
epsilon

    mapAll4 :: (t -> d) -> (t, t, t, t) -> (d, d, d, d)
mapAll4 t -> d
f (t
w,t
x,t
y,t
z) = (t -> d
f t
w, t -> d
f t
x, t -> d
f t
y, t -> d
f t
z)


validThickness :: Double -> Double
validThickness :: Double -> Double
validThickness Double
t
  | Double
t Double -> Double -> Bool
forall a. Ord a => a -> a -> Bool
< Double
0     = String -> Double
forall a. HasCallStack => String -> a
error String
"The line width must be non-negative."
  | Bool
otherwise = Double
t