Last active
July 8, 2017 09:00
-
-
Save paulyoung/eedd47b5495a59523b1a11eaef70d490 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
-- | Based on http://www.fewbutripe.com/swift/html/dsl/2017/06/29/composable-html-views-in-swift.html | |
module Main where | |
import Prelude | |
import React as R | |
import React.DOM as R | |
import React.DOM.Props as RP | |
import Thermite hiding (defaultMain) as T | |
import Thermite.Try as T | |
type View a = a -> Array R.ReactElement | |
headerContent :: View Unit | |
headerContent _ = | |
[ R.h1' [ R.text "Few, but ripe..." ] | |
, R.menu' [ R.a [ RP.href "/about"] | |
[ R.text "About" ] | |
, R.a [ RP.href "/hire-me"] | |
[ R.text "Hire Me" ] | |
, R.a [ RP.href "/talks"] | |
[ R.text "talks" ] | |
] | |
] | |
type FooterData = | |
{ authorName :: String | |
, email :: String | |
, twitter :: String | |
} | |
footerContent :: View FooterData | |
footerContent { authorName, email, twitter } = | |
[ R.ul' [ R.li' [ R.text authorName ] | |
, R.li' [ R.text email ] | |
, R.li' [ R.text $ "@" <> twitter ] | |
] | |
, R.p' [ R.text "Articles about math, functional programming and the Swift programming language." ] | |
] | |
type Article = | |
{ date :: String | |
, title :: String | |
-- more fields, e.g. author, body, categories, ... | |
} | |
articleCallout :: View Article | |
articleCallout article = | |
[ R.span' [ R.text article.date ] | |
, R.a [ RP.href "#" ] | |
[ R.text article.title ] | |
] | |
articlesList :: View (Array Article) | |
articlesList articles = | |
[ R.ul' $ articles >>= articleCallout >>> R.li' >>> pure | |
] | |
type SiteLayoutData a = | |
{ contentData :: a | |
, footerData :: FooterData | |
} | |
siteLayout :: forall a . View a -> View (SiteLayoutData a) | |
siteLayout content = | |
let | |
combined { contentData, footerData } = | |
(R.header' >>> pure <$> headerContent) unit | |
<> content contentData | |
<> (R.footer' >>> pure <$> footerContent) footerData | |
in | |
R.body' >>> pure >>> R.html' >>> pure <$> combined | |
siteLayoutData = | |
{ contentData: [ { date: "Jun 22, 2017" | |
, title: "Type-Safe HTML in Swift" | |
} | |
, { date: "Feb 17, 2015" | |
, title: "Algebraic Structure and Protocols" | |
} | |
, { date: "Jan 6, 2015" | |
, title: "Proof in Functions" | |
} | |
] | |
, footerData: { authorName: "Brandon Williams" | |
, email: "[email protected]" | |
, twitter: "mbrandonw" | |
} | |
} | |
render :: T.Render _ _ _ | |
render _ _ _ _ = siteLayout articlesList siteLayoutData | |
spec :: T.Spec _ _ _ _ | |
spec = T.simpleSpec T.defaultPerformAction render | |
main = T.defaultMain spec unit |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment