Theme-ui: Feature: customize Select arrow

Created on 24 Aug 2020  路  4Comments  路  Source: system-ui/theme-ui

Is your feature request related to a problem? Please describe.

While working on a small design system together with a designer, I realized that there seems to be no way to (fully) customize the Select's <DownArrow /> svg at the moment.

Describe the solution you'd like

Optimally, a way to fully customize the appearance from the theme.
But to my knowledge, there is no browser-compatible, CSS-only way to achieve that?

Another option is an opt-in prop to specify your own SVG, which would default to the current one?

Describe alternatives you've considered

Its style can be overriden using selectors such as shown in this issue, but for instance the path it uses cannot (not in a native, browsers-compatible way?)

// theme.js
forms: {
  select: {
    '& + svg': {
      width: '1em',
      height: '1em',
      ml: '-1.5em',
      fill: 'none',
      path: {
        // this does not seem to work in Firefox
        d: 'path("M5 8L8 11L11 8")',
        stroke: 'currentColor',
        strokeLinecap: 'round',
        strokeLinejoin: 'round'
      }
    }
  }
}

Right now I have built a custom Select with a useLayoutEffect() hook overriding those, but I find that a bit cumbersome, also I do not like the query selectors that are tied to the DOM of the current Select (which could change in the future):

/** @jsx jsx */
import { Select, jsx } from 'theme-ui';
import { useRef, useLayoutEffect } from 'react';

const CustomSelect = (props) => {
  const select = useRef();

  useLayoutEffect(() => {
    if (select.current && select.current.parentNode) {
      const svg = select.current.parentNode.querySelector('svg');

      if (svg) {
        const path = svg.querySelector('path');

        if (path) {
          svg.setAttribute('viewBox', '0 0 16 16');
          path.setAttribute('d', 'M5 8L8 11L11 8');
        }
      }
    }
  });

  return (
    <Select
      ref={select}
      sx={{
        '& + svg': {
          width: '1em',
          height: '1em',
          ml: '-1.5em',
          fill: 'none',
          path: {
            stroke: 'currentColor',
            strokeLinecap: 'round',
            strokeLinejoin: 'round'
          }
        }
      }}
      {...props}
    />
  );
};

Additional context

https://theme-ui.com/components/select

I would gladly contribute by adding an opt-in prop to override that arrow, but just wanted to ask if you think this is relevant before? (And just in case I missed a nicer way?)

Most helpful comment

1232 is merged, we can close!

All 4 comments

@flo-sch - I am going down the list of issues trying to clean up the back log and since there was a more recent Select arrow issue, I missed yours - sorry about that.

Can you please check this #1177 issue and see if the PR will also work for your use-case?

Hi @atanasster, I have not tried it but, just by looking at it, I feel that this PR is all I need :)

@flo-sch - thanks a lot for the confirmation. Not sure if this will make it into 0.4.0 (I assume not since 0.4.0 is practically ready, but the version right after)

1232 is merged, we can close!

Was this page helpful?
0 / 5 - 0 ratings

Related issues

vojtaholik picture vojtaholik  路  3Comments

Everspace picture Everspace  路  3Comments

jxnblk picture jxnblk  路  4Comments

cwgw picture cwgw  路  3Comments

johno picture johno  路  3Comments