@constructor-io/constructorio-ui-autocomplete 1.9.1 → 1.9.3

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.
Files changed (76) hide show
  1. package/dist/constructorio-ui-autocomplete-bundled.js +15 -15
  2. package/lib/cjs/{src/components → components}/Autocomplete/SectionItem/SectionItem.js +13 -8
  3. package/lib/cjs/components/Autocomplete/SectionItem/SectionItemText.js +25 -0
  4. package/lib/cjs/{src/components → components}/Autocomplete/SectionItemsList/SectionItemsList.js +1 -1
  5. package/lib/cjs/{src/constants.js → constants.js} +3 -1
  6. package/lib/cjs/{src/utils.js → utils.js} +5 -3
  7. package/lib/cjs/version.js +3 -0
  8. package/lib/mjs/{src/components → components}/Autocomplete/SectionItem/SectionItem.js +13 -8
  9. package/lib/mjs/components/Autocomplete/SectionItem/SectionItemText.js +21 -0
  10. package/lib/mjs/{src/components → components}/Autocomplete/SectionItemsList/SectionItemsList.js +1 -1
  11. package/lib/mjs/{src/constants.js → constants.js} +2 -0
  12. package/lib/mjs/{src/utils.js → utils.js} +3 -2
  13. package/lib/mjs/version.js +1 -0
  14. package/lib/types/{src/components → components}/Autocomplete/SectionItem/SectionItem.d.ts +1 -0
  15. package/lib/types/components/Autocomplete/SectionItem/SectionItemText.d.ts +8 -0
  16. package/lib/types/{src/constants.d.ts → constants.d.ts} +2 -0
  17. package/lib/types/{src/types.d.ts → types.d.ts} +1 -0
  18. package/lib/types/{src/utils.d.ts → utils.d.ts} +1 -0
  19. package/lib/types/version.d.ts +2 -0
  20. package/package.json +4 -3
  21. package/lib/cjs/package.json +0 -103
  22. package/lib/mjs/package.json +0 -103
  23. /package/lib/cjs/{src/components → components}/Autocomplete/AutocompleteResults/AutocompleteResults.js +0 -0
  24. /package/lib/cjs/{src/components → components}/Autocomplete/CioAutocomplete/CioAutocomplete.js +0 -0
  25. /package/lib/cjs/{src/components → components}/Autocomplete/CioAutocompleteProvider.js +0 -0
  26. /package/lib/cjs/{src/components → components}/Autocomplete/SearchInput/SearchInput.js +0 -0
  27. /package/lib/cjs/{src/hooks → hooks}/useCioAutocomplete.js +0 -0
  28. /package/lib/cjs/{src/hooks → hooks}/useCioClient.js +0 -0
  29. /package/lib/cjs/{src/hooks → hooks}/useConsoleErrors.js +0 -0
  30. /package/lib/cjs/{src/hooks → hooks}/useDebounce.js +0 -0
  31. /package/lib/cjs/{src/hooks → hooks}/useDebouncedFetchSections.js +0 -0
  32. /package/lib/cjs/{src/hooks → hooks}/useDownShift.js +0 -0
  33. /package/lib/cjs/{src/hooks → hooks}/useFetchRecommendationPod.js +0 -0
  34. /package/lib/cjs/{src/hooks → hooks}/useItems.js +0 -0
  35. /package/lib/cjs/{src/hooks → hooks}/usePrevious.js +0 -0
  36. /package/lib/cjs/{src/hooks → hooks}/useSections.js +0 -0
  37. /package/lib/cjs/{src/index.js → index.js} +0 -0
  38. /package/lib/cjs/{src/stories → stories}/Autocomplete/argTypes.js +0 -0
  39. /package/lib/cjs/{src/typeGuards.js → typeGuards.js} +0 -0
  40. /package/lib/cjs/{src/types.js → types.js} +0 -0
  41. /package/lib/mjs/{src/components → components}/Autocomplete/AutocompleteResults/AutocompleteResults.js +0 -0
  42. /package/lib/mjs/{src/components → components}/Autocomplete/CioAutocomplete/CioAutocomplete.js +0 -0
  43. /package/lib/mjs/{src/components → components}/Autocomplete/CioAutocompleteProvider.js +0 -0
  44. /package/lib/mjs/{src/components → components}/Autocomplete/SearchInput/SearchInput.js +0 -0
  45. /package/lib/mjs/{src/hooks → hooks}/useCioAutocomplete.js +0 -0
  46. /package/lib/mjs/{src/hooks → hooks}/useCioClient.js +0 -0
  47. /package/lib/mjs/{src/hooks → hooks}/useConsoleErrors.js +0 -0
  48. /package/lib/mjs/{src/hooks → hooks}/useDebounce.js +0 -0
  49. /package/lib/mjs/{src/hooks → hooks}/useDebouncedFetchSections.js +0 -0
  50. /package/lib/mjs/{src/hooks → hooks}/useDownShift.js +0 -0
  51. /package/lib/mjs/{src/hooks → hooks}/useFetchRecommendationPod.js +0 -0
  52. /package/lib/mjs/{src/hooks → hooks}/useItems.js +0 -0
  53. /package/lib/mjs/{src/hooks → hooks}/usePrevious.js +0 -0
  54. /package/lib/mjs/{src/hooks → hooks}/useSections.js +0 -0
  55. /package/lib/mjs/{src/index.js → index.js} +0 -0
  56. /package/lib/mjs/{src/stories → stories}/Autocomplete/argTypes.js +0 -0
  57. /package/lib/mjs/{src/typeGuards.js → typeGuards.js} +0 -0
  58. /package/lib/mjs/{src/types.js → types.js} +0 -0
  59. /package/lib/types/{src/components → components}/Autocomplete/AutocompleteResults/AutocompleteResults.d.ts +0 -0
  60. /package/lib/types/{src/components → components}/Autocomplete/CioAutocomplete/CioAutocomplete.d.ts +0 -0
  61. /package/lib/types/{src/components → components}/Autocomplete/CioAutocompleteProvider.d.ts +0 -0
  62. /package/lib/types/{src/components → components}/Autocomplete/SearchInput/SearchInput.d.ts +0 -0
  63. /package/lib/types/{src/components → components}/Autocomplete/SectionItemsList/SectionItemsList.d.ts +0 -0
  64. /package/lib/types/{src/hooks → hooks}/useCioAutocomplete.d.ts +0 -0
  65. /package/lib/types/{src/hooks → hooks}/useCioClient.d.ts +0 -0
  66. /package/lib/types/{src/hooks → hooks}/useConsoleErrors.d.ts +0 -0
  67. /package/lib/types/{src/hooks → hooks}/useDebounce.d.ts +0 -0
  68. /package/lib/types/{src/hooks → hooks}/useDebouncedFetchSections.d.ts +0 -0
  69. /package/lib/types/{src/hooks → hooks}/useDownShift.d.ts +0 -0
  70. /package/lib/types/{src/hooks → hooks}/useFetchRecommendationPod.d.ts +0 -0
  71. /package/lib/types/{src/hooks → hooks}/useItems.d.ts +0 -0
  72. /package/lib/types/{src/hooks → hooks}/usePrevious.d.ts +0 -0
  73. /package/lib/types/{src/hooks → hooks}/useSections.d.ts +0 -0
  74. /package/lib/types/{src/index.d.ts → index.d.ts} +0 -0
  75. /package/lib/types/{src/stories → stories}/Autocomplete/argTypes.d.ts +0 -0
  76. /package/lib/types/{src/typeGuards.d.ts → typeGuards.d.ts} +0 -0
