@telus-uds/components-web 2.27.0 → 2.29.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.
package/CHANGELOG.md CHANGED
@@ -1,12 +1,39 @@
1
1
  # Change Log - @telus-uds/components-web
2
2
 
3
- This log was last generated on Wed, 13 Dec 2023 21:13:56 GMT and should not be manually modified.
3
+ This log was last generated on Thu, 18 Jan 2024 22:43:26 GMT and should not be manually modified.
4
4
 
5
5
  <!-- Start content -->
6
6
 
7
+ ## 2.29.0
8
+
9
+ Thu, 18 Jan 2024 22:43:26 GMT
10
+
11
+ ### Minor changes
12
+
13
+ - prop for footer to handle mobile (ben@mcloughlin.dev)
14
+ - Bump @telus-uds/components-base to v1.74.0
15
+ - Bump @telus-uds/system-theme-tokens to v2.50.0
16
+
17
+ ### Patches
18
+
19
+ - fix hardcorded french label from datepicker (guillermo.peitzner@telus.com)
20
+
21
+ ## 2.28.0
22
+
23
+ Mon, 08 Jan 2024 20:16:06 GMT
24
+
25
+ ### Minor changes
26
+
27
+ - Get a theme wrapper to grab thteme from either server or client (wlsdud194@hotmail.com)
28
+ - Update eslintrc (wlsdud194@hotmail.com)
29
+ - update badge story to include subtle variant (evander.owusu@telus.com)
30
+ - add the display token to the table component (guillermo.peitzner@telus.com)
31
+ - Bump @telus-uds/components-base to v1.73.0
32
+ - Bump @telus-uds/system-theme-tokens to v2.49.0
33
+
7
34
  ## 2.27.0
8
35
 
9
- Wed, 13 Dec 2023 21:13:56 GMT
36
+ Wed, 13 Dec 2023 21:24:24 GMT
10
37
 
11
38
  ### Minor changes
12
39
 
