optics-core-0.3: src/Optics/IxGetter.hs
-- |
-- Module: Optics.IxGetter
-- Description: An indexed version of a 'Optics.Getter.Getter'.
--
-- An 'IxGetter' is an indexed version of a 'Optics.Getter.Getter'. See the
-- "Indexed optics" section of the overview documentation in the @Optics@ module
-- of the main @optics@ package for more details on indexed optics.
--
module Optics.IxGetter
(
-- * Formation
IxGetter
-- * Introduction
, ito
, selfIndex
-- * Elimination
, iview
, iviews
-- * Subtyping
, A_Getter
) where
import Data.Profunctor.Indexed
import Optics.Internal.Bi
import Optics.Internal.Indexed
import Optics.Internal.Optic
import Optics.Internal.Utils
-- | Type synonym for an indexed getter.
type IxGetter i s a = Optic' A_Getter (WithIx i) s a
-- | Build an indexed getter from a function.
--
-- >>> iview (ito id) ('i', 'x')
-- ('i','x')
ito :: (s -> (i, a)) -> IxGetter i s a
ito f = Optic (lmap f . ilinear uncurry' . rphantom)
{-# INLINE ito #-}
-- | Use a value itself as its own index. This is essentially an indexed version
-- of 'Optics.Iso.equality'.
selfIndex :: IxGetter a a a
selfIndex = ito (\a -> (a, a))
{-# INLINE selfIndex #-}
-- | View the value pointed to by an indexed getter.
iview
:: (Is k A_Getter, is `HasSingleIndex` i)
=> Optic' k is s a -> s -> (i, a)
iview o = iviews o (,)
{-# INLINE iview #-}
-- | View the function of the value pointed to by an indexed getter.
iviews
:: (Is k A_Getter, is `HasSingleIndex` i)
=> Optic' k is s a -> (i -> a -> r) -> s -> r
iviews o = \f ->
runIxForget (getOptic (castOptic @A_Getter o) (IxForget f)) id
{-# INLINE iviews #-}