-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | ReactJS binding using Glazier and Pipes.Fluid -- -- ReactJS binding using Glazier and Pipes.Fluid, which is more -- functional and composable than Elm/Flux. @package glazier-react @version 0.3.0.1 -- | Contains commons utilities when defining your own widget module Glazier.React.ReactDOM -- | Using a React Element (first arg) give React rendering control over a -- DOM element (second arg). This should only be called for the topmost -- component. render :: JSVal -> JSVal -> IO () module Glazier.React.Model -- | Lens to the callbacks and interactions with React class HasPlan c pln | c -> pln plan :: HasPlan c pln => Lens' c pln -- | Lens to the pure model for state and rendering. class HasModel c mdl | c -> mdl model :: HasModel c mdl => Lens' c mdl -- | A record of Model and Plan data Design mdl pln Design :: mdl -> pln -> Design mdl pln [_model] :: Design mdl pln -> mdl [_plan] :: Design mdl pln -> pln -- | All designs should be disposable to make it easier for cleanup of -- callbacks. class HasDesign c mdl pln | c -> mdl pln design :: HasDesign c mdl pln => Lens' c (Design mdl pln) -- | Frame is a Mvar of Design. React rendering callback uses this MVar for -- rendering. type Frame mdl pln = MVar (Design mdl pln) class HasFrame c mdl pln | c -> mdl pln frame :: HasFrame c mdl pln => Lens' c (Frame mdl pln) -- | A record of Design and Frame. data SuperModel mdl pln SuperModel :: Design mdl pln -> Frame mdl pln -> SuperModel mdl pln [_design] :: SuperModel mdl pln -> Design mdl pln [_frame] :: SuperModel mdl pln -> Frame mdl pln class (HasDesign c mdl pln, HasFrame c mdl pln) => HasSuperModel c mdl pln | c -> mdl pln superModel :: HasSuperModel c mdl pln => Lens' c (SuperModel mdl pln) instance GHC.Generics.Generic (Glazier.React.Model.SuperModel mdl pln) instance GHC.Generics.Generic (Glazier.React.Model.Design mdl pln) instance (Control.Disposable.Disposing pln, Control.Disposable.Disposing mdl) => Control.Disposable.Disposing (Glazier.React.Model.Design mdl pln) instance Glazier.React.Model.HasPlan (Glazier.React.Model.Design mdl pln) pln instance Glazier.React.Model.HasModel (Glazier.React.Model.Design mdl pln) mdl instance Glazier.React.Model.HasDesign (Glazier.React.Model.Design mdl pln) mdl pln instance Glazier.React.Model.HasFrame (Glazier.React.Model.Frame mdl pln) mdl pln instance Control.Disposable.Disposing (Glazier.React.Model.Design mdl pln) => Control.Disposable.Disposing (Glazier.React.Model.SuperModel mdl pln) instance Glazier.React.Model.HasSuperModel (Glazier.React.Model.SuperModel mdl pln) mdl pln instance Glazier.React.Model.HasFrame (Glazier.React.Model.SuperModel mdl pln) mdl pln instance Glazier.React.Model.HasDesign (Glazier.React.Model.SuperModel mdl pln) mdl pln instance Glazier.React.Model.HasPlan (Glazier.React.Model.SuperModel mdl pln) pln instance Glazier.React.Model.HasModel (Glazier.React.Model.SuperModel mdl pln) mdl -- | This module based on ReactFluxPropertiesAndEvents.hs. module Glazier.React.Event -- | The object that dispatched the event. -- https://developer.mozilla.org/en-US/docs/Web/API/Event/target data DOMEventTarget -- | The native event -- https://developer.mozilla.org/en-US/docs/Web/API/Event data DOMEvent -- | Every event in React is a synthetic event, a cross-browser wrapper -- around the native event. SyntheticEvent must only be used in -- the first part of eventHandler. data SyntheticEvent -- | Using the NFData idea from ReactFluxPropertiesAndEvents.hs -- React re-uses SyntheticEvent from a pool, which means it may no longer -- be valid if we lazily parse it. However, we still want lazy parsing so -- we don't parse unnecessary fields. Additionally, we don't want to -- block during the event handling.The reason this is a problem is -- because Javascript is single threaded, but Haskell is lazy. Therefore -- GHCJS threads are a strange mixture of synchronous and asynchronous -- threads, where a synchronous thread might be converted to an -- asynchronous thread if a "black hole" is encountered. See -- https://github.com/ghcjs/ghcjs-base/blob/master/GHCJS/Concurrent.hs -- This safe interface requires two input functions: 1. a function to -- reduce SyntheticEvent to a NFData. The mkEventCallback will ensure -- that the NFData is forced which will ensure all the required fields -- from Synthetic event has been parsed. This function must not block. 2. -- a second function that uses the NFData. This function is allowed to -- block. mkEventHandler results in a function that you can safely pass -- into syncCallback1 with ContinueAsync. eventHandler :: NFData a => (evt -> a) -> (a -> b) -> (evt -> b) -- | a monadic version of eventHandler The monad's effects must not block! eventHandlerM :: (Monad m, NFData a) => (evt -> m a) -> (a -> m b) -> (evt -> m b) -- | Every SyntheticEvent can be parsed to an Event. -- Event must only be used in the first part of -- eventHandler. data Event Event :: Bool -> Bool -> DOMEventTarget -> Bool -> Int -> Bool -> DOMEvent -> DOMEventTarget -> Int -> JSString -> Event preventDefault :: SyntheticEvent -> IO () isDefaultPrevented :: SyntheticEvent -> Bool stopPropagation :: SyntheticEvent -> IO () isPropagationStopped :: SyntheticEvent -> Bool parseEvent :: SyntheticEvent -> IO Event -- | Mouse and Drag/Drop events MouseEvent must only be used in the -- first part of eventHandler. -- https://facebook.github.io/react/docs/events.html#mouse-events -- https://developer.mozilla.org/en-US/docs/Web/Events Event names -- (eventType) onClick (click) onContextMenu (contextmenu) onDoubleClick -- (dblclick) onDrag (drag) onDragEnd (dragend) onDragEnter (dragenter) -- onDragExit (dragexit) onDragLeave (dragleave) onDragOver (dragover) -- onDragStart (dragstart) onDrop (drop) onMouseDown (mousedown) -- onMouseEnter (mouseenter) onMouseLeave (mouseleave) onMouseMove -- (mousemove) onMouseOut (mouseout) onMouseOver (mouseover) onMouseUp -- (mouseup) data MouseEvent MouseEvent :: Bool -> Int -> Int -> Int -> Int -> Bool -> (JSString -> Bool) -> Bool -> Int -> Int -> DOMEventTarget -> Int -> Int -> Bool -> MouseEvent -- | We can lie about this not being in IO because within the strict part -- of eventHandlerM the SyntheticEvent is effectively immutable. parseMouseEvent :: SyntheticEvent -> IO (Maybe MouseEvent) -- | Keyboard events KeyboardEvent must only be used in the first -- part of eventHandler. -- https://facebook.github.io/react/docs/events.html#keyboard-events -- Event names (eventType) onKeyDown (keydown) onKeyPress (keypress) -- onKeyUp (keyyp) data KeyboardEvent KeyboardEvent :: Bool -> Int -> Bool -> (JSString -> Bool) -> JSString -> Int -> JSString -> Int -> Bool -> Bool -> Bool -> Int -> KeyboardEvent -- | We can lie about this not being in IO because within the strict part -- of eventHandlerM the SyntheticEvent is effectively immutable. parseKeyboardEvent :: SyntheticEvent -> IO (Maybe KeyboardEvent) instance GHCJS.Internal.Types.IsJSVal Glazier.React.Event.DOMEventTarget instance GHCJS.Marshal.Internal.PToJSVal Glazier.React.Event.DOMEventTarget instance JavaScript.Extras.Recast.ToJS Glazier.React.Event.DOMEventTarget instance JavaScript.Extras.Recast.FromJS Glazier.React.Event.DOMEventTarget instance GHCJS.Internal.Types.IsJSVal Glazier.React.Event.DOMEvent instance GHCJS.Marshal.Internal.PToJSVal Glazier.React.Event.DOMEvent instance JavaScript.Extras.Recast.ToJS Glazier.React.Event.DOMEvent instance JavaScript.Extras.Recast.FromJS Glazier.React.Event.DOMEvent instance GHCJS.Internal.Types.IsJSVal Glazier.React.Event.SyntheticEvent instance GHCJS.Marshal.Internal.PToJSVal Glazier.React.Event.SyntheticEvent instance JavaScript.Extras.Recast.ToJS Glazier.React.Event.SyntheticEvent instance JavaScript.Extras.Recast.FromJS Glazier.React.Event.SyntheticEvent -- | HtmlT inspired monad for creating ReactElements module Glazier.React.Element data ReactElement -- | Unfortunately, ReactJS did not export an easy way to check if -- something is a ReactElement, although they do so in the internal code -- with REACT_ELEMENT_TYPE. This function allow coercing a ReactElement -- from a JSVal and is marked unsafe as a reminder that the coersion is -- unchecked. This function is required when receiving ReactElement from -- javascript (eg in a callback) or to interface with foreign React -- Elements. unsafeCoerceElement :: JSVal -> ReactElement -- | Create a react element (with children) from a HashMap of properties mkBranchElement :: JSVal -> [Property] -> [ReactElement] -> IO ReactElement -- | Create a react element (with no children) from a HashMap of properties mkLeafElement :: JSVal -> [Property] -> IO ReactElement -- | Not an IO action because JSString is immutable textElement :: JSString -> ReactElement -- | React only allows a single top most element. Provide a handly function -- to wrap a list of ReactElements inside a div if required. If -- there is only one element in the list, then nothing is changed. mkCombinedElements :: [ReactElement] -> IO ReactElement instance GHCJS.Internal.Types.IsJSVal Glazier.React.Element.ReactElement instance GHCJS.Marshal.Internal.PToJSVal Glazier.React.Element.ReactElement instance JavaScript.Extras.Recast.ToJS Glazier.React.Element.ReactElement -- | HtmlT inspired monad for creating ReactElements module Glazier.React.Markup data ReactMarkup ElementMarkup :: ReactElement -> ReactMarkup TextMarkup :: JSString -> ReactMarkup BranchMarkup :: BranchParam -> ReactMarkup LeafMarkup :: LeafParam -> ReactMarkup -- | The parameters required to create a branch ReactElement with children data BranchParam BranchParam :: JSVal -> [Property] -> (DList ReactMarkup) -> BranchParam -- | The parameters required to create a leaf ReactElement (no children) data LeafParam LeafParam :: JSVal -> [Property] -> LeafParam -- | Create ReactElements from a AtomMarkup fromMarkup :: ReactMarkup -> IO (ReactElement) -- | Monadic generator of ReactActom. It is a CPS-style WriterT (ie a -- StateT) to build up a function build up a computations to generate a -- '[AtomMarkup]'. You can use runStateT with an initial state of -- mempty. newtype ReactMlT m a ReactMlT :: StateT (DList ReactMarkup) m a -> ReactMlT m a [runReactMlT] :: ReactMlT m a -> StateT (DList ReactMarkup) m a type ReactMl = ReactMlT Identity -- | To use an exisitng ReactElement fromElement :: Applicative m => ReactElement -> ReactMlT m () -- | Convert the ReactMlt to [R.ReactElement] toElements :: MonadIO io => ReactMlT io () -> io [ReactElement] -- | Render the ReactMlt under a Glazier window markedWindow :: MonadIO io => WindowT s (ReactMlT io) () -> WindowT s io [ReactElement] -- | Fully render the ReactMlt into a [R.ReactElement] markedElements :: MonadIO io => WindowT s (ReactMlT io) () -> s -> io [ReactElement] -- | Fully render the ReactMlt into a R.ReactElement markedElement :: MonadIO io => WindowT s (ReactMlT io) () -> s -> io ReactElement -- | For text content txt :: Applicative m => JSString -> ReactMlT m () -- | For the contentless elements: eg br_ lf :: Applicative m => JSVal -> [Property] -> ReactMlT m () -- | For the contentful elements: eg div_ bh :: Functor m => JSVal -> [Property] -> ReactMlT m a -> ReactMlT m a instance Control.Monad.Morph.MFunctor Glazier.React.Markup.ReactMlT instance Control.Monad.IO.Class.MonadIO m => Control.Monad.IO.Class.MonadIO (Glazier.React.Markup.ReactMlT m) instance Control.Monad.Fix.MonadFix m => Control.Monad.Fix.MonadFix (Glazier.React.Markup.ReactMlT m) instance GHC.Base.MonadPlus m => GHC.Base.MonadPlus (Glazier.React.Markup.ReactMlT m) instance GHC.Base.MonadPlus m => GHC.Base.Alternative (Glazier.React.Markup.ReactMlT m) instance Control.Monad.Fail.MonadFail m => Control.Monad.Fail.MonadFail (Glazier.React.Markup.ReactMlT m) instance GHC.Base.Functor m => GHC.Base.Functor (Glazier.React.Markup.ReactMlT m) instance GHC.Base.Monad m => GHC.Base.Applicative (Glazier.React.Markup.ReactMlT m) instance GHC.Base.Monad m => GHC.Base.Monad (Glazier.React.Markup.ReactMlT m) instance GHC.Base.Monad m => Control.Monad.State.Class.MonadState (Data.DList.DList Glazier.React.Markup.ReactMarkup) (Glazier.React.Markup.ReactMlT m) instance (Data.Semigroup.Semigroup a, GHC.Base.Monad m) => Data.Semigroup.Semigroup (Glazier.React.Markup.ReactMlT m a) instance (GHC.Base.Monoid a, GHC.Base.Monad m) => GHC.Base.Monoid (Glazier.React.Markup.ReactMlT m a) module Glazier.React.Component -- | A newtype wrapper to give a noop disposable instance to React -- components This allows generic deriving of model Adaptors. data ReactComponent mkComponent :: IO ReactComponent instance Control.Disposable.Disposing Glazier.React.Component.ReactComponent instance GHCJS.Internal.Types.IsJSVal Glazier.React.Component.ReactComponent instance GHCJS.Marshal.Internal.PToJSVal Glazier.React.Component.ReactComponent instance JavaScript.Extras.Recast.ToJS Glazier.React.Component.ReactComponent module Glazier.React.Maker -- | DSL for IO effects required during making widget models and callbacks -- Maker remembers the action type to allow mapAction for -- changing the action type by parent widgets. The model type does not -- need to be changed, so it is hidden in the GADT existential. data Maker act nxt [MkHandler] :: (JSVal -> MaybeT IO [act]) -> (Callback (JSVal -> IO ()) -> nxt) -> Maker act nxt [MkEmptyFrame] :: (Frame mdl pln -> nxt) -> Maker act nxt [MkRenderer] :: Frame mdl pln -> (JSVal -> WindowT (Design mdl pln) ReactMl ()) -> (Callback (JSVal -> IO JSVal) -> nxt) -> Maker act nxt [PutFrame] :: Frame mdl pln -> Design mdl pln -> nxt -> Maker act nxt [GetComponent] :: (ReactComponent -> nxt) -> Maker act nxt getComponent :: forall m_aq4C act_apOY. MonadFree (Maker act_apOY) m_aq4C => m_aq4C ReactComponent putFrame :: forall (mdl_XpPm :: Type) (pln_XpPo :: Type) m_aq4y act_apOY. MonadFree (Maker act_apOY) m_aq4y => Frame mdl_XpPm pln_XpPo -> Design mdl_XpPm pln_XpPo -> m_aq4y () mkRenderer :: forall (mdl_XpPi :: Type) (pln_XpPk :: Type) m_aq4t act_apOY. MonadFree (Maker act_apOY) m_aq4t => Frame mdl_XpPi pln_XpPk -> (JSVal -> WindowT (Design mdl_XpPi pln_XpPk) ReactMl ()) -> m_aq4t (Callback (JSVal -> IO JSVal)) mkEmptyFrame :: forall (mdl_XpPe :: Type) (pln_XpPg :: Type) m_aq4q act_apOY. MonadFree (Maker act_apOY) m_aq4q => m_aq4q (Frame mdl_XpPe pln_XpPg) mkHandler :: forall m_aq4m act_apOY. MonadFree (Maker act_apOY) m_aq4m => (JSVal -> MaybeT IO [act_apOY]) -> m_aq4m (Callback (JSVal -> IO ())) -- | Allows changing the action type of Maker mapAction :: (act -> act') -> Maker act a -> Maker act' a instance GHC.Base.Functor (Glazier.React.Maker.Maker act) module Glazier.React.Widget class (Disposing (ModelOf w), Disposing (PlanOf w)) => IsWidget w where type CommandOf w :: * type ActionOf w :: * type ModelOf w :: * type PlanOf w :: * where { type family CommandOf w :: *; type family ActionOf w :: *; type family ModelOf w :: *; type family PlanOf w :: *; } mkPlan :: IsWidget w => w -> Frame (ModelOf w) (PlanOf w) -> F (Maker (ActionOf w)) (PlanOf w) window :: IsWidget w => w -> WindowT (Design (ModelOf w) (PlanOf w)) (ReactMlT Identity) () gadget :: IsWidget w => w -> GadgetT (ActionOf w) (SuperModel (ModelOf w) (PlanOf w)) Identity (DList (CommandOf w)) -- | Contains everything you need to make the model, render, and run the -- event processing. data Widget c a m p Widget :: (Frame m p -> F (Maker a) p) -> (WindowT (Design m p) (ReactMlT Identity) ()) -> (GadgetT a (SuperModel m p) Identity (DList c)) -> Widget c a m p mkSuperModel :: IsWidget w => w -> ModelOf w -> F (Maker (ActionOf w)) (SuperModel (ModelOf w) (PlanOf w)) instance (Control.Disposable.Disposing m, Control.Disposable.Disposing p) => Glazier.React.Widget.IsWidget (Glazier.React.Widget.Widget c a m p) module Glazier.React.Maker.Run -- | This is called synchronously by React to render the DOM. This must not -- block! onRender :: MVar s -> (JSVal -> WindowT s (ReactMlT IO) ()) -> JSVal -> IO JSVal mkActionCallback :: Output act -> (JSVal -> MaybeT IO [act]) -> IO (Callback (JSVal -> IO ())) run :: ReactComponent -> Output act -> Maker act (IO a) -> IO a -- | Common functions used by command interpreters module Glazier.React.Command.Run componentSetState :: HasSuperModel sm mdl pln => sm -> [Property] -> JSVal -> IO () module Glazier.React.Command -- | Just change the state to something different so the React -- pureComponent will call render() renderCmd :: Monad m => (sm -> -- [JE.Property] -> J.JSVal -> cmd) -> G.GadgetT act sm m cmd -- The resulting command should be interpreted using -- componentSetState basicRenderCmd :: MonadState sm m => Lens' sm Int -> Getter sm JSVal -> (sm -> [Property] -> JSVal -> cmd) -> m cmd