    -----------------------------------------------------------------------------
    -- |
    -- Module      :  Graphics.Rendering.Chart.Plot.Points
    -- Copyright   :  (c) Tim Docker 2006, 2014
    -- License     :  BSD-style (see chart/COPYRIGHT)
    --
    -- Functions to plot sets of points, marked in various styles.

    {-# LANGUAGE TemplateHaskell #-}

    module Graphics.Rendering.Chart.Plot.Points(
        PlotPoints(..),

        -- * Accessors
        -- | These accessors are generated by template haskell

        plot_points_title,
        plot_points_style,
        plot_points_values,
    ) where

    import Control.Lens
    import Graphics.Rendering.Chart.Geometry
    import Graphics.Rendering.Chart.Drawing
    import Graphics.Rendering.Chart.Plot.Types
    import Data.Default.Class

    -- | Value defining a series of datapoints, and a style in
    --   which to render them.
    data PlotPoints x y = PlotPoints {
        _plot_points_title  :: String,
        _plot_points_style  :: PointStyle,
        _plot_points_values :: [(x,y)]
    }

    instance ToPlot PlotPoints where
        toPlot p = Plot {
            _plot_render     = renderPlotPoints p,
            _plot_legend     = [(_plot_points_title p, renderPlotLegendPoints p)],
            _plot_all_points = (map fst pts, map snd pts)
        }
          where
            pts = _plot_points_values p

    renderPlotPoints :: PlotPoints x y -> PointMapFn x y -> BackendProgram ()
    renderPlotPoints p pmap =
        mapM_ (drawPoint ps . pmap') (_plot_points_values p)
      where
        pmap' = mapXY pmap
        ps = _plot_points_style p

    renderPlotLegendPoints :: PlotPoints x y -> Rect -> BackendProgram ()
    renderPlotLegendPoints p (Rect p1 p2) = do
        drawPoint ps (Point (p_x p1)              y)
        drawPoint ps (Point ((p_x p1 + p_x p2)/2) y)
        drawPoint ps (Point (p_x p2)              y)

      where
        ps = _plot_points_style p
        y = (p_y p1 + p_y p2)/2

    instance Default (PlotPoints x y) where
      def = PlotPoints
        { _plot_points_title  = ""
        , _plot_points_style  = def
        , _plot_points_values = []
        }

    $( makeLenses ''PlotPoints )