{-# OPTIONS_HADDOCK show-extensions #-} {-# LANGUAGE DataKinds , FlexibleContexts , FlexibleInstances , GADTs , PolyKinds , ScopedTypeVariables , TypeOperators #-} {-| Module : Graphics.QML.DataModel.Vinyl Copyright : (c) Marcin Mrotek, 2015 License : BSD3 Maintainer : marcin.jan.mrotek@gmail.com Stability : experimental HsQML DataModel instances recursively defined for all 'Rec's. 'SetupColumns' requires the field labels to be instances of 'Typeable'. -} module Graphics.QML.DataModel.Vinyl where import Graphics.QML.DataModel.Generic import Graphics.QML.DataModel.FFI import Control.Exception import Data.Vinyl import Data.Type.List import Data.Typeable import GHC.TypeLits instance CountFields (Rec f '[]) where countFields _ = 0 instance CountFields (Rec f xs) => CountFields (Rec f (x ': xs)) where countFields _ = 1 + countFields (undefined :: sing (Rec f xs)) instance Mock (Rec f '[]) where mock = RNil instance (Mock (f x), Mock (Rec f xs)) => Mock (Rec f (x ': xs)) where mock = mock :& mock instance QtTable (Rec f '[]) where getColumn i _ = throwIO $ ColumnIndexOutOfBounds i 0 instance ( KnownNat (Length xs) , QtField (f x) , QtTable (Rec f xs) ) => QtTable (Rec f (x ': xs)) where getColumn i (r :& rs) = if i >= end then qtField r else getColumn i rs where end = lengthVal (undefined :: sing xs) instance SetupColumns (Rec f '[]) where setupColumns _ _ = return () instance ( KnownNat (Length xs) , Typeable x , SetupColumns (Rec f xs) ) => SetupColumns (Rec f (x ': xs)) where setupColumns hndl _ = do addHaskellModelRole hndl ix . show $ typeRep (undefined :: proxy x) setupColumns hndl (undefined :: sing (Rec f xs)) where ix = lengthVal (undefined :: sing xs) lengthVal :: forall sing xs a. ( KnownNat (Length xs) , Integral a ) => sing xs -> a -- |Integral value of the length of a type-level list. lengthVal _ = fromIntegral $ natVal (undefined :: proxy (Length xs))