@@ -4,33 +4,38 @@ const tslib_1 = require("tslib");
4
4
  const react_1 = tslib_1.__importStar(require("react"));
5
5
  const CioAutocompleteProvider_1 = require("../CioAutocompleteProvider");
6
6
  const typeGuards_1 = require("../../../typeGuards");
7
+ const SectionItemText_1 = tslib_1.__importDefault(require("./SectionItemText"));
7
8
  function SectionItem(props) {
8
9
  var _a, _b, _c, _d, _e;
9
- const { item, children } = props;
10
- const { getItemProps, advancedParameters } = (0, react_1.useContext)(CioAutocompleteProvider_1.CioAutocompleteContext);
10
+ const { item, children, displaySearchTermHighlights } = props;
11
+ const { getItemProps, advancedParameters, query } = (0, react_1.useContext)(CioAutocompleteProvider_1.CioAutocompleteContext);
11
12
  const { displaySearchSuggestionImages, displaySearchSuggestionResultCounts } = advancedParameters || {};
12
13
  let defaultChildren;
13
14
  if ((0, typeGuards_1.isProduct)(item)) {
14
15
  defaultChildren = (react_1.default.createElement(react_1.default.Fragment, null,
15
16
  react_1.default.createElement("img", { "data-testid": 'cio-img', src: (_a = item.data) === null || _a === void 0 ? void 0 : _a.image_url, alt: item.value, className: 'cio-product-image' }),
16
- react_1.default.createElement("p", { "data-testid": 'cio-text', className: 'cio-product-text' }, item.value)));
17
+ react_1.default.createElement("p", { "data-testid": 'cio-text', className: 'cio-product-text' },
18
+ react_1.default.createElement(SectionItemText_1.default, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights }))));
17
19
  }
18
20
  else if ((0, typeGuards_1.isInGroupSuggestion)(item)) {
19
- defaultChildren = react_1.default.createElement("p", { className: 'cio-term-in-group' },
20
- "in ",
21
- item.groupName);
21
+ defaultChildren = (react_1.default.createElement("p", { className: 'cio-term-in-group' },
22
+ "in",
23
+ ' ',
24
+ react_1.default.createElement(SectionItemText_1.default, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })));
22
25
  }
23
26
  else if ((0, typeGuards_1.isSearchSuggestion)(item)) {
24
27
  defaultChildren = (react_1.default.createElement(react_1.default.Fragment, null,
25
28
  displaySearchSuggestionImages && ((_b = item.data) === null || _b === void 0 ? void 0 : _b.image_url) && (react_1.default.createElement("img", { src: (_c = item.data) === null || _c === void 0 ? void 0 : _c.image_url, alt: item.value, className: 'cio-suggestion-image' })),
26
- react_1.default.createElement("p", { className: 'cio-suggestion-text' }, item.value),
29
+ react_1.default.createElement("p", { className: 'cio-suggestion-text' },
30
+ react_1.default.createElement(SectionItemText_1.default, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })),
27
31
  displaySearchSuggestionResultCounts && ((_d = item.data) === null || _d === void 0 ? void 0 : _d.total_num_results) && (react_1.default.createElement("p", { className: 'cio-suggestion-count' },
28
32
  "(", (_e = item.data) === null || _e === void 0 ? void 0 :
29
33
  _e.total_num_results,
30
34
  ")"))));
31
35
  }
32
36
  else {
33
- defaultChildren = react_1.default.createElement("p", { className: 'cio-custom-text' }, item.value);
37
+ defaultChildren = (react_1.default.createElement("p", { className: 'cio-custom-text' },
38
+ react_1.default.createElement(SectionItemText_1.default, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })));
34
39
  }
35
40
  return react_1.default.createElement("li", Object.assign({}, getItemProps(item)), children || defaultChildren);
36
41
  }
