<commit_before>{-# LANGUAGE ExistentialQuantification, DeriveDataTypeable #-}
module Graphics.Vty.Widgets.Collections
    ( Collection
    , CollectionError(..)
    , newCollection
    , addToCollection
    , setCurrent
    )
where

import Data.Typeable
    ( Typeable
    )
import Control.Monad.Trans
    ( MonadIO
    , liftIO
    )
import Control.Exception
    ( Exception
    , throw
    )
import Graphics.Vty
    ( DisplayRegion
    , Image
    , Key
    , Modifier
    )
import Graphics.Vty.Widgets.Core
    ( Widget
    , WidgetImpl(..)
    , FocusGroup
    , RenderContext
    , (<~)
    , (<~~)
    , getFocusGroup
    , updateWidgetState
    , setCurrentPosition
    , newWidget
    , updateWidget
    , render
    , handleKeyEvent
    , getState
    , onKeyPressed
    , growHorizontal
    , growVertical
    )

-- Ultimately we'd want support for "stacks" to provide things like
-- overlaid dialogs, but for now we'll just implement a "collection"
-- type which allows is to have a collection of widgets and switch
-- between them.

data CollectionError = EmptyCollection
                     | BadCollectionIndex Int
                       deriving (Show, Typeable)

instance Exception CollectionError

data Entry = forall a. (Show a) => Entry (Widget a)

data Collection =
    Collection { entries :: [Entry]
               , currentEntryNum :: Int
               }

instance Show Collection where
    show (Collection es num) = concat [ "Collection { "
                                      , "entries = <", show $ length es, "entries>"
                                      , ", currentEntryNum = ", show num
                                      , " }"
                                      ]

renderEntry :: (MonadIO m) => Entry -> DisplayRegion -> RenderContext -> m Image
renderEntry (Entry w) = render w

positionEntry :: Entry -> DisplayRegion -> IO ()
positionEntry (Entry w) = setCurrentPosition w

entryHandleKeyEvent :: (MonadIO m) => Entry -> Key -> [Modifier] -> m Bool
entryHandleKeyEvent (Entry w) k mods = handleKeyEvent w k mods

entryFocusGroup :: Entry -> IO (Maybe (Widget FocusGroup))
entryFocusGroup (Entry w) = getFocusGroup w

entryGrowHorizontal :: Entry -> IO Bool
entryGrowHorizontal (Entry w) = growHorizontal w

entryGrowVertical :: Entry -> IO Bool
entryGrowVertical (Entry w) = growVertical w

newCollection :: (MonadIO m) => m (Widget Collection)
newCollection = do
  wRef <- newWidget
  updateWidget wRef $ \w ->
      w { state = Collection { entries = []
                             , currentEntryNum = -1
                             }
        -- XXX technically this should defer to whichever entry is
        -- current!
        , growHorizontal_ = \st -> do
            case currentEntryNum st of
              (-1) -> throw EmptyCollection
              i -> do
                let e = entries st !! i
                liftIO $ entryGrowHorizontal e

        , growVertical_ = \st -> do
            case currentEntryNum st of
              (-1) -> throw EmptyCollection<commit_msg>Collections: stale comment<commit_after>{-# LANGUAGE ExistentialQuantification, DeriveDataTypeable #-}
module Graphics.Vty.Widgets.Collections
    ( Collection
    , CollectionError(..)
    , newCollection
    , addToCollection
    , setCurrent
    )
where

import Data.Typeable
    ( Typeable
    )
import Control.Monad.Trans
    ( MonadIO
    , liftIO
    )
import Control.Exception
    ( Exception
    , throw
    )
import Graphics.Vty
    ( DisplayRegion
    , Image
    , Key
    , Modifier
    )
import Graphics.Vty.Widgets.Core
    ( Widget
    , WidgetImpl(..)
    , FocusGroup
    , RenderContext
    , (<~)
    , (<~~)
    , getFocusGroup
    , updateWidgetState
    , setCurrentPosition
    , newWidget
    , updateWidget
    , render
    , handleKeyEvent
    , getState
    , onKeyPressed
    , growHorizontal
    , growVertical
    )

-- Ultimately we'd want support for "stacks" to provide things like
-- overlaid dialogs, but for now we'll just implement a "collection"
-- type which allows is to have a collection of widgets and switch
-- between them.

data CollectionError = EmptyCollection
                     | BadCollectionIndex Int
                       deriving (Show, Typeable)

instance Exception CollectionError

data Entry = forall a. (Show a) => Entry (Widget a)

data Collection =
    Collection { entries :: [Entry]
               , currentEntryNum :: Int
               }

instance Show Collection where
    show (Collection es num) = concat [ "Collection { "
                                      , "entries = <", show $ length es, "entries>"
                                      , ", currentEntryNum = ", show num
                                      , " }"
                                      ]

renderEntry :: (MonadIO m) => Entry -> DisplayRegion -> RenderContext -> m Image
renderEntry (Entry w) = render w

positionEntry :: Entry -> DisplayRegion -> IO ()
positionEntry (Entry w) = setCurrentPosition w

entryHandleKeyEvent :: (MonadIO m) => Entry -> Key -> [Modifier] -> m Bool
entryHandleKeyEvent (Entry w) k mods = handleKeyEvent w k mods

entryFocusGroup :: Entry -> IO (Maybe (Widget FocusGroup))
entryFocusGroup (Entry w) = getFocusGroup w

entryGrowHorizontal :: Entry -> IO Bool
entryGrowHorizontal (Entry w) = growHorizontal w

entryGrowVertical :: Entry -> IO Bool
entryGrowVertical (Entry w) = growVertical w

newCollection :: (MonadIO m) => m (Widget Collection)
newCollection = do
  wRef <- newWidget
  updateWidget wRef $ \w ->
      w { state = Collection { entries = []
                             , currentEntryNum = -1
                             }
        , growHorizontal_ = \st -> do
            case currentEntryNum st of
              (-1) -> throw EmptyCollection
              i -> do
                let e = entries st !! i
                liftIO $ entryGrowHorizontal e

        , growVertical_ = \st -> do
            case currentEntryNum st of
              (-1) -> throw EmptyCollection
{'fraction_non_alphanumeric': 0.08836278759586529, 'fraction_numerical': 0.0010003334444814939, 'mean_word_length': 1.9683325086590797, 'pattern_counts': {'":': 0, '<': 11, '<?xml version=': 0, '>': 47, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 10, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2479185', 'n_tokens_mistral': 1619, 'n_tokens_neox': 1574, 'n_words': 495}