Styled-components: Shortcut variables for function

Created on 30 Aug 2017  路  3Comments  路  Source: styled-components/styled-components

HI! Thanks for your work, it's great!
When I'm using theme parameters I must write realy large code with function:
color: ${props => props.theme.primaryColor}
thanks for ES6 i can write this as
color: ${({theme}) => theme.primaryColor}
but it's not getting any better

Would be great if I get just one parameter (without some calculation) by some "styled-components-variable" synthesis like:
color: =>primaryColor
It can look better with using $ prefix, but.

So, main question is: could your parser convert =>var to ${p=>p.theme.var} and then to interpret result expression?

Most helpful comment

We could do that, but we won't.

Let me elaborate on why: We strongly believe in using the power of tools we have available. In styled-components case that means JavaScript and CSS; it's the reason why you can write actual CSS vs writing CSS as objects.

The same thing applies to interpolations, we love love love having the power of JavaScript to style our apps. JavaScript can do all the things a preprocessor can do (including sass-style mixins) and many more.

So if JavaScript can do it already, why should we introduce arbitrary custom syntax for it? It makes the code harder to understand, our API surfaces increases and some people will hate it all for the sake of saving a couple of keystrokes? On top of that, where do you draw the line what to add custom syntax for and what not?

Rather than trying to find the right answer to highly subjective questions and trying to battle an onslaught of proposals all to save half a second we prefer to just use the power of the tools we already have available, in this case JavaScript.

I hope that explains!

All 3 comments

We could do that, but we won't.

Let me elaborate on why: We strongly believe in using the power of tools we have available. In styled-components case that means JavaScript and CSS; it's the reason why you can write actual CSS vs writing CSS as objects.

The same thing applies to interpolations, we love love love having the power of JavaScript to style our apps. JavaScript can do all the things a preprocessor can do (including sass-style mixins) and many more.

So if JavaScript can do it already, why should we introduce arbitrary custom syntax for it? It makes the code harder to understand, our API surfaces increases and some people will hate it all for the sake of saving a couple of keystrokes? On top of that, where do you draw the line what to add custom syntax for and what not?

Rather than trying to find the right answer to highly subjective questions and trying to battle an onslaught of proposals all to save half a second we prefer to just use the power of the tools we already have available, in this case JavaScript.

I hope that explains!

I understand the reason behind this opinionated decision, however I disagree.

My argument is: $var (or @var and the kind) is NOT some _arbitrary custom syntax_, it's a _de facto standard_ implemented by practically ALL css-on-steroid solutions.

I recently use props.theme.var very frequently in a company project. In my case, we have an in house stylesheets lib written in less, which is maintained by another team. Then on top of the in house lib, my team adopt styled-components (btw, really awesome work guy! 馃憦), and we obviously have an need to use all the predefined less @variables in styled-components ALOT.

It was actually a torture having to write ${props => props.theme.var} repeatedly, neither were we happy with import { var_1, var_2 } from 'in-house-less-lib' all the time. We missed less-like @variables so badly.

With all due respect, I hope you can take a second look on this matter. People just have practical need in case like mine. I understand the where-to-draw-the-line anxiety as project maintainer, but feature like $var is clearly above that line. It's the missing little brother of things like nested css, if you bring it back, I believe it'll receive welcome from more people than you thought.

In the end, after looking into your source code, I found it's just a matter of 10 lines of code to add-in such feature. So i did it, added my 10-liner, wrap and re-export your lib, make a webpack alias, done. So far nobody gets hurt, everybody is happy.

Here's my 10 liner:

/* Thanks to the way your code is put together,
 * I only need to touch ./lib/css.js 
*/
const $varRegExp = /\$[a-zA-Z\-\_0-9]+/g
const $var2Function = $var => (props) => (props.theme[$var.slice(1)])

const transfromDollarStr = string => {
  const matched = string.match($varRegExp)
  if (!matched) return string
  return interleave(string.split($varRegExp), matched.map($var2Function))
}

const css = (strings, ...interpolations) => (
  flatten(interleave(strings.map(transfromDollarStr), interpolations))
)
Was this page helpful?
0 / 5 - 0 ratings