@opexa/portal-components 0.1.39 → 0.1.41

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.
@@ -9,7 +9,6 @@ import { useDebounceCallback } from 'usehooks-ts';
9
9
  import { useShallow } from 'zustand/shallow';
10
10
  import { useBypassKycChecker, } from '../../client/hooks/useBypassKycChecker.js';
11
11
  import { useControllableState } from '../../client/hooks/useControllableState.js';
12
- import { useFeatureFlag } from '../../client/hooks/useFeatureFlag.js';
13
12
  import { useGamesQuery } from '../../client/hooks/useGamesQuery.js';
14
13
  import { useGlobalStore } from '../../client/hooks/useGlobalStore.js';
15
14
  import { GAME_PROVIDER_DATA, GAME_TYPE_DATA } from '../../constants/index.js';
@@ -37,7 +36,6 @@ function lookup(value, compare) {
37
36
  }
38
37
  export function Search(props) {
39
38
  const isBypass = useBypassKycChecker(props.bypassDomains);
40
- const featureFlag = useFeatureFlag();
41
39
  const globalStore = useGlobalStore(useShallow((ctx) => ({
42
40
  search: ctx.search,
43
41
  })));
@@ -66,12 +64,15 @@ export function Search(props) {
66
64
  .filter((type) => {
67
65
  return props.gameTypeImages?.[type.id] ?? defaultGameTypeImages[type.id];
68
66
  });
67
+ const isProviderOrTypeSearch = gameProviders.length > 0 || gameTypesFiltered.length > 0;
69
68
  const gamesQuery = useGamesQuery({
70
69
  first: 18,
71
- search: gameProviders.length > 0 ? undefined : search,
70
+ search: isProviderOrTypeSearch ? undefined : search,
72
71
  filter: {
73
72
  type: {
74
- in: props.gameTypes,
73
+ in: gameTypesFiltered.length > 0
74
+ ? gameTypesFiltered.map((t) => t.id)
75
+ : props.gameTypes,
75
76
  },
76
77
  provider: {
77
78
  in: gameProviders.length > 0
@@ -84,19 +85,23 @@ export function Search(props) {
84
85
  });
85
86
  const collapsedGamesQuery = useGamesQuery({
86
87
  first: 18,
87
- search: collapsedSearch,
88
+ search: isProviderOrTypeSearch ? undefined : collapsedSearch,
88
89
  filter: {
89
90
  type: {
90
- in: props.gameTypes,
91
+ in: gameTypesFiltered.length > 0
92
+ ? gameTypesFiltered.map((t) => t.id)
93
+ : props.gameTypes,
91
94
  },
92
95
  provider: {
93
- in: props.gameProviders,
96
+ in: gameProviders.length > 0
97
+ ? gameProviders.map((p) => p.id)
98
+ : props.gameProviders,
94
99
  },
95
100
  },
96
101
  }, {
97
102
  enabled: search.length >= 2 &&
98
103
  hasSpaces &&
99
- gameProviders.length === 0 &&
104
+ !isProviderOrTypeSearch &&
100
105
  collapsedSearch.length >= 2,
101
106
  });
102
107
  let games = mergeUniqueById(gamesQuery.data?.pages.flatMap((page) => page.edges.map((edge) => edge.node)) ?? [], collapsedGamesQuery.data?.pages.flatMap((page) => page.edges.map((edge) => edge.node)) ?? []);
@@ -104,6 +109,19 @@ export function Search(props) {
104
109
  const normalizedSearch = normalizeGameName(search);
105
110
  games = games.filter((game) => normalizeGameName(game.name).includes(normalizedSearch));
106
111
  }
112
+ const providersFromGameTypes = gameTypesFiltered.length > 0 && games.length > 0
113
+ ? [
114
+ ...new Set(games
115
+ .filter((game) => gameTypesFiltered.some((gt) => gt.id === game.type))
116
+ .map((game) => game.provider)),
117
+ ]
118
+ .map((providerId) => GAME_PROVIDER_DATA[providerId])
119
+ .filter((p) => p != null)
120
+ : [];
121
+ const displayGameProviders = [
122
+ ...gameProviders,
123
+ ...providersFromGameTypes.filter((p) => !gameProviders.some((gp) => gp.id === p.id)),
124
+ ];
107
125
  const hasNextPage = gamesQuery.hasNextPage || collapsedGamesQuery.hasNextPage;
108
126
  function fetchNextPage() {
109
127
  if (gamesQuery.hasNextPage) {
@@ -136,18 +154,16 @@ export function Search(props) {
136
154
  function fixMojibake(str) {
137
155
  return str.replace(/ÔÇÖ/g, "'").replace(/ÔÇô/g, '');
138
156
  }
139
- console.log(gameTypesFiltered, 'gameTypesFiltered');
140
157
  return (_jsx(Dialog.Root, { open: globalStore.search.open, onOpenChange: (details) => {
141
158
  globalStore.search.setOpen(details.open);
142
159
  setSearch('');
143
160
  }, lazyMount: true, unmountOnExit: true, children: _jsxs(Portal, { children: [_jsx(Dialog.Backdrop, {}), _jsx(Dialog.Positioner, { children: _jsxs(Dialog.Content, { className: "mx-auto min-h-full w-full overflow-y-auto bg-bg-primary pt-xl lg:mt-[132px] lg:min-h-auto lg:max-w-[1136px] lg:bg-unset lg:px-2 lg:pt-0", children: [_jsx(Dialog.Context, { children: (api) => (_jsxs("div", { className: "flex items-center justify-between px-4 lg:hidden", children: [_jsx(Image, { src: props.logo, alt: "", width: 200, height: 40, className: "h-8 w-auto" }), _jsx(IconButton, { size: "sm", colorScheme: "gray", onClick: () => api.setOpen(false), children: _jsx(XIcon, { className: "size-6 text-text-quinary" }) })] })) }), _jsx("div", { className: "flex justify-end", children: _jsx(Dialog.Context, { children: (api) => (_jsx("button", { type: "button", onClick: () => api.setOpen(false), className: "hidden size-9 items-center justify-center rounded-md bg-white/20 lg:flex", children: _jsx(XIcon, { className: "size-5 text-white" }) })) }) }), _jsx("div", { className: "mt-2xl px-4 lg:mt-xl lg:px-0", children: _jsxs("div", { className: "relative", children: [_jsx(SearchLgIcon, { className: "-translate-y-1/2 pointer-events-none absolute top-1/2 left-3.5 size-5 text-text-quinary" }), _jsx(DebouncedInput, { ref: inputRef, value: search, placeholder: props.placeholder ?? 'Search', onChange: setSearch }), _jsx(Presence, { present: search.length > 0, asChild: true, lazyMount: true, children: _jsx("button", { type: "button", className: "-translate-y-1/2 absolute top-1/2 right-3.5 cursor-pointer font-semibold text-text-secondary-700", onClick: () => {
144
161
  setSearch('');
145
162
  inputRef.current?.focus();
146
- }, children: "Clear" }) })] }) }), _jsx("div", { className: "flex max-h-[85dvh] min-h-0 flex-1 flex-col", children: _jsx("div", { className: "mt-2xl p-xl pb-3xl lg:mt-2 lg:max-h-[41rem] lg:overflow-y-auto lg:rounded-xl lg:border lg:border-border-primary lg:bg-bg-primary", children: search.length <= 0 ? (_jsx(Alert, { message: "Search for your favorite game, provider, or game type." })) : search.length === 1 ? (_jsx(Alert, { message: "Search requires at least 2 characters." })) : (_jsxs(_Fragment, { children: [empty && _jsx(Alert, { message: "No results found" }), !empty && (_jsxs(_Fragment, { children: [gameTypesFiltered.length > 0 &&
147
- featureFlag.enabled && (_jsxs(_Fragment, { children: [_jsx("h2", { className: "font-semibold text-lg", children: "Type" }), _jsx("div", { className: "mt-3.5 mb-3xl grid grid-cols-3 gap-1.5 lg:grid-cols-9 lg:gap-3.5", children: gameTypesFiltered.map((type) => (_jsx(Link, { href: viewGameTypeUrl(type), "aria-label": `View ${type.name} games`, className: twMerge('flex h-14 w-full items-center rounded-md bg-bg-primary-alt', classNames.gameTypeThumbnailRoot), onClick: () => {
163
+ }, children: "Clear" }) })] }) }), _jsx("div", { className: "flex max-h-[85dvh] min-h-0 flex-1 flex-col", children: _jsx("div", { className: "mt-2xl p-xl pb-3xl lg:mt-2 lg:max-h-[41rem] lg:overflow-y-auto lg:rounded-xl lg:border lg:border-border-primary lg:bg-bg-primary", children: search.length <= 0 ? (_jsx(Alert, { message: "Search for your favorite game, provider, or game type." })) : search.length === 1 ? (_jsx(Alert, { message: "Search requires at least 2 characters." })) : (_jsxs(_Fragment, { children: [empty && _jsx(Alert, { message: "No results found" }), !empty && (_jsxs(_Fragment, { children: [gameTypesFiltered.length > 0 && (_jsxs(_Fragment, { children: [_jsx("h2", { className: "font-semibold text-lg", children: "Type" }), _jsx("div", { className: "mt-3.5 mb-3xl grid grid-cols-3 gap-1.5 lg:grid-cols-9 lg:gap-3.5", children: gameTypesFiltered.map((type) => (_jsx(Link, { href: viewGameTypeUrl(type), "aria-label": `View ${type.name} games`, className: twMerge('flex h-14 w-full items-center rounded-md bg-bg-primary-alt', classNames.gameTypeThumbnailRoot), onClick: () => {
148
164
  globalStore.search.setOpen(false);
149
165
  }, children: _jsx(Image, { src: (props.gameTypeImages?.[type.id] ??
150
- defaultGameTypeImages[type.id]), alt: "", width: 100, height: 50, className: twMerge('mx-auto h-auto w-full', classNames.gameTypeThumbnailName) }) }, type.id))) })] })), gameProviders.length > 0 && (_jsxs(_Fragment, { children: [_jsx("h2", { className: "font-semibold text-lg", children: "Providers" }), _jsx("div", { className: "mt-3.5 mb-3xl grid grid-cols-3 gap-1.5 lg:grid-cols-9 lg:gap-3.5", children: gameProviders.map((provider) => (_jsx(Link, { href: viewGamesUrl(provider), "aria-label": `View ${provider.name} games`, className: twMerge('flex h-14 w-full items-center rounded-md bg-brand-800', classNames.providerThumbnailRoot), onClick: () => {
166
+ defaultGameTypeImages[type.id]), alt: "", width: 100, height: 50, className: twMerge('mx-auto h-auto w-full', classNames.gameTypeThumbnailName) }) }, type.id))) })] })), displayGameProviders.length > 0 && (_jsxs(_Fragment, { children: [_jsx("h2", { className: "font-semibold text-lg", children: "Providers" }), _jsx("div", { className: "mt-3.5 mb-3xl grid grid-cols-3 gap-1.5 lg:grid-cols-9 lg:gap-3.5", children: displayGameProviders.map((provider) => (_jsx(Link, { href: viewGamesUrl(provider), "aria-label": `View ${provider.name} games`, className: twMerge('flex h-14 w-full items-center rounded-md bg-brand-800', classNames.providerThumbnailRoot), onClick: () => {
151
167
  globalStore.search.setOpen(false);
152
168
  }, children: _jsx(Image, { src: props.gameProviderImages?.[provider.id] ??
153
169
  provider.logo, alt: "", width: 100, height: 50, className: twMerge('mx-auto h-auto w-full', classNames.providerThumbnailImage) }) }, provider.id))) })] })), games.length > 0 && (_jsxs(_Fragment, { children: [_jsx("h2", { className: "font-semibold text-lg", children: "Games" }), _jsx("div", { className: twMerge('mt-3.5 grid grid-cols-3 gap-1.5 lg:grid-cols-9 lg:gap-3.5', classNames.gameSearchResult), children: games.map((game) => (_jsxs(GameLaunchTrigger, { bypassKycCheck: isBypass, game: game, className: twMerge('block w-full shadow-sm', classNames.gameThumbnailRoot), onClick: () => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@opexa/portal-components",
3
- "version": "0.1.39",
3
+ "version": "0.1.41",
4
4
  "exports": {
5
5
  "./ui/*": {
6
6
  "types": "./dist/ui/*/index.d.ts",