@@ -0,0 +1,25 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const tslib_1 = require("tslib");
4
+ const react_1 = tslib_1.__importDefault(require("react"));
5
+ const typeGuards_1 = require("../../../typeGuards");
6
+ const utils_1 = require("../../../utils");
7
+ function SectionItemText({ item, query, highlightSearchTerm, }) {
8
+ const itemText = (0, typeGuards_1.isInGroupSuggestion)(item) ? item.groupName : item.value;
9
+ if (highlightSearchTerm) {
10
+ const queryRegex = new RegExp(`(${(0, utils_1.escapeRegExp)(query)})`, 'gi');
11
+ const queryIncludedInText = queryRegex.test(itemText);
12
+ if (query && queryIncludedInText) {
13
+ const splitText = itemText.split(queryRegex);
14
+ return (react_1.default.createElement(react_1.default.Fragment, null, splitText.map((split, index) => {
15
+ // eslint-disable-next-line react/no-array-index-key
16
+ if (queryRegex.test(split))
17
+ return react_1.default.createElement("b", { key: `matched-word-${index}` }, split);
18
+ return split;
19
+ })));
20
+ }
21
+ }
22
+ // eslint-disable-next-line react/jsx-no-useless-fragment
23
+ return react_1.default.createElement(react_1.default.Fragment, null, itemText);
24
+ }
25
+ exports.default = SectionItemText;
@@ -12,7 +12,7 @@ const DefaultRenderSectionItemsList = function ({ section }) {
12
12
  return null;
13
13
  return (react_1.default.createElement("li", { className: `${sectionName} cio-section`, role: 'none' },
14
14
  react_1.default.createElement("h5", { className: 'cio-sectionName', "aria-hidden": true }, (0, utils_1.camelToStartCase)(sectionName)),
15
- react_1.default.createElement("ul", { className: 'cio-section-items', role: 'none' }, (_b = section === null || section === void 0 ? void 0 : section.data) === null || _b === void 0 ? void 0 : _b.map((item) => (react_1.default.createElement(SectionItem_1.default, { item: item, key: item === null || item === void 0 ? void 0 : item.id }))))));
15
+ react_1.default.createElement("ul", { className: 'cio-section-items', role: 'none' }, (_b = section === null || section === void 0 ? void 0 : section.data) === null || _b === void 0 ? void 0 : _b.map((item) => (react_1.default.createElement(SectionItem_1.default, { item: item, key: item === null || item === void 0 ? void 0 : item.id, displaySearchTermHighlights: section.displaySearchTermHighlights }))))));
16
16
  };
