{-# LANGUAGE CPP #-} -- | Provide definition for some higher level objects (only slightly) module Graphics.Rasterific.ComplexPrimitive( rectangle , roundedRectangle , circle , ellipse ) where #if !MIN_VERSION_base(4,8,0) import Control.Applicative( (<$>) ) #endif import Graphics.Rasterific.Linear( V2( .. ), (^+^), (^*) ) import Graphics.Rasterific.Line import Graphics.Rasterific.CubicBezier import Graphics.Rasterific.Types -- | Generate a list of primitive representing a circle. -- -- > fill $ circle (V2 100 100) 75 -- -- <> -- circle :: Point -- ^ Circle center in pixels -> Float -- ^ Circle radius in pixels -> [Primitive] circle center radius = CubicBezierPrim . transform mv <$> cubicBezierCircle where mv p = (p ^* radius) ^+^ center -- | Generate a list of primitive representing an ellipse. -- -- > fill $ ellipse (V2 100 100) 75 30 -- -- <> -- ellipse :: Point -> Float -> Float -> [Primitive] ellipse center rx ry = CubicBezierPrim . transform mv <$> cubicBezierCircle where mv (V2 x y) = V2 (x * rx) (y * ry) ^+^ center -- | Generate a list of primitive representing a -- rectangle -- -- > fill $ rectangle (V2 30 30) 150 100 -- -- <> -- rectangle :: Point -- ^ Corner upper left -> Float -- ^ Width in pixel -> Float -- ^ Height in pixel -> [Primitive] rectangle p@(V2 px py) w h = LinePrim <$> lineFromPath [ p, V2 (px + w) py, V2 (px + w) (py + h), V2 px (py + h), p ] -- | Generate a list of primitive representing a rectangle -- with rounded corner. -- -- > fill $ roundedRectangle (V2 10 10) 150 150 20 10 -- -- <> -- roundedRectangle :: Point -- ^ Corner upper left -> Float -- ^ Width in pixel -> Float -- ^ Height in pixel. -> Float -- ^ Radius along the x axis of the rounded corner. In pixel. -> Float -- ^ Radius along the y axis of the rounded corner. In pixel. -> [Primitive] roundedRectangle (V2 px py) w h rx ry = [ CubicBezierPrim . transform (^+^ V2 xFar yNear) $ cornerTopR , LinePrim $ Line (V2 xFar py) (V2 xNear py) , CubicBezierPrim . transform (^+^ V2 (px + rx) (py + ry)) $ cornerTopL , LinePrim $ Line (V2 px yNear) (V2 px yFar) , CubicBezierPrim . transform (^+^ V2 (px + rx) yFar) $ cornerBottomL , LinePrim $ Line (V2 xNear (py + h)) (V2 xFar (py + h)) , CubicBezierPrim . transform (^+^ V2 xFar yFar) $ cornerBottomR , LinePrim $ Line (V2 (px + w) yFar) (V2 (px + w) yNear) ] where xNear = px + rx xFar = px + w - rx yNear = py + ry yFar = py + h - ry (cornerBottomR : cornerTopR : cornerTopL : cornerBottomL:_) = transform (\(V2 x y) -> V2 (x * rx) (y * ry)) <$> cubicBezierCircle