@@ -323,7 +323,7 @@ const DatePicker = /*#__PURE__*/(0, _react.forwardRef)((_ref3, ref) => {
323
323
  onChange: onChangeInput,
324
324
  tooltip: tooltip,
325
325
  hintPosition: hintPosition,
326
- label: ((_dictionary$copy = _dictionary.default[copy]) === null || _dictionary$copy === void 0 ? void 0 : _dictionary$copy.roleDescription) ?? label,
326
+ label: label ?? ((_dictionary$copy = _dictionary.default[copy]) === null || _dictionary$copy === void 0 ? void 0 : _dictionary$copy.roleDescription),
327
327
  value: inputText,
328
328
  validation: validation,
329
329
  inactive: disabled,
@@ -30,7 +30,8 @@ const StyledFootnote = /*#__PURE__*/_styledComponents.default.div.withConfig({
30
30
  footnoteBackground,
31
31
  isVisible,
32
32
  footnoteBorderTop,
33
- isScrollable
33
+ isScrollable,
34
+ isMobileFullScreen
34
35
  } = _ref;
35
36
  return {
36
37
  position: 'fixed',
@@ -49,7 +50,7 @@ const StyledFootnote = /*#__PURE__*/_styledComponents.default.div.withConfig({
49
50
  },
50
51
  zIndex: 99999,
51
52
  visibility: isVisible ? 'visible' : 'hidden',
52
- ...(0, _utils.media)().from('md').css({
53
+ ...(0, _utils.media)().from(isMobileFullScreen ? 'md' : 'xs').css({
53
54
  top: 'auto',
54
55
  bottom: 0,
55
56
  height: 'auto',
@@ -262,6 +263,7 @@ const Footnote = props => {
262
263
  isOpen,
263
264
  tokens,
264
265
  variant = {},
266
+ isMobileFullScreen = true,
265
267
  dictionary = _dictionary.default,
266
268
  ...rest
267
269
  } = props;
@@ -507,6 +509,7 @@ const Footnote = props => {
507
509
  footnoteBackground: footnoteBackground,
508
510
  footnoteBorderTop: `${footnoteBorderTopSizeMd}px solid ${footnoteBorderColorMd}`,
509
511
  isScrollable: isScrollable,
512
+ isMobileFullScreen: isMobileFullScreen,
510
513
  children: /*#__PURE__*/(0, _jsxRuntime.jsxs)(ContentContainer, {
511
514
  maxWidth: maxWidth,
512
515
  children: [/*#__PURE__*/(0, _jsxRuntime.jsx)(StyledFootnoteHeader, {
@@ -609,13 +612,18 @@ Footnote.propTypes = {
609
612
  dictionary: _propTypes.default.shape({
610
613
  en: dictionaryContentShape,
611
614
  fr: dictionaryContentShape
612
- })
615
+ }),
616
+ /**
617
+ * A boolean flag used to disable isMobileFullScreen of Footnote for mobile view
618
+ */
619
+ isMobileFullScreen: _propTypes.default.bool
613
620
  };
614
621
  Footnote.defaultProps = {
615
622
  isOpen: false,
616
623
  number: undefined,
617
624
  content: undefined,
618
- copy: 'en'
625
+ copy: 'en',
626
+ isMobileFullScreen: true
619
627
  };
620
628
  var _default = Footnote;
621
629
  exports.default = _default;
@@ -6,40 +6,12 @@ Object.defineProperty(exports, "__esModule", {
6
6
  exports.default = void 0;
7
7
  var _react = _interopRequireDefault(require("react"));
8
8
  var _propTypes = _interopRequireDefault(require("prop-types"));
9
- var _styledComponents = _interopRequireDefault(require("styled-components"));
10
- var _componentsBase = require("@telus-uds/components-base");
11
- var _utils = require("../utils");
9
+ var _server = require("@telus-uds/components-base/server");
10
+ var _logger = require("../utils/logger");
12
11
  var _jsxRuntime = require("react/jsx-runtime");
13
12
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
14
- const [selectProps, selectedSystemPropTypes] = (0, _componentsBase.selectSystemProps)([_utils.htmlAttrs]);
15
- const StyledImage = /*#__PURE__*/_styledComponents.default.img.withConfig({
16
- displayName: "Image__StyledImage",
17
- componentId: "components-web__sc-blwu4l-0"
18
- })(_ref => {
19
- let {
20
- height
21
- } = _ref;
22
- return {
23
- height: height ?? 'auto',
24
- maxWidth: '100%'
25
- };
26
- });
27
- const StyledRoundedImage = /*#__PURE__*/(0, _styledComponents.default)(StyledImage).withConfig({
28
- displayName: "Image__StyledRoundedImage",
29
- componentId: "components-web__sc-blwu4l-1"
30
- })(["border-radius:", "px;"], _ref2 => {
31
- let {
32
- borderRadius
33
- } = _ref2;
34
- return borderRadius;
35
- });
36
- const StyledCircularImage = /*#__PURE__*/(0, _styledComponents.default)(StyledImage).withConfig({
37
- displayName: "Image__StyledCircularImage",
38
- componentId: "components-web__sc-blwu4l-2"
39
- })({
40
- borderRadius: '50%'
41
- });
42
- const Image = _ref3 => {
13
+ const [selectProps, selectedSystemPropTypes] = (0, _server.selectSystemProps)([_server.htmlAttrs]);
14
+ const Image = _ref => {
43
15
  let {
44
16
  src,
45
17
  width,
@@ -48,29 +20,32 @@ const Image = _ref3 => {
48
20
  rounded,
49
21
  loading = 'eager',
50
22
  tokens,
23
+ theme,
51
24
  variant,
52
25
  ...rest
53
- } = _ref3;
54
- const {
26
+ } = _ref;
27
+ let {
55
28
  borderRadius
56
- } = (0, _componentsBase.useThemeTokens)('Image', tokens, variant);
29
+ } = theme;
57
30
  const isCircle = rounded === 'circle';
58
31
  const isCorners = rounded === 'corners';
59
32
  const isSquare = width === height;
60
33
  if (isCircle && !isSquare) {
61
- (0, _utils.warn)('Image', 'rounded="circle" is not supported for non-square images. Please provide a square image, otherwise the resulting shape will not be a circle.');
34
+ (0, _logger.warn)('Image', 'rounded="circle" is not supported for non-square images. Please provide a square image, otherwise the resulting shape will not be a circle.');
62
35
  }
63
- let ImageComponent;
64
36
  if (isCircle) {
65
- ImageComponent = StyledCircularImage;
37
+ borderRadius = '50%';
66
38
  } else if (isCorners) {
67
- ImageComponent = StyledRoundedImage;
68
- } else {
69
- ImageComponent = StyledImage;
39
+ borderRadius = '4px';
70
40
  }
71
- return /*#__PURE__*/(0, _jsxRuntime.jsx)(ImageComponent, {
41
+ const style = {
42
+ borderRadius,
43
+ height: height ?? 'auto',
44
+ maxWidth: '100%'
45
+ };
46
+ return /*#__PURE__*/(0, _jsxRuntime.jsx)("img", {
72
47
  ...selectProps(rest),
73
- borderRadius: borderRadius,
48
+ style: style,
74
49
  src: src,
75
50
  width: width,
76
51
  height: height,
@@ -107,7 +82,8 @@ Image.propTypes = {
107
82
  * Make image render as a circle or with rounded corners.
108
83
  */
109
84
  rounded: _propTypes.default.oneOf(['circle', 'corners']),
110
- tokens: (0, _componentsBase.getTokensPropType)('Image')
85
+ tokens: (0, _server.getTokensPropType)('Image')
111
86
  };
87
+ Image.displayName = 'Image';
112
88
  var _default = Image;
113
89
  exports.default = _default;
@@ -3,8 +3,18 @@
3
3
  Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
+ Object.defineProperty(exports, "DefaultImage", {
7
+ enumerable: true,
8
+ get: function () {
9
+ return _Image.default;
10
+ }
11
+ });
6
12
  exports.default = void 0;
7
13
  var _Image = _interopRequireDefault(require("./Image"));
14
+ var _withClientTheme = _interopRequireDefault(require("../utils/theming/with-client-theme"));
8
15
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
9
- var _default = _Image.default;
16
+ // Exporting the unwrapped component separately for react-docgen to extract info for docsite
17
+
18
+ const ClientThemedImage = (0, _withClientTheme.default)(_Image.default);
19
+ var _default = ClientThemedImage;
10
20
  exports.default = _default;
@@ -0,0 +1,12 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _withServerTheme = _interopRequireDefault(require("../utils/theming/with-server-theme"));
8
+ var _Image = _interopRequireDefault(require("./Image"));
9
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
10
+ const ServerThemedImage = (0, _withServerTheme.default)(_Image.default, 'Image');
11
+ var _default = ServerThemedImage;
12
+ exports.default = _default;
package/lib/Table/Cell.js CHANGED
@@ -49,23 +49,30 @@ const sharedStyles = /*#__PURE__*/(0, _styledComponents.css)(["", ""], _ref2 =>
49
49
  const createStyledCell = htmlElement => _styledComponents.default[htmlElement].withConfig({
50
50
  displayName: "Cell__createStyledCell",
51
51
  componentId: "components-web__sc-ltgfic-0"
52
- })(["", ";box-shadow:", ";"], sharedStyles, _ref3 => {
52
+ })(["", ";box-shadow:", ";", ""], sharedStyles, _ref3 => {
53
53
  let {
54
54
  cellBoxShadowColor,
55
55
  type
56
56
  } = _ref3;
57
57
  return type === HEADER_TYPE.HEADING ? `inset 0 1px 0 ${cellBoxShadowColor}, inset 0 -1px 0 ${cellBoxShadowColor}` : `inset 0 1px 0 ${cellBoxShadowColor}`;
58
+ }, _ref4 => {
59
+ let {
60
+ display
61
+ } = _ref4;
62
+ return display && `*:not(:empty) {
63
+ display: ${display};
64
+ }`;
58
65
  });
59
66
  const StyledHeaderCell = createStyledCell('th');
60
67
  const StyledDataCell = createStyledCell('td');
61
- const Cell = _ref4 => {
68
+ const Cell = _ref5 => {
62
69
  let {
63
70
  children,
64
71
  isFirstInRow,
65
72
  align = 'left',
66
73
  tokens: cellTokens,
67
74
  type = 'default'
68
- } = _ref4;
75
+ } = _ref5;
69
76
  const {
70
77
  text,
71
78
  isScrollable: isTableScrollable,
@@ -90,7 +97,8 @@ const Cell = _ref4 => {
90
97
  fontSize,
91
98
  lineHeight,
92
99
  stickyBackgroundColor,
93
- fontColor
100
+ fontColor,
101
+ display
94
102
  } = (0, _componentsBase.useThemeTokens)('Table', themeTokens, {
95
103
  spacing,
96
104
  type,
@@ -107,7 +115,8 @@ const Cell = _ref4 => {
107
115
  cellPaddingLeft,
108
116
  cellPaddingBottom,
109
117
  stickyBackgroundColor,
110
- cellBoxShadowColor
118
+ cellBoxShadowColor,
119
+ display
111
120
  };
112
121
  const typographyTokens = {
113
122
  fontName,
package/lib/index.js CHANGED
@@ -1,4 +1,5 @@
1
1
  "use strict";
2
+ 'use client';
2
3
 
3
4
  Object.defineProperty(exports, "__esModule", {
4
5
  value: true
@@ -19,6 +20,8 @@ var _exportNames = {
19
20
  Footnote: true,
20
21
  QuantitySelector: true,
21
22
  IconButton: true,
23
+ Image: true,
24
+ DefaultImage: true,
22
25
  transformGradient: true,
23
26
  ssrStyles: true,
24
27
  Breadcrumbs: true,
@@ -27,7 +30,6 @@ var _exportNames = {
27
30
  Testimonial: true,
28
31
  Toast: true,
29
32
  Table: true,
30
- Image: true,
31
33
  WebVideo: true,
32
34
  WaffleGrid: true,
33
35
  Spinner: true,
@@ -85,6 +87,12 @@ Object.defineProperty(exports, "DatePicker", {
85
87
  return _DatePicker.default;
86
88
  }
87
89
  });
90
+ Object.defineProperty(exports, "DefaultImage", {
91
+ enumerable: true,
92
+ get: function () {
93
+ return _Image.DefaultImage;
94
+ }
95
+ });
88
96
  Object.defineProperty(exports, "Disclaimer", {
89
97
  enumerable: true,
90
98
  get: function () {
@@ -286,6 +294,7 @@ var _PriceLockup = _interopRequireDefault(require("./PriceLockup"));
286
294
  var _Footnote = _interopRequireDefault(require("./Footnote"));
287
295
  var _QuantitySelector = _interopRequireDefault(require("./QuantitySelector"));
288
296
  var _IconButton = _interopRequireDefault(require("./IconButton"));
297
+ var _Image = _interopRequireWildcard(require("./Image"));
289
298
  var _utils = require("./utils");
290
299
  var _Breadcrumbs = _interopRequireDefault(require("./Breadcrumbs"));
291
300
  var _BlockQuote = _interopRequireDefault(require("./BlockQuote"));
@@ -293,7 +302,6 @@ var _OptimizeImage = _interopRequireDefault(require("./OptimizeImage"));
293
302
  var _Testimonial = _interopRequireDefault(require("./Testimonial"));
294
303
  var _Toast = _interopRequireDefault(require("./Toast"));
295
304
  var _Table = _interopRequireDefault(require("./Table"));
296
- var _Image = _interopRequireDefault(require("./Image"));
297
305
  var _WebVideo = _interopRequireDefault(require("./WebVideo"));
298
306
  var _WaffleGrid = _interopRequireDefault(require("./WaffleGrid"));
299
307
  var _Spinner = _interopRequireDefault(require("./Spinner"));
@@ -320,4 +328,6 @@ Object.keys(_baseExports).forEach(function (key) {
320
328
  }
321
329
  });
322
330
  });
331
+ function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
332
+ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
323
333
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
package/lib/server.js ADDED
@@ -0,0 +1,13 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ Object.defineProperty(exports, "Image", {
7
+ enumerable: true,
8
+ get: function () {
9
+ return _server.default;
10
+ }
11
+ });
12
+ var _server = _interopRequireDefault(require("./Image/server"));
13
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
@@ -0,0 +1,24 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = getTheme;
7
+ function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
8
+ function _interopRequireWildcard(obj, nodeInterop) { if (!nodeInterop && obj && obj.__esModule) { return obj; } if (obj === null || typeof obj !== "object" && typeof obj !== "function") { return { default: obj }; } var cache = _getRequireWildcardCache(nodeInterop); if (cache && cache.has(obj)) { return cache.get(obj); } var newObj = {}; var hasPropertyDescriptor = Object.defineProperty && Object.getOwnPropertyDescriptor; for (var key in obj) { if (key !== "default" && Object.prototype.hasOwnProperty.call(obj, key)) { var desc = hasPropertyDescriptor ? Object.getOwnPropertyDescriptor(obj, key) : null; if (desc && (desc.get || desc.set)) { Object.defineProperty(newObj, key, desc); } else { newObj[key] = obj[key]; } } } newObj.default = obj; if (cache) { cache.set(obj, newObj); } return newObj; }
9
+ const cachedTheme = {};
10
+ const theme = process.env.UDS_THEME;
11
+ async function importTheme(componentName) {
12
+ try {
13
+ cachedTheme[componentName] = await Promise.resolve(`@telus-uds/theme-${theme}/build/rn/${componentName}.js`).then(s => _interopRequireWildcard(require(s)));
14
+ } catch (_) {
15
+ throw new Error(`An error occurred while trying to import theme-${process.env.UDS_THEME}. Please check that the theme has been installed in your app or that you are not importing a server component inside a client component.`);
16
+ }
17
+ }
18
+ async function getTheme(componentName) {
19
+ if (cachedTheme[componentName]) {
20
+ return cachedTheme[componentName];
21
+ }
22
+ await importTheme(componentName);
23
+ return cachedTheme[componentName];
24
+ }
@@ -0,0 +1,32 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _react = _interopRequireDefault(require("react"));
8
+ var _propTypes = _interopRequireDefault(require("prop-types"));
9
+ var _componentsBase = require("@telus-uds/components-base");
10
+ var _jsxRuntime = require("react/jsx-runtime");
11
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
12
+ const withClientTheme = Component => {
13
+ const UdsStyledComponent = _ref => {
14
+ let {
15
+ tokens: tokenOverrides,
16
+ variant,
17
+ ...props
18
+ } = _ref;
19
+ const theme = (0, _componentsBase.useThemeTokens)(Component.displayName, variant, tokenOverrides);
20
+ return /*#__PURE__*/(0, _jsxRuntime.jsx)(Component, {
21
+ theme: theme,
22
+ ...props
23
+ });
24
+ };
25
+ UdsStyledComponent.propTypes = {
26
+ tokens: _propTypes.default.oneOfType([_propTypes.default.func, _propTypes.default.object]),
27
+ variant: _propTypes.default.string
28
+ };
29
+ return UdsStyledComponent;
30
+ };
31
+ var _default = withClientTheme;
32
+ exports.default = _default;
@@ -0,0 +1,34 @@
1
+ "use strict";
2
+
3
+ Object.defineProperty(exports, "__esModule", {
4
+ value: true
5
+ });
6
+ exports.default = void 0;
7
+ var _react = _interopRequireDefault(require("react"));
8
+ var _propTypes = _interopRequireDefault(require("prop-types"));
9
+ var _server = require("@telus-uds/components-base/server");
10
+ var _getThemeFromServer = _interopRequireDefault(require("./get-theme-from-server"));
11
+ var _jsxRuntime = require("react/jsx-runtime");
12
+ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
13
+ const withServerTheme = (Component, componentName) => {
14
+ const UdsStyledComponent = async _ref => {
15
+ let {
16
+ tokens: tokenOverrides,
17
+ variant,
18
+ ...props
19
+ } = _ref;
20
+ const componentTheme = await (0, _getThemeFromServer.default)(componentName);
21
+ const themeTokens = (0, _server.getThemeTokens)(componentTheme, tokenOverrides, variant);
22
+ return /*#__PURE__*/(0, _jsxRuntime.jsx)(Component, {
23
+ theme: themeTokens,
24
+ ...props
25
+ });
26
+ };
27
+ UdsStyledComponent.propTypes = {
28
+ tokens: _propTypes.default.oneOfType([_propTypes.default.func, _propTypes.default.object]),
29
+ variant: _propTypes.default.string
30
+ };
31
+ return UdsStyledComponent;
32
+ };
33
+ var _default = withServerTheme;
34
+ exports.default = _default;
@@ -316,7 +316,7 @@ const DatePicker = /*#__PURE__*/forwardRef((_ref3, ref) => {
316
316
  onChange: onChangeInput,
317
317
  tooltip: tooltip,
318
318
  hintPosition: hintPosition,
319
- label: ((_dictionary$copy = dictionary[copy]) === null || _dictionary$copy === void 0 ? void 0 : _dictionary$copy.roleDescription) ?? label,
319
+ label: label ?? ((_dictionary$copy = dictionary[copy]) === null || _dictionary$copy === void 0 ? void 0 : _dictionary$copy.roleDescription),
320
320
  value: inputText,
321
321
  validation: validation,
322
322
  inactive: disabled,
@@ -22,7 +22,8 @@ const StyledFootnote = /*#__PURE__*/styled.div.withConfig({
22
22
  footnoteBackground,
23
23
  isVisible,
24
24
  footnoteBorderTop,
25
- isScrollable
25
+ isScrollable,
26
+ isMobileFullScreen
26
27
  } = _ref;
27
28
  return {
28
29
  position: 'fixed',
@@ -41,7 +42,7 @@ const StyledFootnote = /*#__PURE__*/styled.div.withConfig({
41
42
  },
42
43
  zIndex: 99999,
43
44
  visibility: isVisible ? 'visible' : 'hidden',
44
- ...media().from('md').css({
45
+ ...media().from(isMobileFullScreen ? 'md' : 'xs').css({
45
46
  top: 'auto',
46
47
  bottom: 0,
47
48
  height: 'auto',
@@ -254,6 +255,7 @@ const Footnote = props => {
254
255
  isOpen,
255
256
  tokens,
256
257
  variant = {},
258
+ isMobileFullScreen = true,
257
259
  dictionary = defaultDictionary,
258
260
  ...rest
259
261
  } = props;
@@ -499,6 +501,7 @@ const Footnote = props => {
499
501
  footnoteBackground: footnoteBackground,
500
502
  footnoteBorderTop: `${footnoteBorderTopSizeMd}px solid ${footnoteBorderColorMd}`,
501
503
  isScrollable: isScrollable,
504
+ isMobileFullScreen: isMobileFullScreen,
502
505
  children: /*#__PURE__*/_jsxs(ContentContainer, {
503
506
  maxWidth: maxWidth,
504
507
  children: [/*#__PURE__*/_jsx(StyledFootnoteHeader, {
@@ -601,12 +604,17 @@ Footnote.propTypes = {
601
604
  dictionary: PropTypes.shape({
602
605
  en: dictionaryContentShape,
603
606
  fr: dictionaryContentShape
604
- })
607
+ }),
608
+ /**
609
+ * A boolean flag used to disable isMobileFullScreen of Footnote for mobile view
610
+ */
611
+ isMobileFullScreen: PropTypes.bool
605
612
  };
606
613
  Footnote.defaultProps = {
607
614
  isOpen: false,
608
615
  number: undefined,
609
616
  content: undefined,
610
- copy: 'en'
617
+ copy: 'en',
618
+ isMobileFullScreen: true
611
619
  };
612
620
  export default Footnote;
@@ -1,38 +1,10 @@
1
1
  import React from 'react';
2
2
  import PropTypes from 'prop-types';
3
- import styled from 'styled-components';
4
- import { selectSystemProps, useThemeTokens, getTokensPropType } from '@telus-uds/components-base';
5
- import { htmlAttrs, warn } from '../utils';
3
+ import { htmlAttrs, selectSystemProps, getTokensPropType } from '@telus-uds/components-base/server';
4
+ import { warn } from '../utils/logger';
6
5
  import { jsx as _jsx } from "react/jsx-runtime";
7
6
  const [selectProps, selectedSystemPropTypes] = selectSystemProps([htmlAttrs]);
8
- const StyledImage = /*#__PURE__*/styled.img.withConfig({
9
- displayName: "Image__StyledImage",
10
- componentId: "components-web__sc-blwu4l-0"
11
- })(_ref => {
12
- let {
13
- height
14
- } = _ref;
15
- return {
16
- height: height ?? 'auto',
17
- maxWidth: '100%'
18
- };
19
- });
20
- const StyledRoundedImage = /*#__PURE__*/styled(StyledImage).withConfig({
21
- displayName: "Image__StyledRoundedImage",
22
- componentId: "components-web__sc-blwu4l-1"
23
- })(["border-radius:", "px;"], _ref2 => {
24
- let {
25
- borderRadius
26
- } = _ref2;
27
- return borderRadius;
28
- });
29
- const StyledCircularImage = /*#__PURE__*/styled(StyledImage).withConfig({
30
- displayName: "Image__StyledCircularImage",
31
- componentId: "components-web__sc-blwu4l-2"
32
- })({
33
- borderRadius: '50%'
34
- });
35
- const Image = _ref3 => {
7
+ const Image = _ref => {
36
8
  let {
37
9
  src,
38
10
  width,
@@ -41,29 +13,32 @@ const Image = _ref3 => {
41
13
  rounded,
42
14
  loading = 'eager',
43
15
  tokens,
16
+ theme,
44
17
  variant,
45
18
  ...rest
46
- } = _ref3;
47
- const {
19
+ } = _ref;
20
+ let {
48
21
  borderRadius
49
- } = useThemeTokens('Image', tokens, variant);
22
+ } = theme;
50
23
  const isCircle = rounded === 'circle';
51
24
  const isCorners = rounded === 'corners';
52
25
  const isSquare = width === height;
53
26
  if (isCircle && !isSquare) {
54
27
  warn('Image', 'rounded="circle" is not supported for non-square images. Please provide a square image, otherwise the resulting shape will not be a circle.');
55
28
  }
56
- let ImageComponent;
57
29
  if (isCircle) {
58
- ImageComponent = StyledCircularImage;
30
+ borderRadius = '50%';
59
31
  } else if (isCorners) {
60
- ImageComponent = StyledRoundedImage;
61
- } else {
62
- ImageComponent = StyledImage;
32
+ borderRadius = '4px';
63
33
  }
64
- return /*#__PURE__*/_jsx(ImageComponent, {
34
+ const style = {
35
+ borderRadius,
36
+ height: height ?? 'auto',
37
+ maxWidth: '100%'
38
+ };
39
+ return /*#__PURE__*/_jsx("img", {
65
40
  ...selectProps(rest),
66
- borderRadius: borderRadius,
41
+ style: style,
67
42
  src: src,
68
43
  width: width,
69
44
  height: height,
@@ -102,4 +77,5 @@ Image.propTypes = {
102
77
  rounded: PropTypes.oneOf(['circle', 'corners']),
103
78
  tokens: getTokensPropType('Image')
104
79
  };
80
+ Image.displayName = 'Image';
105
81
  export default Image;
@@ -1,2 +1,7 @@
1
1
  import Image from './Image';
2
- export default Image;
2
+ import withClientTheme from '../utils/theming/with-client-theme';
3
+
4
+ // Exporting the unwrapped component separately for react-docgen to extract info for docsite
5
+ export { Image as DefaultImage };
6
+ const ClientThemedImage = withClientTheme(Image);
7
+ export default ClientThemedImage;
@@ -0,0 +1,4 @@
1
+ import withServerTheme from '../utils/theming/with-server-theme';
2
+ import Image from './Image';
3
+ const ServerThemedImage = withServerTheme(Image, 'Image');
4
+ export default ServerThemedImage;
@@ -40,23 +40,30 @@ const sharedStyles = /*#__PURE__*/css(["", ""], _ref2 => {
40
40
  const createStyledCell = htmlElement => styled[htmlElement].withConfig({
41
41
  displayName: "Cell__createStyledCell",
42
42
  componentId: "components-web__sc-ltgfic-0"
43
- })(["", ";box-shadow:", ";"], sharedStyles, _ref3 => {
43
+ })(["", ";box-shadow:", ";", ""], sharedStyles, _ref3 => {
44
44
  let {
45
45
  cellBoxShadowColor,
46
46
  type
47
47
  } = _ref3;
48
48
  return type === HEADER_TYPE.HEADING ? `inset 0 1px 0 ${cellBoxShadowColor}, inset 0 -1px 0 ${cellBoxShadowColor}` : `inset 0 1px 0 ${cellBoxShadowColor}`;
49
+ }, _ref4 => {
50
+ let {
51
+ display
52
+ } = _ref4;
53
+ return display && `*:not(:empty) {
54
+ display: ${display};
55
+ }`;
49
56
  });
50
57
  const StyledHeaderCell = createStyledCell('th');
51
58
  const StyledDataCell = createStyledCell('td');
52
- const Cell = _ref4 => {
59
+ const Cell = _ref5 => {
53
60
  let {
54
61
  children,
55
62
  isFirstInRow,
56
63
  align = 'left',
57
64
  tokens: cellTokens,
58
65
  type = 'default'
59
- } = _ref4;
66
+ } = _ref5;
60
67
  const {
61
68
  text,
62
69
  isScrollable: isTableScrollable,
@@ -81,7 +88,8 @@ const Cell = _ref4 => {
81
88
  fontSize,
82
89
  lineHeight,
83
90
  stickyBackgroundColor,
84
- fontColor
91
+ fontColor,
92
+ display
85
93
  } = useThemeTokens('Table', themeTokens, {
86
94
  spacing,
87
95
  type,
@@ -98,7 +106,8 @@ const Cell = _ref4 => {
98
106
  cellPaddingLeft,
99
107
  cellPaddingBottom,
100
108
  stickyBackgroundColor,
101
- cellBoxShadowColor
109
+ cellBoxShadowColor,
110
+ display
102
111
  };
103
112
  const typographyTokens = {
104
113
  fontName,
@@ -1,3 +1,5 @@
1
+ 'use client';
2
+
1
3
  export { default as Badge } from './Badge';
2
4
  export { default as OrderedList } from './OrderedList';
3
5
  export { default as PreviewCard } from './PreviewCard';
@@ -13,6 +15,7 @@ export { default as PriceLockup } from './PriceLockup';
13
15
  export { default as Footnote } from './Footnote';
14
16
  export { default as QuantitySelector } from './QuantitySelector';
15
17
  export { default as IconButton } from './IconButton';
18
+ export { default as Image, DefaultImage } from './Image';
16
19
  export { transformGradient } from './utils';
17
20
  export { default as Breadcrumbs } from './Breadcrumbs';
18
21
  export { default as BlockQuote } from './BlockQuote';
@@ -20,7 +23,6 @@ export { default as OptimizeImage } from './OptimizeImage';
20
23
  export { default as Testimonial } from './Testimonial';
21
24
  export { default as Toast } from './Toast';
22
25
  export { default as Table } from './Table';
23
- export { default as Image } from './Image';
24
26
  export { default as WebVideo } from './WebVideo';
25
27
  export { default as WaffleGrid } from './WaffleGrid';
26
28
  export { default as Spinner } from './Spinner';
@@ -0,0 +1,5 @@
1
+ import ServerThemedImage from './Image/server';
2
+
3
+ // Export themed components
4
+ /* eslint-disable import/prefer-default-export */
5
+ export { ServerThemedImage as Image };
@@ -0,0 +1,16 @@
1
+ const cachedTheme = {};
2
+ const theme = process.env.UDS_THEME;
3
+ async function importTheme(componentName) {
4
+ try {
5
+ cachedTheme[componentName] = await import(`@telus-uds/theme-${theme}/build/rn/${componentName}.js`);
6
+ } catch (_) {
7
+ throw new Error(`An error occurred while trying to import theme-${process.env.UDS_THEME}. Please check that the theme has been installed in your app or that you are not importing a server component inside a client component.`);
8
+ }
9
+ }
10
+ export default async function getTheme(componentName) {
11
+ if (cachedTheme[componentName]) {
12
+ return cachedTheme[componentName];
13
+ }
14
+ await importTheme(componentName);
15
+ return cachedTheme[componentName];
16
+ }
@@ -0,0 +1,24 @@
1
+ import React from 'react';
2
+ import PropTypes from 'prop-types';
3
+ import { useThemeTokens } from '@telus-uds/components-base';
4
+ import { jsx as _jsx } from "react/jsx-runtime";
5
+ const withClientTheme = Component => {
6
+ const UdsStyledComponent = _ref => {
7
+ let {
8
+ tokens: tokenOverrides,
9
+ variant,
10
+ ...props
11
+ } = _ref;
12
+ const theme = useThemeTokens(Component.displayName, variant, tokenOverrides);
13
+ return /*#__PURE__*/_jsx(Component, {
14
+ theme: theme,
15
+ ...props
16
+ });
17
+ };
18
+ UdsStyledComponent.propTypes = {
19
+ tokens: PropTypes.oneOfType([PropTypes.func, PropTypes.object]),
20
+ variant: PropTypes.string
21
+ };
22
+ return UdsStyledComponent;
23
+ };
24
+ export default withClientTheme;
@@ -0,0 +1,26 @@
1
+ import React from 'react';
2
+ import PropTypes from 'prop-types';
3
+ import { getThemeTokens } from '@telus-uds/components-base/server';
4
+ import getTheme from './get-theme-from-server';
5
+ import { jsx as _jsx } from "react/jsx-runtime";
6
+ const withServerTheme = (Component, componentName) => {
7
+ const UdsStyledComponent = async _ref => {
8
+ let {
9
+ tokens: tokenOverrides,
10
+ variant,
11
+ ...props
12
+ } = _ref;
13
+ const componentTheme = await getTheme(componentName);
14
+ const themeTokens = getThemeTokens(componentTheme, tokenOverrides, variant);
15
+ return /*#__PURE__*/_jsx(Component, {
16
+ theme: themeTokens,
17
+ ...props
18
+ });
19
+ };
20
+ UdsStyledComponent.propTypes = {
21
+ tokens: PropTypes.oneOfType([PropTypes.func, PropTypes.object]),
22
+ variant: PropTypes.string
23
+ };
24
+ return UdsStyledComponent;
25
+ };
26
+ export default withServerTheme;
package/package.json CHANGED
@@ -5,18 +5,37 @@
5
5
  ],
6
6
  "dependencies": {
7
7
  "@gorhom/portal": "^1.0.14",
8
- "@telus-uds/components-base": "1.72.0",
8
+ "@telus-uds/components-base": "1.74.0",
9
9
  "@telus-uds/system-constants": "^1.3.0",
10
10
  "fscreen": "^1.2.0",
11
11
  "lodash.omit": "^4.5.0",
12
+ "moment": "2.29.4",
12
13
  "react-dates": "^21.8.0",
13
14
  "react-helmet-async": "^1.3.0",
14
15
  "react-moment-proptypes": "^1.8.1",
15
- "@telus-uds/system-theme-tokens": "^2.48.0",
16
+ "@telus-uds/system-theme-tokens": "^2.50.0",
16
17
  "prop-types": "^15.7.2",
17
18
  "lodash.throttle": "^4.1.1",
18
19
  "react-youtube": "^10.1.0",
19
- "moment": "2.29.4"
20
+ "semver": "^7.5.4"
21
+ },
22
+ "exports": {
23
+ ".": {
24
+ "import": "./lib-module/index.js",
25
+ "require": "./lib/index.js"
26
+ },
27
+ "./*": {
28
+ "import": "./lib-module/*/index.js",
29
+ "require": "./lib/*/index.js"
30
+ },
31
+ "./server": {
32
+ "import": "./lib-module/server.js",
33
+ "require": "./lib/server.js"
34
+ },
35
+ "./server/*": {
36
+ "import": "./lib-module/*/server.js",
37
+ "require": "./lib/server/*/server.js"
38
+ }
20
39
  },
21
40
  "description": "UDS mult-brand web components",
22
41
  "devDependencies": {
@@ -27,6 +46,8 @@
27
46
  "assert": "^2.0.0",
28
47
  "babel-plugin-react-native-web": "^0.18.7",
29
48
  "babel-plugin-styled-components": "^2.0.6",
49
+ "eslint-import-resolver-alias": "^1.1.2",
50
+ "eslint-import-resolver-exports": "^1.0.0-beta.5",
30
51
  "jest-axe": "^6.0.0",
31
52
  "jest-styled-components": "^7.0.8",
32
53
  "react-test-renderer": "~18.0.0",
@@ -62,5 +83,5 @@
62
83
  "skip": true
63
84
  },
64
85
  "types": "types/index.d.ts",
65
- "version": "2.27.0"
86
+ "version": "2.29.0"
66
87
  }
@@ -288,7 +288,7 @@ const DatePicker = forwardRef(
288
288
  onChange={onChangeInput}
289
289
  tooltip={tooltip}
290
290
  hintPosition={hintPosition}
291
- label={dictionary[copy]?.roleDescription ?? label}
291
+ label={label ?? dictionary[copy]?.roleDescription}
292
292
  value={inputText}
293
293
  validation={validation}
294
294
  inactive={disabled}
@@ -26,7 +26,7 @@ const GlobalBodyScrollLock = createGlobalStyle({
26
26
  })
27
27
 
28
28
  const StyledFootnote = styled.div(
29
- ({ footnoteBackground, isVisible, footnoteBorderTop, isScrollable }) => ({
29
+ ({ footnoteBackground, isVisible, footnoteBorderTop, isScrollable, isMobileFullScreen }) => ({
30
30
  position: 'fixed',
31
31
  overflowY: isVisible && isScrollable ? 'scroll' : 'hidden',
32
32
  top: 0,
@@ -43,13 +43,15 @@ const StyledFootnote = styled.div(
43
43
  },
44
44
  zIndex: 99999,
45
45
  visibility: isVisible ? 'visible' : 'hidden',
46
- ...media().from('md').css({
47
- top: 'auto',
48
- bottom: 0,
49
- height: 'auto',
50
- maxHeight: '50vh',
51
- borderTop: footnoteBorderTop
52
- })
46
+ ...media()
47
+ .from(isMobileFullScreen ? 'md' : 'xs')
48
+ .css({
49
+ top: 'auto',
50
+ bottom: 0,
51
+ height: 'auto',
52
+ maxHeight: '50vh',
53
+ borderTop: footnoteBorderTop
54
+ })
53
55
  }),
54
56
  ({ isOpen }) => {
55
57
  if (isOpen) {
@@ -217,6 +219,7 @@ const Footnote = (props) => {
217
219
  isOpen,
218
220
  tokens,
219
221
  variant = {},
222
+ isMobileFullScreen = true,
220
223
  dictionary = defaultDictionary,
221
224
  ...rest
222
225
  } = props
@@ -488,6 +491,7 @@ const Footnote = (props) => {
488
491
  footnoteBackground={footnoteBackground}
489
492
  footnoteBorderTop={`${footnoteBorderTopSizeMd}px solid ${footnoteBorderColorMd}`}
490
493
  isScrollable={isScrollable}
494
+ isMobileFullScreen={isMobileFullScreen}
491
495
  >
492
496
  <ContentContainer maxWidth={maxWidth}>
493
497
  <StyledFootnoteHeader ref={headerRef} viewport={viewport}>
@@ -588,14 +592,19 @@ Footnote.propTypes = {
588
592
  dictionary: PropTypes.shape({
589
593
  en: dictionaryContentShape,
590
594
  fr: dictionaryContentShape
591
- })
595
+ }),
596
+ /**
597
+ * A boolean flag used to disable isMobileFullScreen of Footnote for mobile view
598
+ */
599
+ isMobileFullScreen: PropTypes.bool
592
600
  }
593
601
 
594
602
  Footnote.defaultProps = {
595
603
  isOpen: false,
596
604
  number: undefined,
597
605
  content: undefined,
598
- copy: 'en'
606
+ copy: 'en',
607
+ isMobileFullScreen: true
599
608
  }
600
609
 
601
610
  export default Footnote
@@ -1,24 +1,10 @@
1
1
  import React from 'react'
2
2
  import PropTypes from 'prop-types'
3
- import styled from 'styled-components'
4
- import { selectSystemProps, useThemeTokens, getTokensPropType } from '@telus-uds/components-base'
5
- import { htmlAttrs, warn } from '../utils'
3
+ import { htmlAttrs, selectSystemProps, getTokensPropType } from '@telus-uds/components-base/server'
4
+ import { warn } from '../utils/logger'
6
5
 
7
6
  const [selectProps, selectedSystemPropTypes] = selectSystemProps([htmlAttrs])
8
7
 
9
- const StyledImage = styled.img(({ height }) => {
10
- return {
11
- height: height ?? 'auto',
12
- maxWidth: '100%'
13
- }
14
- })
15
- const StyledRoundedImage = styled(StyledImage)`
16
- border-radius: ${({ borderRadius }) => borderRadius}px;
17
- `
18
- const StyledCircularImage = styled(StyledImage)({
19
- borderRadius: '50%'
20
- })
21
-
22
8
  const Image = ({
23
9
  src,
24
10
  width,
@@ -27,10 +13,11 @@ const Image = ({
27
13
  rounded,
28
14
  loading = 'eager',
29
15
  tokens,
16
+ theme,
30
17
  variant,
31
18
  ...rest
32
19
  }) => {
33
- const { borderRadius } = useThemeTokens('Image', tokens, variant)
20
+ let { borderRadius } = theme
34
21
  const isCircle = rounded === 'circle'
35
22
  const isCorners = rounded === 'corners'
36
23
  const isSquare = width === height
@@ -42,19 +29,21 @@ const Image = ({
42
29
  )
43
30
  }
44
31
 
45
- let ImageComponent
46
32
  if (isCircle) {
47
- ImageComponent = StyledCircularImage
33
+ borderRadius = '50%'
48
34
  } else if (isCorners) {
49
- ImageComponent = StyledRoundedImage
50
- } else {
51
- ImageComponent = StyledImage
35
+ borderRadius = '4px'
52
36
  }
53
37
 
38
+ const style = {
39
+ borderRadius,
40
+ height: height ?? 'auto',
41
+ maxWidth: '100%'
42
+ }
54
43
  return (
55
- <ImageComponent
44
+ <img
56
45
  {...selectProps(rest)}
57
- borderRadius={borderRadius}
46
+ style={style}
58
47
  src={src}
59
48
  width={width}
60
49
  height={height}
@@ -97,4 +86,6 @@ Image.propTypes = {
97
86
  tokens: getTokensPropType('Image')
98
87
  }
99
88
 
89
+ Image.displayName = 'Image'
90
+
100
91
  export default Image
@@ -1,3 +1,8 @@
1
1
  import Image from './Image'
2
+ import withClientTheme from '../utils/theming/with-client-theme'
2
3
 
3
- export default Image
4
+ // Exporting the unwrapped component separately for react-docgen to extract info for docsite
5
+ export { Image as DefaultImage }
6
+
7
+ const ClientThemedImage = withClientTheme(Image)
8
+ export default ClientThemedImage
@@ -0,0 +1,5 @@
1
+ import withServerTheme from '../utils/theming/with-server-theme'
2
+ import Image from './Image'
3
+
4
+ const ServerThemedImage = withServerTheme(Image, 'Image')
5
+ export default ServerThemedImage
@@ -59,6 +59,11 @@ const createStyledCell = (htmlElement) => styled[htmlElement]`
59
59
  ? `inset 0 1px 0 ${cellBoxShadowColor}, inset 0 -1px 0 ${cellBoxShadowColor}`
60
60
  : `inset 0 1px 0 ${cellBoxShadowColor}`
61
61
  }};
62
+ ${({ display }) =>
63
+ display &&
64
+ `*:not(:empty) {
65
+ display: ${display};
66
+ }`}
62
67
  `
63
68
  const StyledHeaderCell = createStyledCell('th')
64
69
  const StyledDataCell = createStyledCell('td')
@@ -81,7 +86,8 @@ const Cell = ({ children, isFirstInRow, align = 'left', tokens: cellTokens, type
81
86
  fontSize,
82
87
  lineHeight,
83
88
  stickyBackgroundColor,
84
- fontColor
89
+ fontColor,
90
+ display
85
91
  } = useThemeTokens('Table', themeTokens, { spacing, type, text })
86
92
 
87
93
  const sharedProps = {
@@ -95,7 +101,8 @@ const Cell = ({ children, isFirstInRow, align = 'left', tokens: cellTokens, type
95
101
  cellPaddingLeft,
96
102
  cellPaddingBottom,
97
103
  stickyBackgroundColor,
98
- cellBoxShadowColor
104
+ cellBoxShadowColor,
105
+ display
99
106
  }
100
107
 
101
108
  const typographyTokens = {
package/src/index.js CHANGED
@@ -1,3 +1,5 @@
1
+ 'use client'
2
+
1
3
  export { default as Badge } from './Badge'
2
4
  export { default as OrderedList } from './OrderedList'
3
5
  export { default as PreviewCard } from './PreviewCard'
@@ -13,6 +15,7 @@ export { default as PriceLockup } from './PriceLockup'
13
15
  export { default as Footnote } from './Footnote'
14
16
  export { default as QuantitySelector } from './QuantitySelector'
15
17
  export { default as IconButton } from './IconButton'
18
+ export { default as Image, DefaultImage } from './Image'
16
19
  export { transformGradient } from './utils'
17
20
  export { default as Breadcrumbs } from './Breadcrumbs'
18
21
  export { default as BlockQuote } from './BlockQuote'
@@ -20,7 +23,6 @@ export { default as OptimizeImage } from './OptimizeImage'
20
23
  export { default as Testimonial } from './Testimonial'
21
24
  export { default as Toast } from './Toast'
22
25
  export { default as Table } from './Table'
23
- export { default as Image } from './Image'
24
26
  export { default as WebVideo } from './WebVideo'
25
27
  export { default as WaffleGrid } from './WaffleGrid'
26
28
  export { default as Spinner } from './Spinner'
package/src/server.js ADDED
@@ -0,0 +1,5 @@
1
+ import ServerThemedImage from './Image/server'
2
+
3
+ // Export themed components
4
+ /* eslint-disable import/prefer-default-export */
5
+ export { ServerThemedImage as Image }
@@ -0,0 +1,22 @@
1
+ const cachedTheme = {}
2
+ const theme = process.env.UDS_THEME
3
+
4
+ async function importTheme(componentName) {
5
+ try {
6
+ cachedTheme[componentName] = await import(
7
+ `@telus-uds/theme-${theme}/build/rn/${componentName}.js`
8
+ )
9
+ } catch (_) {
10
+ throw new Error(
11
+ `An error occurred while trying to import theme-${process.env.UDS_THEME}. Please check that the theme has been installed in your app or that you are not importing a server component inside a client component.`
12
+ )
13
+ }
14
+ }
15
+
16
+ export default async function getTheme(componentName) {
17
+ if (cachedTheme[componentName]) {
18
+ return cachedTheme[componentName]
19
+ }
20
+ await importTheme(componentName)
21
+ return cachedTheme[componentName]
22
+ }
@@ -0,0 +1,20 @@
1
+ import React from 'react'
2
+ import PropTypes from 'prop-types'
3
+
4
+ import { useThemeTokens } from '@telus-uds/components-base'
5
+
6
+ const withClientTheme = (Component) => {
7
+ const UdsStyledComponent = ({ tokens: tokenOverrides, variant, ...props }) => {
8
+ const theme = useThemeTokens(Component.displayName, variant, tokenOverrides)
9
+ return <Component theme={theme} {...props} />
10
+ }
11
+
12
+ UdsStyledComponent.propTypes = {
13
+ tokens: PropTypes.oneOfType([PropTypes.func, PropTypes.object]),
14
+ variant: PropTypes.string
15
+ }
16
+
17
+ return UdsStyledComponent
18
+ }
19
+
20
+ export default withClientTheme
@@ -0,0 +1,21 @@
1
+ import React from 'react'
2
+ import PropTypes from 'prop-types'
3
+ import { getThemeTokens } from '@telus-uds/components-base/server'
4
+
5
+ import getTheme from './get-theme-from-server'
6
+
7
+ const withServerTheme = (Component, componentName) => {
8
+ const UdsStyledComponent = async ({ tokens: tokenOverrides, variant, ...props }) => {
9
+ const componentTheme = await getTheme(componentName)
10
+ const themeTokens = getThemeTokens(componentTheme, tokenOverrides, variant)
11
+ return <Component theme={themeTokens} {...props} />
12
+ }
13
+ UdsStyledComponent.propTypes = {
14
+ tokens: PropTypes.oneOfType([PropTypes.func, PropTypes.object]),
15
+ variant: PropTypes.string
16
+ }
17
+
18
+ return UdsStyledComponent
19
+ }
20
+
21
+ export default withServerTheme