17
17
  function SectionItemsList(props) {
18
18
  const { section, children = DefaultRenderSectionItemsList } = props;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.termsWithImagesAndCountsDescription = exports.filteredSuggestionsDescription = exports.termsWithGroupSuggestionsDescription = exports.advancedParametersDefaultDescription = exports.advancedParametersDescription = exports.customStylesDescription = exports.multipleSectionsDescription = exports.openOnFocusDescription = exports.zeroStateSectionsDescription = exports.onSubmitDefault = exports.onSubmitDescription = exports.onChangeDescription = exports.onFocusDescription = exports.customSectionDescription = exports.recommendationsDescription = exports.sectionOrderDescription = exports.numResultsDescription = exports.contentDescription = exports.productsDescription = exports.searchSuggestionsDescription = exports.placeholderDescription = exports.cioJsClientDescription = exports.apiKeyDescription = exports.zeroStateDescription = exports.userEventsDescription = exports.sectionsDescription = exports.hookDescription = exports.componentDescription = exports.apiKey = void 0;
3
+ exports.termsWithImagesAndCountsDescription = exports.filteredSuggestionsDescription = exports.termsWithGroupSuggestionsDescription = exports.advancedParametersDefaultDescription = exports.advancedParametersDescription = exports.customStylesDescription = exports.multipleSectionsDescription = exports.openOnFocusDescription = exports.zeroStateSectionsDescription = exports.onSubmitDefault = exports.onSubmitDescription = exports.onChangeDescription = exports.onFocusDescription = exports.customSectionDescription = exports.displaySearchTermHighlightsDescription = exports.recommendationsDescription = exports.sectionOrderDescription = exports.numResultsDescription = exports.contentDescription = exports.productsDescription = exports.searchSuggestionsDescription = exports.placeholderDescription = exports.cioJsClientDescription = exports.apiKeyDescription = exports.fullFeaturedAndStyledExampleDescription = exports.zeroStateDescription = exports.userEventsDescription = exports.sectionsDescription = exports.hookDescription = exports.componentDescription = exports.apiKey = void 0;
4
4
  // Autocomplete key index
5
5
  exports.apiKey = 'key_M57QS8SMPdLdLx4x';
6
6
  /// //////////////////////////////
@@ -97,6 +97,7 @@ exports.zeroStateDescription = `- when the text input field has no text, we call
97
97
  /// //////////////////////////////
98
98
  // Storybook Stories
99
99
  /// //////////////////////////////
100
+ exports.fullFeaturedAndStyledExampleDescription = `Using the default options, the library displays clean and minimal visual elements, with the intent of making it easy for consumers to easily extend and customize the styles to suit unique needs. The example below shows a full featured and styled example to demonstrate what is possible using Constructor.io's advanced Autocomplete UI library.`;
100
101
  exports.apiKeyDescription = `Pass an \`apiKey\` to request results from constructor's servers`;
101
102
  exports.cioJsClientDescription = `If you are already using an instance of the \`ConstructorIOClient\`, you can pass a \`cioJsClient\` instead of an \`apiKey\` to request results from constructor's servers
102
103
 
@@ -108,6 +109,7 @@ exports.contentDescription = `Override default \`sections\` to only suggest cont
108
109
  exports.numResultsDescription = `Override default \`numResults\` to only suggest 2 products per query`;
109
110
  exports.sectionOrderDescription = `Override default \`numResults\` to suggest products, then terms`;
110
111
  exports.recommendationsDescription = `Use constructor's recommendations service, with \`"type": "recommendations"\``;
112
+ exports.displaySearchTermHighlightsDescription = `Use constructor's auto highlighting of words that match the search keyword, with \`"displaySearchTermHighlights": true\``;
111
113
  exports.customSectionDescription = `Use a custom section, by managing and passing your own data, with \`"type": "custom"\` and \`"data":[{...}]\``;
112
114
  exports.onFocusDescription = `Pass an \`onFocus\` callback function to execute some code each time the user applies focus to the text input field`;
113
115
  exports.onChangeDescription = `Pass an \`onChange\` callback function to execute some code each time the user changes the value of the text input field`;
@@ -1,10 +1,10 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getActiveSectionsWithData = exports.getCioClient = exports.disableStoryActions = exports.stringifyWithDefaults = exports.functionStrings = exports.getStoryParams = exports.sleep = exports.clearConstructorRequests = exports.isTrackingRequestSent = exports.camelToStartCase = exports.getItemPosition = void 0;
3
+ exports.escapeRegExp = exports.getActiveSectionsWithData = exports.getCioClient = exports.disableStoryActions = exports.stringifyWithDefaults = exports.functionStrings = exports.getStoryParams = exports.sleep = exports.clearConstructorRequests = exports.isTrackingRequestSent = exports.camelToStartCase = exports.getItemPosition = void 0;
4
4
  const tslib_1 = require("tslib");
5
5
  const constructorio_client_javascript_1 = tslib_1.__importDefault(require("@constructor-io/constructorio-client-javascript"));
6
6
  const typeGuards_1 = require("./typeGuards");
7
- const package_json_1 = require("../package.json");
7
+ const version_1 = tslib_1.__importDefault(require("./version"));
8
8
  const getItemPosition = ({ item, items }) => {
9
9
  var _a;
10
10
  const index = items.findIndex((itemInFlatList) => (itemInFlatList === null || itemInFlatList === void 0 ? void 0 : itemInFlatList.id) === (item === null || item === void 0 ? void 0 : item.id));
@@ -89,7 +89,7 @@ const getCioClient = (apiKey) => {
89
89
  return new constructorio_client_javascript_1.default({
90
90
  apiKey,
91
91
  sendTrackingEvents: true,
92
- version: `cio-ui-autocomplete-${package_json_1.version}`,
92
+ version: `cio-ui-autocomplete-${version_1.default}`,
93
93
  });
94
94
  }
95
95
  return null;
@@ -117,3 +117,5 @@ const getActiveSectionsWithData = (activeSections, sectionResults) => {
117
117
  return activeSectionsWithData;
118
118
  };
119
119
  exports.getActiveSectionsWithData = getActiveSectionsWithData;
120
+ const escapeRegExp = (string) => string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
121
+ exports.escapeRegExp = escapeRegExp;
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.default = '1.9.3';
@@ -1,32 +1,37 @@
1
1
  import React, { useContext } from 'react';
2
2
  import { CioAutocompleteContext } from '../CioAutocompleteProvider';
3
3
  import { isProduct, isInGroupSuggestion, isSearchSuggestion } from '../../../typeGuards';
4
+ import SectionItemText from './SectionItemText';
4
5
  export default function SectionItem(props) {
5
- const { item, children } = props;
6
- const { getItemProps, advancedParameters } = useContext(CioAutocompleteContext);
6
+ const { item, children, displaySearchTermHighlights } = props;
7
+ const { getItemProps, advancedParameters, query } = useContext(CioAutocompleteContext);
7
8
  const { displaySearchSuggestionImages, displaySearchSuggestionResultCounts } = advancedParameters || {};
8
9
  let defaultChildren;
9
10
  if (isProduct(item)) {
10
11
  defaultChildren = (React.createElement(React.Fragment, null,
11
12
  React.createElement("img", { "data-testid": 'cio-img', src: item.data?.image_url, alt: item.value, className: 'cio-product-image' }),
12
- React.createElement("p", { "data-testid": 'cio-text', className: 'cio-product-text' }, item.value)));
13
+ React.createElement("p", { "data-testid": 'cio-text', className: 'cio-product-text' },
14
+ React.createElement(SectionItemText, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights }))));
13
15
  }
14
16
  else if (isInGroupSuggestion(item)) {
15
- defaultChildren = React.createElement("p", { className: 'cio-term-in-group' },
16
- "in ",
17
- item.groupName);
17
+ defaultChildren = (React.createElement("p", { className: 'cio-term-in-group' },
18
+ "in",
19
+ ' ',
20
+ React.createElement(SectionItemText, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })));
18
21
  }
19
22
  else if (isSearchSuggestion(item)) {
20
23
  defaultChildren = (React.createElement(React.Fragment, null,
21
24
  displaySearchSuggestionImages && item.data?.image_url && (React.createElement("img", { src: item.data?.image_url, alt: item.value, className: 'cio-suggestion-image' })),
22
- React.createElement("p", { className: 'cio-suggestion-text' }, item.value),
25
+ React.createElement("p", { className: 'cio-suggestion-text' },
26
+ React.createElement(SectionItemText, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })),
23
27
  displaySearchSuggestionResultCounts && item.data?.total_num_results && (React.createElement("p", { className: 'cio-suggestion-count' },
24
28
  "(",
25
29
  item.data?.total_num_results,
26
30
  ")"))));
27
31
  }
28
32
  else {
29
- defaultChildren = React.createElement("p", { className: 'cio-custom-text' }, item.value);
33
+ defaultChildren = (React.createElement("p", { className: 'cio-custom-text' },
34
+ React.createElement(SectionItemText, { item: item, query: query, highlightSearchTerm: displaySearchTermHighlights })));
30
35
  }
