git.iko.soy/rowtype-yoga/psfp
on 134dc56 help sign in
143 lines 4.7 kB history raw
1module Container.Sidebar where
3import Prelude
4import Data.Foldable (intercalate)
5import Data.Monoid (guard)
6import Effect (Effect)
7import JSS (jss, jssClasses)
8import React.Basic (JSX)
9import React.Basic.DOM as R
10import React.Basic.Events (handler_)
11import React.Basic.Hooks (ReactComponent, component, element)
12import React.Basic.Hooks as React
13import Yoga.SVG.Icon (ActiveArrowDirection(..), mkMenu)
14import Yoga.Theme.Styles (makeStylesJSS)
15import Yoga.Theme.Types (CSSTheme)
17mkSidebar ∷
18 Effect
19 ( ReactComponent
20 { kids ∷ Array JSX
21 , modifyCollapsed ∷ (Boolean -> Boolean) -> Effect Unit
22 , collapsed ∷ Boolean
23 }
24 )
25mkSidebar = do
26 useStyles <-
27 makeStylesJSS
28 $ jssClasses \(theme ∷ CSSTheme) ->
29 { sidebar:
30 jss
31 { background: theme.interfaceColourLighter
32 , fontFamily: intercalate ", " theme.textFontFamily
33 , borderRadius: "0 12px 12px 0"
34 , color: theme.textColour
35 , position: "absolute"
36 , marginTop: "calc(100vh + 20px)"
37 , paddingBottom: "20px"
38 , display: "flex"
39 , flexDirection: "column"
40 , transition: "0.4s"
41 , transitionTimingFunction: "cubic-bezier(.56,-0.32,.36,1)"
42 , overflowX: "hidden"
43 , zIndex: 24
44 , boxShadow:
45 "0px 0px 60px rgba(0,0,0,0."
46 <> (if theme.isLight then "17" else "43")
47 <> ")"
48 }
49 , sidebarCollapsed: jss { width: "70px" }
50 , sidebarExpanded: jss { width: "220px" }
51 , logo:
52 jss
53 { width: "60px"
54 , height: "60px"
55 , padding: "0 5px 0 5px"
56 , transition: "0.2s ease-in-out"
57 , transitionDelay: "0.1s"
58 , alignSelf: "flex-end"
59 }
60 , logoCollapsed:
61 jss
62 {} -- transform: "rotate(180deg)"}
63 }
64 menu <- mkMenu
65 component "Sidebar" \{ kids, collapsed, modifyCollapsed } -> React.do
66 classes <- useStyles {}
67 pure
68 $ R.nav
69 { className: classes.sidebar <> " " <> if collapsed then classes.sidebarCollapsed else classes.sidebarExpanded
70 , children:
71 [ R.ul
72 { className: classes.logo <> " " <> guard collapsed classes.logoCollapsed
73 , onClick: handler_ $ (modifyCollapsed not)
74 , children:
75 [ element menu
76 { activeArrowDirection: if collapsed then ArrowPointsRight else ArrowPointsLeft }
77 ]
78 }
79 ]
80 <> kids
81 }
83mkSidebarLink ∷ Effect (ReactComponent { name ∷ String, icon ∷ JSX, collapsed ∷ Boolean })
84mkSidebarLink = do
85 useStyles <-
86 makeStylesJSS
87 $ jssClasses \(theme ∷ CSSTheme) ->
88 { sidebarEntry:
89 jss
90 { fontFamily: intercalate ", " theme.headingFontFamily
91 , alignSelf: "flex-end"
92 , justifyContent: "space-between"
93 , alignContent: "stretch"
94 , color: theme.textColour
95 , gridArea: "nav"
96 , display: "flex"
97 , flexDirection: "row"
98 , overflowX: "hidden"
99 , width: "190px"
100 , paddingLeft: "5px"
101 , borderRadius: "5px 0 0 5px"
102 , cursor: "pointer"
103 , "&:hover":
104 { background: theme.highlightColour
105 }
106 -- , "&:hover": jss{ opacity: "1.0"}
107 }
108 , label:
109 jss
110 { fontFamily: intercalate ", " theme.textFontFamily
111 , color: theme.textColour
112 , paddingLeft: "20px"
113 , textTransform: "uppercase"
114 , lineHeight: "60px"
115 , fontSize: "1.4em"
116 }
117 , icon:
118 jss
119 { width: "50px"
120 , height: "50px"
121 , padding: "5px 10px 5px 5px"
122 , transition: "0.2s ease-in-out"
123 , transitionDelay: "0.1s"
124 , alignSelf: "flex-end"
125 , fill: theme.textColour
126 }
127 }
128 component "SidebarLink" \{ name, icon, collapsed } -> React.do
129 classes <- useStyles {}
130 pure
131 $ R.li
132 { className: classes.sidebarEntry
133 , children:
134 [ R.div
135 { className: classes.label
136 , children: [ R.text name ]
137 }
138 , R.div
139 { className: classes.icon
140 , children: [ icon ]
141 }
142 ]
143 }