module Gargantext.Components.Nodes.Lists where import Gargantext.Prelude (Unit, bind, const, discard, pure, show, unit, ($), (<>)) import Data.Maybe (Maybe(..)) import Data.Tuple (fst, snd) import Data.Tuple.Nested ((/\)) import Effect (Effect) import Effect.Aff (launchAff_) import Reactix as R import Reactix.DOM.HTML as H import Record as Record import Toestand as T import Gargantext.AsyncTasks as GAT import Gargantext.Components.Forest as Forest import Gargantext.Components.NgramsTable.Loader (clearCache) import Gargantext.Components.Node (NodePoly(..)) import Gargantext.Components.Nodes.Corpus (loadCorpusWithChild) import Gargantext.Components.Nodes.Corpus.Types ( getCorpusInfo, CorpusInfo(..), Hyperdata(..) ) import Gargantext.Components.Nodes.Lists.Tabs as Tabs import Gargantext.Components.Nodes.Lists.Types ( CacheState(..), ListsLayoutControls, SidePanelState(..) , initialControls, toggleSidePanelState ) import Gargantext.Components.Table as Table import Gargantext.Hooks.Loader (useLoader) import Gargantext.Sessions (Session, sessionId, getCacheState, setCacheState) import Gargantext.Types as GT import Gargantext.Utils.Reactix as R2 import Gargantext.Utils.Toestand as T2 here :: R2.Here here = R2.here "Gargantext.Components.Nodes.Lists" type ListsWithForest = ( forestProps :: Record Forest.Props , listsProps :: Record CommonProps ) listsWithForest :: R2.Component ListsWithForest listsWithForest = R.createElement listsWithForestCpt listsWithForestCpt :: R.Component ListsWithForest listsWithForestCpt = here.component "listsWithForest" cpt where cpt { forestProps, listsProps: listsProps@{ session } } _ = do controls <- initialControls pure $ Forest.forestLayoutWithTopBar forestProps [ topBar { controls } [] , listsLayout (Record.merge listsProps { controls }) [] , H.div { className: "side-panel" } [ sidePanel { controls, session } [] ] ] type TopBarProps = ( controls :: Record ListsLayoutControls ) topBar :: R2.Component TopBarProps topBar = R.createElement topBarCpt topBarCpt :: R.Component TopBarProps topBarCpt = here.component "topBar" cpt where cpt { controls } _ = do -- empty for now because the button is moved to the side panel pure $ H.div {} [] -- H.ul { className: "nav navbar-nav" } [ -- H.li {} [ -- sidePanelToggleButton { state: controls.showSidePanel } [] -- ] -- ] -- head (goes to top bar) type CommonProps = ( nodeId :: Int , reloadForest :: T.Box T2.Reload , reloadRoot :: T.Box T2.Reload , session :: Session , sessionUpdate :: Session -> Effect Unit , tasks :: T.Box (Maybe GAT.Reductor) ) type Props = ( controls :: Record ListsLayoutControls | CommonProps ) type WithTreeProps = ( handed :: GT.Handed | Props ) listsLayout :: R2.Component Props listsLayout = R.createElement listsLayoutCpt listsLayoutCpt :: R.Component Props listsLayoutCpt = here.component "listsLayout" cpt where cpt path@{ nodeId, session } _ = do let sid = sessionId session pure $ listsLayoutWithKey $ Record.merge path { key: show sid <> "-" <> show nodeId } type KeyProps = ( key :: String | Props ) listsLayoutWithKey :: Record KeyProps -> R.Element listsLayoutWithKey props = R.createElement listsLayoutWithKeyCpt props [] listsLayoutWithKeyCpt :: R.Component KeyProps listsLayoutWithKeyCpt = here.component "listsLayoutWithKey" cpt where cpt { controls, nodeId, reloadForest, reloadRoot, session, sessionUpdate, tasks } _ = do let path = { nodeId, session } cacheState <- R.useState' $ getCacheState CacheOn session nodeId useLoader path loadCorpusWithChild $ \corpusData@{ corpusId, corpusNode: NodePoly poly, defaultListId } -> let { date, hyperdata : Hyperdata h, name } = poly CorpusInfo { authors, desc, query } = getCorpusInfo h.fields in R.fragment [ Table.tableHeaderLayout { afterCacheStateChange , cacheState , date , desc , key: "listsLayoutWithKey-header-" <> (show $ fst cacheState) , query , title: "Corpus " <> name , user: authors } , Tabs.tabs { cacheState , corpusData , corpusId , key: "listsLayoutWithKey-tabs-" <> (show $ fst cacheState) , reloadForest , reloadRoot , session , sidePanelTriggers: controls.triggers , tasks } ] where afterCacheStateChange cacheState = do launchAff_ $ clearCache unit sessionUpdate $ setCacheState session nodeId cacheState type SidePanelProps = ( controls :: Record ListsLayoutControls , session :: Session ) sidePanel :: R2.Component SidePanelProps sidePanel = R.createElement sidePanelCpt sidePanelCpt :: R.Component SidePanelProps sidePanelCpt = here.component "sidePanel" cpt where cpt { controls: { triggers: { toggleSidePanel, triggerSidePanel } } , session } _ = do showSidePanel <- R.useState' InitialClosed R.useEffect' $ do let toggleSidePanel' _ = snd showSidePanel toggleSidePanelState triggerSidePanel' _ = snd showSidePanel $ const Opened R2.setTrigger toggleSidePanel toggleSidePanel' R2.setTrigger triggerSidePanel triggerSidePanel' (mCorpusId /\ setMCorpusId) <- R.useState' Nothing (mListId /\ setMListId) <- R.useState' Nothing (mNodeId /\ setMNodeId) <- R.useState' Nothing let mainStyle = case fst showSidePanel of Opened -> { display: "block" } _ -> { display: "none" } let closeSidePanel _ = snd showSidePanel $ const Closed pure $ H.div { style: mainStyle } [ H.div { className: "header" } [ H.span { className: "btn btn-danger", on: { click: closeSidePanel } } [ H.span { className: "fa fa-times" } [] ]] , sidePanelDocView { session } [] ] type SidePanelDocView = ( session :: Session ) sidePanelDocView :: R2.Component SidePanelDocView sidePanelDocView = R.createElement sidePanelDocViewCpt sidePanelDocViewCpt :: R.Component SidePanelDocView sidePanelDocViewCpt = here.component "sidePanelDocView" cpt where cpt { session } _ = do -- pure $ H.h4 {} [ H.text txt ] pure $ H.div {} [ H.text "Hello ngrams" ]