31
36
  return React.createElement("li", { ...getItemProps(item) }, children || defaultChildren);
32
37
  }
@@ -0,0 +1,21 @@
1
+ import React from 'react';
2
+ import { isInGroupSuggestion } from '../../../typeGuards';
3
+ import { escapeRegExp } from '../../../utils';
4
+ export default function SectionItemText({ item, query, highlightSearchTerm, }) {
5
+ const itemText = isInGroupSuggestion(item) ? item.groupName : item.value;
6
+ if (highlightSearchTerm) {
7
+ const queryRegex = new RegExp(`(${escapeRegExp(query)})`, 'gi');
8
+ const queryIncludedInText = queryRegex.test(itemText);
9
+ if (query && queryIncludedInText) {
10
+ const splitText = itemText.split(queryRegex);
11
+ return (React.createElement(React.Fragment, null, splitText.map((split, index) => {
12
+ // eslint-disable-next-line react/no-array-index-key
13
+ if (queryRegex.test(split))
14
+ return React.createElement("b", { key: `matched-word-${index}` }, split);
15
+ return split;
16
+ })));
17
+ }
18
+ }
19
+ // eslint-disable-next-line react/jsx-no-useless-fragment
20
+ return React.createElement(React.Fragment, null, itemText);
21
+ }
@@ -8,7 +8,7 @@ const DefaultRenderSectionItemsList = function ({ section }) {
8
8
  return null;
9
9
  return (React.createElement("li", { className: `${sectionName} cio-section`, role: 'none' },
10
10
  React.createElement("h5", { className: 'cio-sectionName', "aria-hidden": true }, camelToStartCase(sectionName)),
11
- React.createElement("ul", { className: 'cio-section-items', role: 'none' }, section?.data?.map((item) => (React.createElement(SectionItem, { item: item, key: item?.id }))))));
11
+ React.createElement("ul", { className: 'cio-section-items', role: 'none' }, section?.data?.map((item) => (React.createElement(SectionItem, { item: item, key: item?.id, displaySearchTermHighlights: section.displaySearchTermHighlights }))))));
12
12
  };
13
13
  export default function SectionItemsList(props) {
14
14
  const { section, children = DefaultRenderSectionItemsList } = props;
@@ -94,6 +94,7 @@ export const zeroStateDescription = `- when the text input field has no text, we
94
94
  /// //////////////////////////////
95
95
  // Storybook Stories
96
96
  /// //////////////////////////////
97
+ export const fullFeaturedAndStyledExampleDescription = `Using the default options, the library displays clean and minimal visual elements, with the intent of making it easy for consumers to easily extend and customize the styles to suit unique needs. The example below shows a full featured and styled example to demonstrate what is possible using Constructor.io's advanced Autocomplete UI library.`;
97
98
  export const apiKeyDescription = `Pass an \`apiKey\` to request results from constructor's servers`;
98
99
  export const cioJsClientDescription = `If you are already using an instance of the \`ConstructorIOClient\`, you can pass a \`cioJsClient\` instead of an \`apiKey\` to request results from constructor's servers
99
100
 
@@ -105,6 +106,7 @@ export const contentDescription = `Override default \`sections\` to only suggest
105
106
  export const numResultsDescription = `Override default \`numResults\` to only suggest 2 products per query`;
106
107
  export const sectionOrderDescription = `Override default \`numResults\` to suggest products, then terms`;
107
108
  export const recommendationsDescription = `Use constructor's recommendations service, with \`"type": "recommendations"\``;
109
+ export const displaySearchTermHighlightsDescription = `Use constructor's auto highlighting of words that match the search keyword, with \`"displaySearchTermHighlights": true\``;
108
110
  export const customSectionDescription = `Use a custom section, by managing and passing your own data, with \`"type": "custom"\` and \`"data":[{...}]\``;
109
111
  export const onFocusDescription = `Pass an \`onFocus\` callback function to execute some code each time the user applies focus to the text input field`;
110
112
  export const onChangeDescription = `Pass an \`onChange\` callback function to execute some code each time the user changes the value of the text input field`;
@@ -1,6 +1,6 @@
1
1
  import ConstructorIOClient from '@constructor-io/constructorio-client-javascript';
2
2
  import { isCustomSection } from './typeGuards';
3
- import { version as packageVersion } from '../package.json';
3
+ import version from './version';
4
4
  export const getItemPosition = ({ item, items }) => {
5
5
  const index = items.findIndex((itemInFlatList) => itemInFlatList?.id === item?.id);
6
6
  const sectionId = items[index]?.section;
@@ -74,7 +74,7 @@ export const getCioClient = (apiKey) => {
74
74
  return new ConstructorIOClient({
75
75
  apiKey,
76
76
  sendTrackingEvents: true,
77
- version: `cio-ui-autocomplete-${packageVersion}`,
77
+ version: `cio-ui-autocomplete-${version}`,
78
78
  });
79
79
  }
80
80
  return null;
@@ -100,3 +100,4 @@ export const getActiveSectionsWithData = (activeSections, sectionResults) => {
100
100
  });
101
101
  return activeSectionsWithData;
102
102
  };
103
+ export const escapeRegExp = (string) => string.replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
@@ -0,0 +1 @@
1
+ export default '1.9.3';
@@ -4,5 +4,6 @@ export interface SectionItemProps {
4
4
  item: Item;
5
5
  children?: ReactNode;
6
6
  key?: string;
7
+ displaySearchTermHighlights?: boolean;
7
8
  }
8
9
  export default function SectionItem(props: SectionItemProps): JSX.Element;
