-- | This module contains mainly the informative 'IsMedia' type class and -- corresponding type classes for media lenses. module Data.MediaBus.Media.Media ( IsMedia() , MediaDescription(..) , HasMedia(..) , type HasMedia' , media' , type HasMediaL , type HasMediaL' , EachMedia(..) , type EachMedia' , eachMedia' , type EachMediaL , type EachMediaL' ) where import Control.DeepSeq import Control.Lens -- * Media -- | Very abstract class of media content types. The only universal feature is that it has a static description. class ( NFData i , Show (MediaDescription i) -- TODO HasDuration instance?? ) => IsMedia i -- | A proxy type to display static media info via a 'Show' instance data MediaDescription i where MkShowMedia :: (Show (MediaDescription i)) => MediaDescription i -- * Media container 'Lens'es -- | Types that contain an 'IsMedia' instance. class (IsMedia (MediaFrom s), IsMedia (MediaTo t)) => HasMedia s t where type MediaFrom s type MediaTo t -- | A 'Lens' for the media within 's' media :: Lens s t (MediaFrom s) (MediaTo t) -- | Types that contain an 'IsMedia' instance. type HasMedia' s = (IsMedia (MediaFrom s), HasMedia s s, MediaFrom s ~ MediaTo s) -- | A simple 'Lens' for the media within 's' media' :: HasMedia' s => Lens' s (MediaFrom s) media' = media -- | Types that contain an 'IsMedia' instance with the traditional lens-like type parameters type HasMediaL s t a b = (IsMedia a, HasMedia s t, MediaFrom s ~ a, MediaTo t ~ b) -- | Like 'HasMedia' but with the **simple** lens-like type parameters type HasMediaL' s a = (IsMedia a, HasMedia s s, MediaFrom s ~ a, MediaTo s ~ a, MediaFrom s ~ MediaTo s) -- * Media container 'Traversal's -- | Types that contain zero or more 'IsMedia' instance. class (IsMedia (MediaFromE s), IsMedia (MediaToE t)) => EachMedia s t where -- | The contained input media type, since the name 'MediaFrom' was taken -- , this is named 'MediaFromE' where the @E@ is supposed to hint at the fact -- that this class is called 'EachMedia'. type MediaFromE s type MediaToE t -- | A 'Traversal' for the media within 's' eachMedia :: Traversal s t (MediaFromE s) (MediaToE t) default eachMedia :: HasMediaL s t (MediaFromE s) (MediaToE t) => Traversal s t (MediaFromE s) (MediaToE t) eachMedia = media -- | Types that contain zero or more 'IsMedia' instance. type EachMedia' s = (IsMedia (MediaFromE s), EachMedia s s, MediaFromE s ~ MediaToE s) -- | A simple 'Traversal' for the media within 's' eachMedia' :: EachMedia' s => Traversal' s (MediaFromE s) eachMedia' = eachMedia -- | Types that contain zero or more 'IsMedia' instance with the traditional lens-like type parameters type EachMediaL s t a b = (IsMedia a, EachMedia s t, MediaFromE s ~ a, MediaToE t ~ b) -- | Like 'EachMedia' but with the **simple** lens-like type parameters type EachMediaL' s a = (IsMedia a, EachMedia s s, MediaFromE s ~ a, MediaToE s ~ a, MediaFromE s ~ MediaToE s)