项目作者: danieljharvey

项目描述 :
Utilities to attach purescript-stylesheet to purescript-react
高级语言: PureScript
项目地址: git://github.com/danieljharvey/purescript-react-stylesheet.git


purescript-react-stylesheet

Utilities to use Purescript Stylesheet with Purescript React. Demo app here.

Purescript Stylesheet is a Virtual Stylesheet that allows you to dynamically add styles to a CSS Stylesheet. This library provides components that provide and consume a Virtual Stylesheet via React Context.

What?

Purescript Stylesheet allows you to create styles for your app that change depending on state. You provide functions from props to CSS and Stylesheet takes care of plopping them into a real stylesheet in your browser and making things look nice.

Like Styled Components?

Yeah, that kind of thing. The ideas in this library aren’t really new, I just wanted something like this in Purescript.

How do I use it then?

Good question.

We’ll start by creating a StyleContext.

  1. import React.Stylesheet
  2. styleContext :: StyleContext
  3. styleContext
  4. = createStyleContext (SProxy :: SProxy "hey-nice-styles-buddy")

This contains three things -

  1. Provider - a React class that provides the Stylesheet superpowers via React Context.
  2. Consumer - a React class that can be used to consume the Stylesheet superpowers
  3. Elements - a big pile of pre-wrapped DOM elements that will probably be the most useful part.

We need to put the Provider at the tree of our app.

  1. mainClass :: React.ReactClass { }
  2. mainClass = React.component "Main" component
  3. where
  4. component this =
  5. pure { state: {
  6. { todos: []
  7. }
  8. , render: pure
  9. $ React.createLeafElement styleContext.provider
  10. { children: [ render ] }
  11. }
  12. where
  13. render state = ...

In this example the render function then takes care of the rest of your app.

What now?

Let’s make an element with styles!

We define styles with a CSSRuleSet. It takes a type that defines the props it can receive. Here is one that takes no props (which we represent with unit).

  1. containerStyle :: CSSRuleSet Unit
  2. containerStyle
  3. = str """
  4. margin: 20px;
  5. padding: 20px;
  6. border-radius: 10px;
  7. display: flex;
  8. flex-direction: row;
  9. justify-content: center;
  10. """

We are using Purescript’s triple quote thing to smash a big lump of stupid CSS into a CSSRuleSet. Now let’s give them to an element…

  1. container :: Array Props -> Array ReactElement -> ReactElement
  2. container
  3. = styleContext.elements.div containerStyles unit

We’ve taken the div element from our StyleContext, and added these styles to it. Now we can use this container element in our app:

  1. render = container [] [ text "I am some text in an attractive looking box" ]

Good stuff.

Now, what about something smarter? Let’s have something with props.

  1. data TrafficLights
  2. = Red
  3. | Yellow
  4. | Green
  5. trafficStyle :: CSSRuleSet TrafficLights
  6. trafficStyle
  7. = str """
  8. border: none;
  9. border-radius: 20px;
  10. width: 40px;
  11. height: 40px;
  12. """
  13. <> fun (\light -> case light of
  14. Red -> "background-color: red;"
  15. Yellow -> "background-color: yellow;"
  16. Green -> "background-color: green;")
  17. trafficLight :: TrafficLights -> ReactElement
  18. trafficLight colour
  19. = styleContext.elements.div trafficStyle colour [] {}

We have have a colour-changing traffic light!

Working example:

The full working example is here.

Why just Purescript React? Why not [insert thing]?

If this doesn’t turn out to be an utter disaster, I would like to port it for use in React Basic and Halogen. If you are good at those things and want to help, by all means get in touch.

Why plain text CSS and not something more type-safe?

Three reasons:

  1. Lazyness
  2. Easy to paste existing CSS in for ease of adoption
  3. Lazyness

Docs?

Yes, on Pursuit111