@@ -0,0 +1,8 @@
1
+ /// <reference types="react" />
2
+ import { Item } from '../../../types';
3
+ export interface SectionItemTextProps {
4
+ item: Item;
5
+ query: string;
6
+ highlightSearchTerm?: boolean;
7
+ }
8
+ export default function SectionItemText({ item, query, highlightSearchTerm, }: SectionItemTextProps): JSX.Element;
@@ -5,6 +5,7 @@ export declare const hookDescription = "- import `useCioAutocomplete` and call t
5
5
  export declare const sectionsDescription = "- by default, typing a query will fetch data for search suggestions and Products\n- to override this, pass an array of sections objects\n- the order of the objects in the `sections` array determines the order of the results\n- each section object must have an `identifier`\n- each section object can specify a `type`\n- each section object can override the default `numResults` of 8\n\nWhen no values are passed for the `sections` argument, the following defaults are used:\n\n```jsx\n[\n {\n identifier: 'Search Suggestions',\n type: 'autocomplete',\n numResults: 8\n },\n {\n identifier: 'Products',\n type: 'autocomplete',\n numResults: 8\n }\n]\n```\n";
6
6
  export declare const userEventsDescription = "- pass callback functions to respond to user events\n- if provided, the onFocus callback function will be called each time the user focuses on the text input field\n- if provided, the onChange callback function will be called each time the user changes the value in the text input field\n- the onSubmit callback function will be called each time the user submits the form\n- the user can submit the form by pressing the enter key in the text input field, clicking a submit button within the form, clicking on a result, or pressing enter while a result is selected\n\n> \u26A0\uFE0F NOTE \u26A0\uFE0F Use the Storybook Canvas Actions tab to explore the behavior of all of these `OnEvent` callback functions as you interact with our Default User Events example rendered in the Canvas. In the stories below, Storybook Canvas Actions have been disabled to focus on each of these callback functions in isolation. Each of the example callback functions in the stories below log output to the console tab of the browser's developer tools.";
7
7
  export declare const zeroStateDescription = "- when the text input field has no text, we call this zero state\n- by default, the autocomplete shows nothing in the menu it's for zero state\n- to show zero state results, pass an array of section objects for `zeroStateSections`\n- when `zeroStateSections` has sections, the menu will open on user focus by default\n- set `openOnFocus` to false, to only show `zeroStateSections` after user has typed and then cleared the text input, instead of as soon as the user focuses on the text input\n- the order of the objects in the `zeroStateSections` array determines the order of the results\n- each section object must have an `identifier`\n- each section object can specify a `type`\n- each section object can override the default `numResults` of 8";
8
+ export declare const fullFeaturedAndStyledExampleDescription = "Using the default options, the library displays clean and minimal visual elements, with the intent of making it easy for consumers to easily extend and customize the styles to suit unique needs. The example below shows a full featured and styled example to demonstrate what is possible using Constructor.io's advanced Autocomplete UI library.";
8
9
  export declare const apiKeyDescription = "Pass an `apiKey` to request results from constructor's servers";
9
10
  export declare const cioJsClientDescription = "If you are already using an instance of the `ConstructorIOClient`, you can pass a `cioJsClient` instead of an `apiKey` to request results from constructor's servers\n\n> Note: when we say `cioJsClient`, we are referring to an instance of the [constructorio-client-javascript](https://www.npmjs.com/package/@constructor-io/constructorio-client-javascript)";
10
11
  export declare const placeholderDescription = "Pass a `placeholder` to override the default input field placeholder text shown to users before they start typing their query";
@@ -14,6 +15,7 @@ export declare const contentDescription = "Override default `sections` to only s
14
15
  export declare const numResultsDescription = "Override default `numResults` to only suggest 2 products per query";
15
16
  export declare const sectionOrderDescription = "Override default `numResults` to suggest products, then terms";
16
17
  export declare const recommendationsDescription = "Use constructor's recommendations service, with `\"type\": \"recommendations\"`";
18
+ export declare const displaySearchTermHighlightsDescription = "Use constructor's auto highlighting of words that match the search keyword, with `\"displaySearchTermHighlights\": true`";
17
19
  export declare const customSectionDescription = "Use a custom section, by managing and passing your own data, with `\"type\": \"custom\"` and `\"data\":[{...}]`";
18
20
  export declare const onFocusDescription = "Pass an `onFocus` callback function to execute some code each time the user applies focus to the text input field";
19
21
  export declare const onChangeDescription = "Pass an `onChange` callback function to execute some code each time the user changes the value of the text input field";
@@ -56,6 +56,7 @@ export type SectionConfiguration = {
56
56
  identifier: string;
57
57
  displayName?: string;
58
58
  numResults?: number;
59
+ displaySearchTermHighlights?: boolean;
59
60
  };
