@zendeskgarden/react-theming 9.0.0-next.9 → 9.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -10,15 +10,12 @@ import DEFAULT_THEME from './theme/index.js';
10
10
 
11
11
  const ThemeProvider = _ref => {
12
12
  let {
13
- theme,
13
+ theme = DEFAULT_THEME,
14
14
  ...other
15
15
  } = _ref;
16
16
  return React.createElement(ThemeProvider$1, Object.assign({
17
17
  theme: theme
18
18
  }, other));
19
19
  };
20
- ThemeProvider.defaultProps = {
21
- theme: DEFAULT_THEME
22
- };
23
20
 
24
21
  export { ThemeProvider };
@@ -44,26 +44,27 @@ const colors = {
44
44
  recessed: 'neutralHue.1200',
45
45
  subtle: 'neutralHue.1000',
46
46
  emphasis: 'neutralHue.600',
47
- primary: 'primaryHue.900',
48
47
  success: 'successHue.1000',
49
48
  warning: 'warningHue.1000',
50
49
  danger: 'dangerHue.1000',
51
50
  primaryEmphasis: 'primaryHue.600',
52
51
  successEmphasis: 'successHue.600',
53
52
  warningEmphasis: 'warningHue.600',
54
- dangerEmphasis: 'dangerHue.600'
53
+ dangerEmphasis: 'dangerHue.600',
54
+ disabled: 'rgba(neutralHue.500, 100)'
55
55
  },
56
56
  border: {
57
57
  default: 'neutralHue.800',
58
58
  emphasis: 'neutralHue.600',
59
59
  subtle: 'neutralHue.900',
60
- success: 'successHue.800',
61
- warning: 'warningHue.800',
62
- danger: 'dangerHue.800',
60
+ success: 'successHue.900',
61
+ warning: 'warningHue.900',
62
+ danger: 'dangerHue.900',
63
63
  primaryEmphasis: 'primaryHue.600',
64
64
  successEmphasis: 'successHue.600',
65
65
  warningEmphasis: 'warningHue.600',
66
- dangerEmphasis: 'dangerHue.600'
66
+ dangerEmphasis: 'dangerHue.600',
67
+ disabled: 'neutralHue.800'
67
68
  },
68
69
  foreground: {
69
70
  default: 'neutralHue.300',
@@ -75,7 +76,13 @@ const colors = {
75
76
  danger: 'dangerHue.400',
76
77
  successEmphasis: 'successHue.300',
77
78
  warningEmphasis: 'warningHue.300',
78
- dangerEmphasis: 'dangerHue.300'
79
+ dangerEmphasis: 'dangerHue.300',
80
+ disabled: 'neutralHue.700'
81
+ },
82
+ shadow: {
83
+ small: 'rgba(neutralHue.1200, 1100)',
84
+ medium: 'rgba(neutralHue.1200, 800)',
85
+ large: 'rgba(neutralHue.1200, 1000)'
79
86
  }
80
87
  },
81
88
  light: {
@@ -85,14 +92,14 @@ const colors = {
85
92
  recessed: 'neutralHue.100',
86
93
  subtle: 'neutralHue.100',
87
94
  emphasis: 'neutralHue.700',
88
- primary: 'primaryHue.100',
89
95
  success: 'successHue.100',
90
96
  warning: 'warningHue.100',
91
97
  danger: 'dangerHue.100',
92
98
  primaryEmphasis: 'primaryHue.700',
93
99
  successEmphasis: 'successHue.700',
94
100
  warningEmphasis: 'warningHue.700',
95
- dangerEmphasis: 'dangerHue.700'
101
+ dangerEmphasis: 'dangerHue.700',
102
+ disabled: 'rgba(neutralHue.700, 100)'
96
103
  },
97
104
  border: {
98
105
  default: 'neutralHue.300',
@@ -104,7 +111,8 @@ const colors = {
104
111
  primaryEmphasis: 'primaryHue.700',
105
112
  successEmphasis: 'successHue.700',
106
113
  warningEmphasis: 'warningHue.700',
107
- dangerEmphasis: 'dangerHue.700'
114
+ dangerEmphasis: 'dangerHue.700',
115
+ disabled: 'neutralHue.300'
108
116
  },
109
117
  foreground: {
110
118
  default: 'neutralHue.900',
@@ -116,7 +124,13 @@ const colors = {
116
124
  danger: 'dangerHue.700',
117
125
  successEmphasis: 'successHue.900',
118
126
  warningEmphasis: 'warningHue.900',
119
- dangerEmphasis: 'dangerHue.900'
127
+ dangerEmphasis: 'dangerHue.900',
128
+ disabled: 'neutralHue.600'
129
+ },
130
+ shadow: {
131
+ small: 'rgba(neutralHue.1200, 200)',
132
+ medium: 'rgba(neutralHue.1200, 200)',
133
+ large: 'rgba(neutralHue.1200, 200)'
120
134
  }
121
135
  }
122
136
  }
package/dist/esm/index.js CHANGED
@@ -7,7 +7,6 @@
7
7
  export { ThemeProvider } from './elements/ThemeProvider.js';
8
8
  export { default as DEFAULT_THEME } from './elements/theme/index.js';
9
9
  export { default as PALETTE } from './elements/palette/index.js';
10
- export { default as PALETTE_V8 } from './elements/palette/v8.js';
11
10
  export { default as retrieveComponentStyles } from './utils/retrieveComponentStyles.js';
12
11
  export { getArrowPosition } from './utils/getArrowPosition.js';
13
12
  export { getCheckeredBackground } from './utils/getCheckeredBackground.js';
@@ -5,60 +5,49 @@
5
5
  * found at http://www.apache.org/licenses/LICENSE-2.0.
6
6
  */
7
7
  import { css, keyframes } from 'styled-components';
8
- import { math } from 'polished';
8
+ import { stripUnit } from 'polished';
9
9
 
10
- const exponentialSymbols = {
11
- symbols: {
12
- sqrt: {
13
- func: {
14
- symbol: 'sqrt',
15
- f: a => Math.sqrt(a),
16
- notation: 'func',
17
- precedence: 0,
18
- rightToLeft: 0,
19
- argCount: 1
20
- },
21
- symbol: 'sqrt',
22
- regSymbol: 'sqrt\\b'
23
- }
24
- }
25
- };
26
10
  const animationStyles = (position, modifier) => {
27
11
  const property = position.split('-')[0];
28
12
  const animationName = keyframes(["0%,66%{", ":2px;border:transparent;}"], property);
29
13
  return css(["&", "::before,&", "::after{animation:0.3s ease-in-out ", ";}"], modifier, modifier, animationName);
30
14
  };
31
- const positionStyles = (position, size, inset) => {
32
- const margin = math(`${size} / -2`);
33
- const placement = math(`${margin} + ${inset}`);
34
- let clipPath;
15
+ const positionStyles = (position, size, inset, shift) => {
16
+ const defaultInset = 0.3;
17
+ const margin = size / -2;
18
+ const placement = Math.round((margin + inset + defaultInset) * 100) / 100;
19
+ const marginPx = `${margin}px`;
20
+ const placementPx = `${placement}px`;
21
+ const offsetPx = `${size + shift}px`;
35
22
  let positionCss;
36
- let propertyRadius;
23
+ let transform;
37
24
  if (position.startsWith('top')) {
38
- propertyRadius = 'border-bottom-right-radius';
39
- clipPath = 'polygon(100% 0, 100% 1px, 1px 100%, 0 100%, 0 0)';
40
- positionCss = css(["top:", ";right:", ";left:", ";margin-left:", ";"], placement, position === 'top-right' && size, position === 'top' ? '50%' : position === 'top-left' && size, position === 'top' && margin);
25
+ transform = 'rotate(-135deg)';
26
+ positionCss = css(["top:", ";right:", ";left:", ";margin-left:", ";"], placementPx, position === 'top-right' && offsetPx, position === 'top' ? '50%' : position === 'top-left' && offsetPx, position === 'top' && marginPx);
41
27
  } else if (position.startsWith('right')) {
42
- propertyRadius = 'border-bottom-left-radius';
43
- clipPath = 'polygon(100% 0, 100% 100%, calc(100% - 1px) 100%, 0 1px, 0 0)';
44
- positionCss = css(["top:", ";right:", ";bottom:", ";margin-top:", ";"], position === 'right' ? '50%' : position === 'right-top' && size, placement, position === 'right-bottom' && size, position === 'right' && margin);
28
+ transform = 'rotate(-45deg)';
29
+ positionCss = css(["top:", ";right:", ";bottom:", ";margin-top:", ";"], position === 'right' ? '50%' : position === 'right-top' && offsetPx, placementPx, position === 'right-bottom' && offsetPx, position === 'right' && marginPx);
45
30
  } else if (position.startsWith('bottom')) {
46
- propertyRadius = 'border-top-left-radius';
47
- clipPath = 'polygon(100% 0, calc(100% - 1px) 0, 0 calc(100% - 1px), 0 100%, 100% 100%)';
48
- positionCss = css(["right:", ";bottom:", ";left:", ";margin-left:", ";"], position === 'bottom-right' && size, placement, position === 'bottom' ? '50%' : position === 'bottom-left' && size, position === 'bottom' && margin);
31
+ transform = 'rotate(45deg)';
32
+ positionCss = css(["right:", ";bottom:", ";left:", ";margin-left:", ";"], position === 'bottom-right' && offsetPx, placementPx, position === 'bottom' ? '50%' : position === 'bottom-left' && offsetPx, position === 'bottom' && marginPx);
49
33
  } else if (position.startsWith('left')) {
50
- propertyRadius = 'border-top-right-radius';
51
- clipPath = 'polygon(0 100%, 100% 100%, 100% calc(100% - 1px), 1px 0, 0 0)';
52
- positionCss = css(["top:", ";bottom:", ";left:", ";margin-top:", ";"], position === 'left' ? '50%' : position === 'left-top' && size, size, placement, position === 'left' && margin);
34
+ transform = 'rotate(135deg)';
35
+ positionCss = css(["top:", ";bottom:", ";left:", ";margin-top:", ";"], position === 'left' ? '50%' : position === 'left-top' && offsetPx, offsetPx, placementPx, position === 'left' && marginPx);
53
36
  }
54
- return css(["&::before{", ":100%;clip-path:", ";}&::before,&::after{", "}"], propertyRadius, clipPath, positionCss);
37
+ return css(["&::before,&::after{transform:", ";", ";}"], transform, positionCss);
55
38
  };
56
39
  function arrowStyles(position) {
57
40
  let options = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : {};
58
- const size = options.size || '6px';
59
- const inset = options.inset || '0';
60
- const squareSize = math(`${size} * 2 / sqrt(2)`, exponentialSymbols);
61
- return css(["position:relative;&::before{border-width:inherit;border-style:inherit;border-color:transparent;background-clip:content-box;}&::after{z-index:-1;border:inherit;box-shadow:inherit;}&::before,&::after{position:absolute;transform:rotate(45deg);background-color:inherit;box-sizing:inherit;width:", ";height:", ";content:'';}", ";", ";"], squareSize, squareSize, positionStyles(position, squareSize, inset), options.animationModifier && animationStyles(position, options.animationModifier));
41
+ const inset = stripUnit(options.inset || '0');
42
+ const size = stripUnit(options.size || '6');
43
+ const shift = stripUnit(options.shift || '0');
44
+ const sizeOffset = 2;
45
+ const squareSize = size * 2 / Math.sqrt(2) + sizeOffset;
46
+ const squareSizeRounded = Math.round(squareSize * 100) / 100;
47
+ const squareSizePx = `${squareSizeRounded}px`;
48
+ const afterOffset = 0;
49
+ const beforeOffset = afterOffset + 2;
50
+ return css(["position:relative;&::before,&::after{position:absolute;border-width:inherit;border-style:inherit;background-color:inherit;width:", ";height:", ";content:'';box-sizing:inherit;}&::before{border-color:inherit;clip-path:polygon(100% ", "px,", "px 100%,100% 100%);}&::after{border-color:transparent;background-clip:content-box;clip-path:polygon(100% ", "px,", "px 100%,100% 100%);}", ";", ";"], squareSizePx, squareSizePx, beforeOffset, beforeOffset, afterOffset, afterOffset, positionStyles(position, squareSizeRounded, inset, shift), options.animationModifier && animationStyles(position, options.animationModifier));
62
51
  }
63
52
 
64
- export { arrowStyles as default, exponentialSymbols };
53
+ export { arrowStyles as default };
@@ -4,14 +4,12 @@
4
4
  * Use of this source code is governed under the Apache License, Version 2.0
5
5
  * found at http://www.apache.org/licenses/LICENSE-2.0.
6
6
  */
7
- import { valid, scale } from 'chroma-js';
8
- import { rgba, darken, lighten } from 'polished';
7
+ import { getScale, parseToRgba } from 'color2k';
8
+ import { getContrast, rgba, darken, lighten } from 'polished';
9
9
  import get from 'lodash.get';
10
10
  import memoize from 'lodash.memoize';
11
11
  import DEFAULT_THEME from '../elements/theme/index.js';
12
- import PALETTE from '../elements/palette/index.js';
13
12
 
14
- const PALETTE_SIZE = Object.keys(PALETTE.blue).length;
15
13
  const adjust = (color, expected, actual) => {
16
14
  if (expected !== actual) {
17
15
  const amount = Math.abs(expected - actual) / 100 * 0.05;
@@ -42,6 +40,78 @@ const toHex = (hue, shade, offset, scheme) => {
42
40
  }
43
41
  return retVal;
44
42
  };
43
+ const isValidColor = maybeColor => {
44
+ let retVal = ['currentcolor', 'inherit', 'transparent'].includes(maybeColor);
45
+ if (!retVal) {
46
+ try {
47
+ retVal = !!parseToRgba(maybeColor);
48
+ } catch {
49
+ retVal = false;
50
+ }
51
+ }
52
+ return retVal;
53
+ };
54
+ function findNearestIndex(target, arr) {
55
+ let startIndex = arguments.length > 2 && arguments[2] !== undefined ? arguments[2] : 0;
56
+ if (typeof target !== 'number' || isNaN(target)) {
57
+ throw new Error('Target must be a number.');
58
+ }
59
+ if (!Array.isArray(arr)) {
60
+ throw new Error('Second argument must be an array.');
61
+ }
62
+ let left = startIndex;
63
+ let right = arr.length - 1;
64
+ if (target < arr[left]) return left;
65
+ if (target > arr[right]) return right;
66
+ while (left <= right) {
67
+ const mid = Math.floor((left + right) / 2);
68
+ if (arr[mid] === target) {
69
+ return mid;
70
+ } else if (arr[mid] < target) {
71
+ left = mid + 1;
72
+ } else {
73
+ right = mid - 1;
74
+ }
75
+ }
76
+ return arr[left] - target < target - arr[right] ? left : right;
77
+ }
78
+ const OFFSET_TO_TARGET_RATIO = {
79
+ 100: 1.08,
80
+ 200: 1.2,
81
+ 300: 1.35,
82
+ 400: 2,
83
+ 500: 2.8,
84
+ 600: 3.3,
85
+ 700: 5,
86
+ 800: 10,
87
+ 900: 13,
88
+ 1000: 16,
89
+ 1100: 17.5,
90
+ 1200: 19
91
+ };
92
+ const generateColorScale = memoize(color => {
93
+ const scaleSize = 200;
94
+ const _scale = getScale('#FFF', color, '#000');
95
+ const scale = x => _scale(x / scaleSize);
96
+ const colors = [];
97
+ const contrastRatios = [];
98
+ for (let i = 0; i <= scaleSize; i++) {
99
+ const _color = scale(i);
100
+ colors.push(_color);
101
+ contrastRatios.push(getContrast('#FFF', _color));
102
+ }
103
+ const palette = {};
104
+ let startIndex = 0;
105
+ for (const offset in OFFSET_TO_TARGET_RATIO) {
106
+ if (Object.prototype.hasOwnProperty.call(OFFSET_TO_TARGET_RATIO, offset)) {
107
+ const ratio = OFFSET_TO_TARGET_RATIO[offset];
108
+ const nearestIndex = findNearestIndex(ratio, contrastRatios, startIndex);
109
+ startIndex = nearestIndex + 1;
110
+ palette[offset] = colors[nearestIndex];
111
+ }
112
+ }
113
+ return palette;
114
+ });
45
115
  const toColor = (colors, palette, opacity, scheme, hue, shade, offset, transparency) => {
46
116
  let retVal;
47
117
  let _hue = colors[hue] || hue;
@@ -50,17 +120,11 @@ const toColor = (colors, palette, opacity, scheme, hue, shade, offset, transpare
50
120
  }
51
121
  if (typeof _hue === 'object') {
52
122
  retVal = toHex(_hue, shade, offset, scheme);
53
- } else if (_hue === 'transparent' || valid(_hue)) {
123
+ } else if (isValidColor(_hue)) {
54
124
  if (shade === undefined) {
55
125
  retVal = _hue;
56
126
  } else {
57
- const _colors = scale([PALETTE.white, _hue, PALETTE.black]).correctLightness().colors(PALETTE_SIZE + 2);
58
- _hue = _colors.reduce((_retVal, color, index) => {
59
- if (index > 0 && index <= PALETTE_SIZE) {
60
- _retVal[index * 100] = color;
61
- }
62
- return _retVal;
63
- }, {});
127
+ _hue = generateColorScale(_hue);
64
128
  retVal = toHex(_hue, shade, offset, scheme);
65
129
  }
66
130
  }
@@ -83,6 +147,41 @@ const toProperty = (object, path) => {
83
147
  throw new TypeError(`Error: unexpected '${typeof retVal}' type for color variable "${path}"`);
84
148
  }
85
149
  };
150
+ const fromRgba = value => {
151
+ let retVal;
152
+ const regex = /rgba\s*\(\s*(?<property>[#\w.]+)\s*,\s*(?<alpha>[\w.]+)\s*\)/gu;
153
+ const _rgba = regex.exec(value);
154
+ if (_rgba && _rgba.groups) {
155
+ const property = _rgba.groups.property;
156
+ const transparency = parseFloat(_rgba.groups.alpha);
157
+ retVal = {
158
+ property,
159
+ transparency
160
+ };
161
+ } else {
162
+ throw new Error(`Error: invalid \`rgba\` value "${value}"`);
163
+ }
164
+ return retVal;
165
+ };
166
+ const fromVariable = (variable, variables, palette) => {
167
+ const retVal = {};
168
+ let property = toProperty(variables, variable);
169
+ if (property.startsWith('rgba')) {
170
+ const value = fromRgba(property);
171
+ property = value.property;
172
+ retVal.transparency = value.transparency;
173
+ }
174
+ const [key, value] = property.split(/\.(?<value>.*)/u);
175
+ if (key === 'palette') {
176
+ retVal.hue = toProperty(palette, value);
177
+ } else {
178
+ retVal.hue = key;
179
+ if (value !== undefined) {
180
+ retVal.shade = parseInt(value, 10);
181
+ }
182
+ }
183
+ return retVal;
184
+ };
86
185
  const getColor = memoize(_ref => {
87
186
  let {
88
187
  dark,
@@ -106,17 +205,13 @@ const getColor = memoize(_ref => {
106
205
  let _hue = mode?.hue || hue;
107
206
  let _shade = mode?.shade === undefined ? shade : mode.shade;
108
207
  const _offset = mode?.offset === undefined ? offset : mode.offset;
109
- const _transparency = mode?.transparency === undefined ? transparency : mode.transparency;
208
+ let _transparency = mode?.transparency === undefined ? transparency : mode.transparency;
110
209
  if (variable) {
111
210
  const _variables = variables?.[scheme] ? variables[scheme] : DEFAULT_THEME.colors.variables[scheme];
112
- const property = toProperty(_variables, variable);
113
- const [key, value] = property.split(/\.(?<value>.*)/u);
114
- if (key === 'palette') {
115
- _hue = toProperty(palette, value);
116
- } else {
117
- _hue = key;
118
- _shade = parseInt(value, 10);
119
- }
211
+ const value = fromVariable(variable, _variables, palette);
212
+ _hue = value.hue;
213
+ _shade = value.shade;
214
+ _transparency = _transparency === undefined ? value.transparency : _transparency;
120
215
  }
121
216
  if (_hue) {
122
217
  const opacity = theme.opacity && Object.keys(theme.opacity).length > 0 ? theme.opacity : DEFAULT_THEME.opacity;
@@ -145,6 +240,7 @@ const getColor = memoize(_ref => {
145
240
  shade,
146
241
  colors: theme.colors,
147
242
  palette: theme.palette,
243
+ opacity: theme.opacity,
148
244
  transparency,
149
245
  variable
150
246
  });
@@ -23,9 +23,30 @@ const animationStyles = (position, options) => {
23
23
  } else {
24
24
  transformFunction = 'translateX';
25
25
  }
26
- const animationName = keyframes(["0%{transform:", "(", ");}"], transformFunction, translateValue);
26
+ const animationName = keyframes(["0%{transform:", "(", ");pointer-events:none;}100%{pointer-events:auto;}"], transformFunction, translateValue);
27
27
  return css(["&", " ", "{animation:0.2s cubic-bezier(0.15,0.85,0.35,1.2) ", ";}"], options.animationModifier, options.childSelector || '> *', animationName);
28
28
  };
29
+ const colorStyles = theme => {
30
+ const backgroundColor = getColor({
31
+ theme,
32
+ variable: 'background.raised'
33
+ });
34
+ const borderColor = getColor({
35
+ theme,
36
+ variable: 'border.default'
37
+ });
38
+ const boxShadowColor = getColor({
39
+ variable: 'shadow.medium',
40
+ theme
41
+ });
42
+ const boxShadowBlurRadius = `${theme.space.base * (theme.colors.base === 'dark' ? 5 : 6)}px`;
43
+ const boxShadowOffsetY = `${theme.space.base * (theme.colors.base === 'dark' ? 4 : 5)}px`;
44
+ const foregroundColor = getColor({
45
+ theme,
46
+ variable: 'foreground.default'
47
+ });
48
+ return css(["border-color:", ";box-shadow:", ";background-color:", ";color:", ";"], borderColor, theme.shadows.lg(boxShadowOffsetY, boxShadowBlurRadius, boxShadowColor), backgroundColor, foregroundColor);
49
+ };
29
50
  const hiddenStyles = options => {
30
51
  const transition = 'opacity 0.2s ease-in-out, 0.2s visibility 0s linear';
31
52
  return css(["transition:", ";visibility:hidden;opacity:0;"], options.animationModifier && transition);
@@ -43,21 +64,7 @@ function menuStyles(position) {
43
64
  } else {
44
65
  marginProperty = 'margin-right';
45
66
  }
46
- return css(["position:absolute;z-index:", ";", ":", ";line-height:0;font-size:0.01px;& ", "{display:inline-block;position:relative;margin:0;box-sizing:border-box;border:", " ", ";border-radius:", ";box-shadow:", ";background-color:", ";cursor:default;padding:0;text-align:", ";white-space:normal;color:", ";font-size:", ";font-weight:", ";direction:", ";:focus{outline:none;}}", ";", ";"], options.zIndex || 0, marginProperty, options.margin, options.childSelector || '> *', theme.borders.sm, getColor({
47
- theme,
48
- variable: 'border.default'
49
- }), theme.borderRadii.md, theme.shadows.lg(`${theme.space.base * 5}px`, `${theme.space.base * 7.5}px`, getColor({
50
- theme,
51
- hue: 'chromeHue',
52
- shade: 600,
53
- transparency: 0.15
54
- })), getColor({
55
- theme,
56
- variable: 'background.raised'
57
- }), theme.rtl ? 'right' : 'left', getColor({
58
- theme,
59
- variable: 'foreground.default'
60
- }), theme.fontSizes.md, theme.fontWeights.regular, theme.rtl && 'rtl', options.animationModifier && animationStyles(position, options), options.hidden && hiddenStyles(options));
67
+ return css(["position:absolute;z-index:", ";", ":", ";line-height:0;font-size:0.01px;color-scheme:only ", ";& ", "{display:inline-block;position:relative;margin:0;box-sizing:border-box;border:", ";border-radius:", ";cursor:default;padding:0;text-align:", ";white-space:normal;font-size:", ";font-weight:", ";direction:", ";", ";:focus{outline:none;}}", ";", ";"], options.zIndex || 0, marginProperty, options.margin, p => p.theme.colors.base, options.childSelector || '> *', theme.borders.sm, theme.borderRadii.md, theme.rtl ? 'right' : 'left', theme.fontSizes.md, theme.fontWeights.regular, theme.rtl && 'rtl', colorStyles(theme), options.animationModifier && animationStyles(position, options), options.hidden && hiddenStyles(options));
61
68
  }
62
69
 
63
70
  export { menuStyles as default };