60
61
  export interface AutocompleteSection extends SectionConfiguration {
61
62
  type?: 'autocomplete';
@@ -33,4 +33,5 @@ export declare const stringifyWithDefaults: (obj: {
33
33
  export declare const disableStoryActions: (story: any) => void;
34
34
  export declare const getCioClient: (apiKey?: string) => ConstructorIOClient | null;
35
35
  export declare const getActiveSectionsWithData: (activeSections: UserDefinedSection[], sectionResults: AutocompleteResultSections) => Section[];
36
+ export declare const escapeRegExp: (string: string) => string;
36
37
  export {};
@@ -0,0 +1,2 @@
1
+ declare const _default: "1.9.3";
2
+ export default _default;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@constructor-io/constructorio-ui-autocomplete",
3
- "version": "1.9.1",
3
+ "version": "1.9.3",
4
4
  "description": "Constructor.io Autocomplete UI library for web applications",
5
5
  "main": "lib/cjs/index.js",
6
6
  "module": "lib/mjs/index.js",
@@ -34,8 +34,9 @@
34
34
  "build-storybook": "storybook build -o 'docs'",
35
35
  "serve-built-storybook": "npx http-server docs",
36
36
  "verify-node-version": "chmod +x ./scripts/verify-node-version.sh && ./scripts/verify-node-version.sh",
37
- "version": "npm run verify-node-version && npm run build-storybook && git add -u ./docs && git add ./docs/* && npm run compile",
38
- "compile": "rm -rf lib && tsc -p tsconfig.json && tsc -p tsconfig-cjs.json && npm run copy-styles && vite build"
37
+ "preversion": "node ./src/generateVersion.js",
38
+ "version": "npm run preversion && npm run verify-node-version && npm run build-storybook && git add -u ./docs && git add ./docs/* && git add ./src/version.ts && npm run compile",
39
+ "compile": "node ./src/generateVersion.js && rm -rf lib && tsc -p tsconfig.json && tsc -p tsconfig-cjs.json && npm run copy-styles && vite build"
39
40
  },
40
41
  "author": "constructor.io",
41
42
  "license": "MIT",
@@ -1,103 +0,0 @@
1
- {
2
- "name": "@constructor-io/constructorio-ui-autocomplete",
3
- "version": "1.9.1",
4
- "description": "Constructor.io Autocomplete UI library for web applications",
5
- "main": "lib/cjs/index.js",
6
- "module": "lib/mjs/index.js",
7
- "exports": {
8
- "./styles.css": {
9
- "import": "./lib/styles.css",
10
- "require": "./lib/styles.css"
11
- },
12
- ".": {
13
- "import": "./lib/mjs/index.js",
14
- "require": "./lib/cjs/index.js"
15
- },
16
- "./constructorio-ui-autocomplete-bundled": {
17
- "import": "./dist/constructorio-ui-autocomplete-bundled.js",
18
- "require": "./dist/constructorio-ui-autocomplete-bundled.js"
19
- }
20
- },
21
- "homepage": "https://github.com/Constructor-io/constructorio-ui-autocomplete#readme",
22
- "types": "lib/types/index.d.ts",
23
- "scripts": {
24
- "lint": "eslint src --ext js,ts,jsx,tsx",
25
- "check-types": "npx tsc --noEmit",
26
- "check-license": "license-checker --production --onlyAllow 'Apache-2.0;BSD-3-Clause;MIT;0BSD;BSD-2-Clause'",
27
- "copy-styles": "cp src/styles.css lib/styles.css",
28
- "prepare": "husky install",
29
- "dev": "storybook dev -p 6006",
30
- "storybook:ci": "storybook dev --ci --quiet -p 6006",
31
- "test-storybook": "test-storybook",
32
- "test-storybook:watch": "test-storybook --watch",
33
- "test-storybook:ci": "start-server-and-test storybook:ci http://localhost:6006 test-storybook",
34
- "build-storybook": "storybook build -o 'docs'",
35
- "serve-built-storybook": "npx http-server docs",
36
- "verify-node-version": "chmod +x ./scripts/verify-node-version.sh && ./scripts/verify-node-version.sh",
37
- "version": "npm run verify-node-version && npm run build-storybook && git add -u ./docs && git add ./docs/* && npm run compile",
38
- "compile": "rm -rf lib && tsc -p tsconfig.json && tsc -p tsconfig-cjs.json && npm run copy-styles && vite build"
39
- },
40
- "author": "constructor.io",
41
- "license": "MIT",
42
- "volta": {
43
- "node": "16.17.0",
44
- "npm": "8.19.2"
45
- },
46
- "repository": {
47
- "type": "git",
48
- "url": "git+https://github.com/Constructor-io/constructorio-ui-autocomplete.git"
49
- },
50
- "bugs": {
51
- "url": "https://github.com/Constructor-io/constructorio-ui-autocomplete/issues"
52
- },
53
- "files": [
54
- "lib/**/*",
55
- "dist/constructorio-ui-autocomplete-bundled.js"
56
- ],
57
- "engines": {
58
- "node": ">=14"
59
- },
60
- "devDependencies": {
61
- "@cspell/eslint-plugin": "^6.18.1",
62
- "@storybook/addon-a11y": "^7.0.14",
63
- "@storybook/addon-actions": "^7.0.14",
64
- "@storybook/addon-essentials": "^7.0.14",
65
- "@storybook/addon-interactions": "^7.0.14",
66
- "@storybook/addon-links": "^7.0.14",
67
- "@storybook/jest": "^0.1.0",
68
- "@storybook/react-webpack5": "7.0.14",
69
- "@storybook/test-runner": "^0.10.0",
70
- "@storybook/testing-library": "^0.1.0",
71
- "@types/react": "^18.0.20",
72
- "@types/react-dom": "^18.0.6",
73
- "@typescript-eslint/eslint-plugin": "^5.38.0",
74
- "@typescript-eslint/parser": "^5.38.0",
75
- "eslint": "^8.23.1",
76
- "eslint-config-airbnb": "^19.0.4",
77
- "eslint-config-airbnb-typescript": "^17.0.0",
78
- "eslint-config-prettier": "^8.5.0",
79
- "eslint-plugin-import": "^2.26.0",
80
- "eslint-plugin-jsx-a11y": "^6.6.1",
81
- "eslint-plugin-prettier": "^4.2.1",
82
- "eslint-plugin-react": "^7.31.11",
83
- "eslint-plugin-react-hooks": "^4.6.0",
84
- "eslint-plugin-storybook": "^0.6.12",
85
- "husky": "^8.0.1",
86
- "license-checker": "^25.0.1",
87
- "react": "^18.2.0",
88
- "react-dom": "^18.2.0",
89
- "start-server-and-test": "^1.15.2",
90
- "storybook": "^7.0.14",
91
- "typescript": "^4.8.3",
92
- "vite": "^4.3.7",
93
- "vite-plugin-css-injected-by-js": "^3.1.1",
94
- "webpack": "^5.75.0"
95
- },
96
- "peerDependencies": {
97
- "@constructor-io/constructorio-client-javascript": "^2.36.0",
98
- "downshift": "^7.2.1",
99
- "react": ">=16.12.0",
100
- "react-dom": ">=16.12.0",
101
- "tslib": "^2.5.0"
102
- }
103
- }
@@ -1,103 +0,0 @@
1
- {
2
- "name": "@constructor-io/constructorio-ui-autocomplete",
3
- "version": "1.9.1",
4
- "description": "Constructor.io Autocomplete UI library for web applications",
5
- "main": "lib/cjs/index.js",
6
- "module": "lib/mjs/index.js",
7
- "exports": {
8
- "./styles.css": {
9
- "import": "./lib/styles.css",
10
- "require": "./lib/styles.css"
11
- },
12
- ".": {
13
- "import": "./lib/mjs/index.js",
14
- "require": "./lib/cjs/index.js"
15
- },
16
- "./constructorio-ui-autocomplete-bundled": {
17
- "import": "./dist/constructorio-ui-autocomplete-bundled.js",
18
- "require": "./dist/constructorio-ui-autocomplete-bundled.js"
19
- }
20
- },
21
- "homepage": "https://github.com/Constructor-io/constructorio-ui-autocomplete#readme",
22
- "types": "lib/types/index.d.ts",
23
- "scripts": {
24
- "lint": "eslint src --ext js,ts,jsx,tsx",
25
- "check-types": "npx tsc --noEmit",
26
- "check-license": "license-checker --production --onlyAllow 'Apache-2.0;BSD-3-Clause;MIT;0BSD;BSD-2-Clause'",
27
- "copy-styles": "cp src/styles.css lib/styles.css",
28
- "prepare": "husky install",
29
- "dev": "storybook dev -p 6006",
30
- "storybook:ci": "storybook dev --ci --quiet -p 6006",
31
- "test-storybook": "test-storybook",
32
- "test-storybook:watch": "test-storybook --watch",
33
- "test-storybook:ci": "start-server-and-test storybook:ci http://localhost:6006 test-storybook",
34
- "build-storybook": "storybook build -o 'docs'",
35
- "serve-built-storybook": "npx http-server docs",
36
- "verify-node-version": "chmod +x ./scripts/verify-node-version.sh && ./scripts/verify-node-version.sh",
37
- "version": "npm run verify-node-version && npm run build-storybook && git add -u ./docs && git add ./docs/* && npm run compile",
38
- "compile": "rm -rf lib && tsc -p tsconfig.json && tsc -p tsconfig-cjs.json && npm run copy-styles && vite build"
39
- },
40
- "author": "constructor.io",
41
- "license": "MIT",
42
- "volta": {
43
- "node": "16.17.0",
44
- "npm": "8.19.2"
45
- },
46
- "repository": {
47
- "type": "git",
48
- "url": "git+https://github.com/Constructor-io/constructorio-ui-autocomplete.git"
49
- },
50
- "bugs": {
51
- "url": "https://github.com/Constructor-io/constructorio-ui-autocomplete/issues"
52
- },
53
- "files": [
54
- "lib/**/*",
55
- "dist/constructorio-ui-autocomplete-bundled.js"
56
- ],
57
- "engines": {
58
- "node": ">=14"
59
- },
60
- "devDependencies": {
61
- "@cspell/eslint-plugin": "^6.18.1",
62
- "@storybook/addon-a11y": "^7.0.14",
63
- "@storybook/addon-actions": "^7.0.14",
64
- "@storybook/addon-essentials": "^7.0.14",
65
- "@storybook/addon-interactions": "^7.0.14",
66
- "@storybook/addon-links": "^7.0.14",
67
- "@storybook/jest": "^0.1.0",
68
- "@storybook/react-webpack5": "7.0.14",
69
- "@storybook/test-runner": "^0.10.0",
70
- "@storybook/testing-library": "^0.1.0",
71
- "@types/react": "^18.0.20",
72
- "@types/react-dom": "^18.0.6",
73
- "@typescript-eslint/eslint-plugin": "^5.38.0",
74
- "@typescript-eslint/parser": "^5.38.0",
75
- "eslint": "^8.23.1",
76
- "eslint-config-airbnb": "^19.0.4",
77
- "eslint-config-airbnb-typescript": "^17.0.0",
78
- "eslint-config-prettier": "^8.5.0",
79
- "eslint-plugin-import": "^2.26.0",
80
- "eslint-plugin-jsx-a11y": "^6.6.1",
81
- "eslint-plugin-prettier": "^4.2.1",
82
- "eslint-plugin-react": "^7.31.11",
83
- "eslint-plugin-react-hooks": "^4.6.0",
84
- "eslint-plugin-storybook": "^0.6.12",
85
- "husky": "^8.0.1",
86
- "license-checker": "^25.0.1",
87
- "react": "^18.2.0",
88
- "react-dom": "^18.2.0",
89
- "start-server-and-test": "^1.15.2",
90
- "storybook": "^7.0.14",
91
- "typescript": "^4.8.3",
92
- "vite": "^4.3.7",
93
- "vite-plugin-css-injected-by-js": "^3.1.1",
94
- "webpack": "^5.75.0"
95
- },
96
- "peerDependencies": {
97
- "@constructor-io/constructorio-client-javascript": "^2.36.0",
98
- "downshift": "^7.2.1",
99
- "react": ">=16.12.0",
100
- "react-dom": ">=16.12.0",
101
- "tslib": "^2.5.0"
102
- }
103
- }
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes