@hhgtech/hhg-components 1.28.67 → 1.28.69
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/build/BMI_BOYS.percentile.monthly-48c9471d.js +688 -0
- package/build/BMI_BOYS.percentile.weekly-4965852e.js +182 -0
- package/build/BMI_BOYS.percentile.yearly-0f7cc8f4.js +83 -0
- package/build/BMI_BOYS.zscore.monthly-5bb8a433.js +440 -0
- package/build/BMI_BOYS.zscore.weekly-3d56f80f.js +118 -0
- package/build/BMI_BOYS.zscore.yearly-57081f24.js +55 -0
- package/build/BMI_GIRLS.percentile.monthly-95859cd9.js +688 -0
- package/build/BMI_GIRLS.percentile.weekly-009cf4df.js +182 -0
- package/build/BMI_GIRLS.percentile.yearly-4436947b.js +83 -0
- package/build/BMI_GIRLS.zscore.monthly-689b4eee.js +440 -0
- package/build/BMI_GIRLS.zscore.weekly-dff693df.js +118 -0
- package/build/BMI_GIRLS.zscore.yearly-05ef5f4f.js +55 -0
- package/build/ChevronDown-275f1ab5.js +29 -0
- package/build/HEAD CIRCUM_BOYS.percentile.monthly-55c580a7.js +688 -0
- package/build/HEAD CIRCUM_BOYS.percentile.weekly-e30f4a42.js +182 -0
- package/build/HEAD CIRCUM_BOYS.percentile.yearly-2378a5f0.js +83 -0
- package/build/HEAD CIRCUM_BOYS.zscore.monthly-102d5559.js +440 -0
- package/build/HEAD CIRCUM_BOYS.zscore.weekly-7b0f1ba8.js +118 -0
- package/build/HEAD CIRCUM_BOYS.zscore.yearly-e9237d31.js +55 -0
- package/build/HEAD CIRCUM_GIRLS.percentile.monthly-1ddda8b3.js +688 -0
- package/build/HEAD CIRCUM_GIRLS.percentile.weekly-843147ea.js +182 -0
- package/build/HEAD CIRCUM_GIRLS.percentile.yearly-9b51c237.js +83 -0
- package/build/HEAD CIRCUM_GIRLS.zscore.monthly-3f1b233c.js +440 -0
- package/build/HEAD CIRCUM_GIRLS.zscore.weekly-9e14d3fe.js +118 -0
- package/build/HEAD CIRCUM_GIRLS.zscore.yearly-d924f5ae.js +55 -0
- package/build/HEIGHT_BOYS.percentile.monthly-15538920.js +688 -0
- package/build/HEIGHT_BOYS.percentile.weekly-10bd0277.js +182 -0
- package/build/HEIGHT_BOYS.percentile.yearly-8e678d38.js +237 -0
- package/build/HEIGHT_BOYS.zscore.monthly-2c110da9.js +440 -0
- package/build/HEIGHT_BOYS.zscore.weekly-288b7733.js +118 -0
- package/build/HEIGHT_BOYS.zscore.yearly-42f6f9f7.js +153 -0
- package/build/HEIGHT_GIRLS.percentile.monthly-04abe7d2.js +688 -0
- package/build/HEIGHT_GIRLS.percentile.weekly-9653b16c.js +182 -0
- package/build/HEIGHT_GIRLS.percentile.yearly-9efacd67.js +237 -0
- package/build/HEIGHT_GIRLS.zscore.monthly-c64a97b2.js +440 -0
- package/build/HEIGHT_GIRLS.zscore.weekly-3302dd83.js +118 -0
- package/build/HEIGHT_GIRLS.zscore.yearly-ebe5114f.js +153 -0
- package/build/Subot-5fc40fb5.js +217 -0
- package/build/Visible-5c5d57cf.js +29 -0
- package/build/WEIGHT_BOYS.percentile.monthly-5e11e7a0.js +688 -0
- package/build/WEIGHT_BOYS.percentile.weekly-68ae2578.js +182 -0
- package/build/WEIGHT_BOYS.percentile.yearly-030c06a4.js +138 -0
- package/build/WEIGHT_BOYS.zscore.monthly-d22c7b57.js +440 -0
- package/build/WEIGHT_BOYS.zscore.weekly-d8d901e6.js +118 -0
- package/build/WEIGHT_BOYS.zscore.yearly-c311a084.js +90 -0
- package/build/WEIGHT_GIRLS.percentile.monthly-5c44f8eb.js +688 -0
- package/build/WEIGHT_GIRLS.percentile.weekly-faa98671.js +182 -0
- package/build/WEIGHT_GIRLS.percentile.yearly-560b862e.js +138 -0
- package/build/WEIGHT_GIRLS.zscore.monthly-5365ba1a.js +440 -0
- package/build/WEIGHT_GIRLS.zscore.weekly-0d9dc521.js +118 -0
- package/build/WEIGHT_GIRLS.zscore.yearly-5a3c4e43.js +90 -0
- package/build/adapters.js +36 -1
- package/build/{esm/animation-0340efb3.js → animation-eb4e500b.js} +32 -10
- package/build/babyGrowth.js +913 -47
- package/build/cache.js +13 -1
- package/build/care.js +38 -1
- package/build/components/navigationV2/hooks/useNavConfig.d.ts +1 -3
- package/build/components.js +186 -1
- package/build/constants-8b8bc19f.js +255 -0
- package/build/constants-ae18ce18.js +935 -0
- package/build/constants.js +43 -1
- package/build/cookieHelper-5c9f4bb8.js +43 -0
- package/build/core-2aa8d86c.js +51 -0
- package/build/dataTransform-089f414c.js +66 -0
- package/build/ecom.js +745 -1
- package/build/esm/BMI_BOYS.percentile.monthly-de5dce68.js +686 -0
- package/build/esm/BMI_BOYS.percentile.weekly-9d3990b6.js +180 -0
- package/build/esm/BMI_BOYS.percentile.yearly-98b9114a.js +81 -0
- package/build/esm/BMI_BOYS.zscore.monthly-394646f0.js +438 -0
- package/build/esm/BMI_BOYS.zscore.weekly-c669ea51.js +116 -0
- package/build/esm/BMI_BOYS.zscore.yearly-771ef6b6.js +53 -0
- package/build/esm/BMI_GIRLS.percentile.monthly-1ff3d499.js +686 -0
- package/build/esm/BMI_GIRLS.percentile.weekly-211d2f27.js +180 -0
- package/build/esm/BMI_GIRLS.percentile.yearly-206fdcff.js +81 -0
- package/build/esm/BMI_GIRLS.zscore.monthly-b1137e36.js +438 -0
- package/build/esm/BMI_GIRLS.zscore.weekly-63ed3cd6.js +116 -0
- package/build/esm/BMI_GIRLS.zscore.yearly-221d187c.js +53 -0
- package/build/esm/ChevronDown-9a8ece61.js +7 -0
- package/build/esm/HEAD CIRCUM_BOYS.percentile.monthly-4c37847c.js +686 -0
- package/build/esm/HEAD CIRCUM_BOYS.percentile.weekly-8f6ea38a.js +180 -0
- package/build/esm/HEAD CIRCUM_BOYS.percentile.yearly-6c12a99a.js +81 -0
- package/build/esm/HEAD CIRCUM_BOYS.zscore.monthly-c531b497.js +438 -0
- package/build/esm/HEAD CIRCUM_BOYS.zscore.weekly-6cafba00.js +116 -0
- package/build/esm/HEAD CIRCUM_BOYS.zscore.yearly-fe8114a0.js +53 -0
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.monthly-25ce0d36.js +686 -0
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.weekly-5d3f2862.js +180 -0
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.yearly-2b709ca5.js +81 -0
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.monthly-e8617bae.js +438 -0
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.weekly-f3252d67.js +116 -0
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.yearly-5b62d41f.js +53 -0
- package/build/esm/HEIGHT_BOYS.percentile.monthly-63d2cf96.js +686 -0
- package/build/esm/HEIGHT_BOYS.percentile.weekly-8ea5102d.js +180 -0
- package/build/esm/HEIGHT_BOYS.percentile.yearly-8107b77b.js +235 -0
- package/build/esm/HEIGHT_BOYS.zscore.monthly-641cdfa3.js +438 -0
- package/build/esm/HEIGHT_BOYS.zscore.weekly-86da0362.js +116 -0
- package/build/esm/HEIGHT_BOYS.zscore.yearly-060f6e79.js +151 -0
- package/build/esm/HEIGHT_GIRLS.percentile.monthly-fb987d37.js +686 -0
- package/build/esm/HEIGHT_GIRLS.percentile.weekly-82655dc0.js +180 -0
- package/build/esm/HEIGHT_GIRLS.percentile.yearly-a63b8456.js +235 -0
- package/build/esm/HEIGHT_GIRLS.zscore.monthly-77d676a3.js +438 -0
- package/build/esm/HEIGHT_GIRLS.zscore.weekly-c0387a4e.js +116 -0
- package/build/esm/HEIGHT_GIRLS.zscore.yearly-41203c20.js +151 -0
- package/build/esm/Subot-3289bd8e.js +212 -0
- package/build/esm/Visible-a3d436dd.js +7 -0
- package/build/esm/WEIGHT_BOYS.percentile.monthly-50802d8b.js +686 -0
- package/build/esm/WEIGHT_BOYS.percentile.weekly-4d72ddd6.js +180 -0
- package/build/esm/WEIGHT_BOYS.percentile.yearly-20a29844.js +136 -0
- package/build/esm/WEIGHT_BOYS.zscore.monthly-729e6614.js +438 -0
- package/build/esm/WEIGHT_BOYS.zscore.weekly-90352f48.js +116 -0
- package/build/esm/WEIGHT_BOYS.zscore.yearly-fe1871cc.js +88 -0
- package/build/esm/WEIGHT_GIRLS.percentile.monthly-e6afb2e0.js +686 -0
- package/build/esm/WEIGHT_GIRLS.percentile.weekly-b66d3016.js +180 -0
- package/build/esm/WEIGHT_GIRLS.percentile.yearly-a55622c5.js +136 -0
- package/build/esm/WEIGHT_GIRLS.zscore.monthly-2cdcbe75.js +438 -0
- package/build/esm/WEIGHT_GIRLS.zscore.weekly-d5be31d5.js +116 -0
- package/build/esm/WEIGHT_GIRLS.zscore.yearly-99e8d3a7.js +88 -0
- package/build/esm/adapters.js +26 -1
- package/build/{animation-d5d9ef32.js → esm/animation-3d5edc39.js} +22 -10
- package/build/esm/babyGrowth.js +883 -47
- package/build/esm/cache.js +3 -1
- package/build/esm/care.js +26 -1
- package/build/esm/components/navigationV2/hooks/useNavConfig.d.ts +1 -3
- package/build/esm/components.js +88 -1
- package/build/esm/constants-2a6d2434.js +932 -0
- package/build/esm/constants-b77ffe3d.js +238 -0
- package/build/esm/constants.js +4 -1
- package/build/esm/cookieHelper-d314282c.js +39 -0
- package/build/esm/core-8c73d133.js +47 -0
- package/build/esm/dataTransform-8ecfc046.js +56 -0
- package/build/esm/ecom.js +737 -1
- package/build/esm/footer.js +31 -1
- package/build/esm/gAssets.js +5 -1
- package/build/esm/getDynamicHealthTool-f4497aa5.js +44 -0
- package/build/esm/getSocialList-a5b8462e.js +66 -0
- package/build/esm/hooks.js +21 -1
- package/build/esm/i18n-values/en-PH.js +600 -1
- package/build/esm/i18n-values/hi-IN.js +600 -1
- package/build/esm/i18n-values/id-ID.js +600 -1
- package/build/esm/i18n-values/km-KH.js +600 -1
- package/build/esm/i18n-values/ms-MY.js +602 -1
- package/build/esm/i18n-values/my-MM.js +600 -1
- package/build/esm/i18n-values/th-TH.js +600 -1
- package/build/esm/i18n-values/tl-PH.js +600 -1
- package/build/esm/i18n-values/vi-VN.js +607 -1
- package/build/esm/i18n-values/vi-VN_MB.js +607 -1
- package/build/esm/i18n-values/zh-TW.js +600 -1
- package/build/esm/i18n.js +55 -1
- package/build/esm/i18nV2.js +18 -1
- package/build/esm/index-12fa4985.js +8 -0
- package/build/esm/index-1e59f99a.js +152 -0
- package/build/esm/index-32e53dac.js +1936 -0
- package/build/esm/index-3474401a.js +149 -0
- package/build/esm/index-34899aa3.js +17 -0
- package/build/esm/index-350e8f5b.js +124 -0
- package/build/esm/index-41bf860a.js +151 -0
- package/build/esm/index-4aa8e518.js +116 -0
- package/build/esm/index-4fe2b03f.js +32 -0
- package/build/esm/index-6ea6484e.js +29 -0
- package/build/esm/index-717401ee.js +184 -0
- package/build/esm/index-7af5242a.js +24 -0
- package/build/esm/index-7b8c85cd.js +8302 -0
- package/build/esm/index-81f295b7.js +23 -0
- package/build/esm/index-8858383e.js +52 -0
- package/build/esm/index-8f52dcf3.js +33 -0
- package/build/esm/index-9ea7e838.js +33 -0
- package/build/esm/index-aabac2aa.js +3241 -0
- package/build/esm/index-b9b2c417.js +837 -0
- package/build/esm/index-c2da5293.js +12 -0
- package/build/esm/index-c56d60db.js +370 -0
- package/build/esm/index-c5d7f692.js +24 -0
- package/build/esm/index-cc93e010.js +53 -0
- package/build/esm/index-d7f046db.js +5 -0
- package/build/esm/index-d8177667.js +14 -0
- package/build/esm/index-da139dda.js +615 -0
- package/build/esm/index-e612be9c.js +905 -0
- package/build/esm/index-f3d0592b.js +71 -0
- package/build/esm/index.js +190 -1
- package/build/{index.styled-0a1fb891.js → esm/index.styled-9c9db9cc.js} +17 -5
- package/build/esm/index.styles-5add27c5.js +1303 -0
- package/build/esm/isProduction-0ea904dd.js +27 -0
- package/build/esm/lead.js +2140 -1
- package/build/esm/localizeNumberFormat-2ac3773e.js +23 -0
- package/build/esm/mantine.js +113 -1
- package/build/esm/misc.js +22 -1
- package/build/esm/navigation.js +51 -1
- package/build/esm/normalizeLink-d1c9617e.js +12 -0
- package/build/esm/number-0c126a39.js +38 -0
- package/build/esm/onboardingV2.js +860 -34
- package/build/esm/paths-a8204db4.js +14 -0
- package/build/esm/pwg.js +208 -7
- package/build/esm/routing-2474f896.js +40 -0
- package/build/esm/subot.js +4553 -134
- package/build/esm/theme-e74db08c.js +186 -0
- package/build/esm/together.js +52 -1
- package/build/esm/translationsContext-ad3e25de.js +5 -0
- package/build/esm/tslib.es6-1b1533a9.js +38 -0
- package/build/esm/types-06f00b3d.js +8015 -0
- package/build/esm/types-15e34418.js +3432 -0
- package/build/esm/types-ba190c26.js +21 -0
- package/build/esm/types.js +1 -1
- package/build/esm/unifyEnv.js +42 -1
- package/build/esm/useCategory-2c87152d.js +292 -0
- package/build/esm/useHealthToolCache-29d22ddb.js +17 -0
- package/build/esm/useIsInit-8a2fc8e5.js +11 -0
- package/build/esm/useOutsideClick-c8a7ff20.js +45 -0
- package/build/esm/usePlacesAutocomplete-63e04e8e.js +80 -0
- package/build/esm/useScrollbarSize-51ce1374.js +57 -0
- package/build/esm/useTranslations-4f1db486.js +26 -0
- package/build/esm/useUniqueId-3638402f.js +41 -0
- package/build/esm/utils-2c484c05.js +132 -0
- package/build/esm/utils-3a2a47d9.js +22 -0
- package/build/esm/utils-6d7b88da.js +367 -0
- package/build/esm/utils-70718e9c.js +1124 -0
- package/build/esm/vaccination.js +868 -40
- package/build/footer.js +39 -1
- package/build/gAssets.js +14 -1
- package/build/getDynamicHealthTool-114a1e27.js +48 -0
- package/build/getSocialList-4713441d.js +72 -0
- package/build/hooks.js +44 -1
- package/build/i18n-values/en-PH.js +611 -1
- package/build/i18n-values/hi-IN.js +611 -1
- package/build/i18n-values/id-ID.js +611 -1
- package/build/i18n-values/km-KH.js +611 -1
- package/build/i18n-values/ms-MY.js +613 -1
- package/build/i18n-values/my-MM.js +611 -1
- package/build/i18n-values/th-TH.js +611 -1
- package/build/i18n-values/tl-PH.js +611 -1
- package/build/i18n-values/vi-VN.js +618 -1
- package/build/i18n-values/vi-VN_MB.js +618 -1
- package/build/i18n-values/zh-TW.js +611 -1
- package/build/i18n.js +64 -1
- package/build/i18nV2.js +26 -1
- package/build/index-020e6908.js +39 -0
- package/build/index-0da9b2e8.js +59 -0
- package/build/index-11468c00.js +157 -0
- package/build/index-117448a5.js +133 -0
- package/build/index-12c07f71.js +18 -0
- package/build/index-1a105e87.js +123 -0
- package/build/index-1baaedb0.js +55 -0
- package/build/index-32d38318.js +7 -0
- package/build/index-38582ee0.js +8373 -0
- package/build/index-3e5fc2d6.js +1994 -0
- package/build/index-3eef6bed.js +853 -0
- package/build/index-4035e658.js +159 -0
- package/build/index-488d71ae.js +30 -0
- package/build/index-5553f9e1.js +930 -0
- package/build/index-5fa68e45.js +380 -0
- package/build/index-7b467209.js +39 -0
- package/build/index-81cb1142.js +77 -0
- package/build/index-84ab5b89.js +38 -0
- package/build/index-8a95d709.js +30 -0
- package/build/index-9da9f0c3.js +35 -0
- package/build/index-af91c83e.js +20 -0
- package/build/index-b6aea85e.js +191 -0
- package/build/index-bc4f4c33.js +156 -0
- package/build/index-c604d6bb.js +624 -0
- package/build/index-d330735e.js +30 -0
- package/build/index-d8a7efaf.js +14 -0
- package/build/index-e2e81fa2.js +23 -0
- package/build/index-e3d896b3.js +3261 -0
- package/build/index.js +436 -1
- package/build/{esm/index.styled-14b65c9e.js → index.styled-5628b3e7.js} +25 -5
- package/build/index.styles-b822bf42.js +1342 -0
- package/build/isProduction-5ce3a388.js +29 -0
- package/build/lead.js +2168 -1
- package/build/localizeNumberFormat-f5f50987.js +31 -0
- package/build/mantine.js +154 -1
- package/build/misc.js +70 -1
- package/build/navigation.js +61 -1
- package/build/normalizeLink-6f7b85d8.js +15 -0
- package/build/number-79fe92e1.js +40 -0
- package/build/onboardingV2.js +892 -34
- package/build/paths-a5643d9e.js +16 -0
- package/build/pwg.js +217 -7
- package/build/routing-191a9a00.js +46 -0
- package/build/subot.js +4592 -134
- package/build/theme-fa910869.js +189 -0
- package/build/together.js +112 -1
- package/build/translationsContext-950334bf.js +7 -0
- package/build/tslib.es6-65e312a5.js +41 -0
- package/build/types-0f117a9f.js +8084 -0
- package/build/types-1fedb3d1.js +3446 -0
- package/build/types-52a4e888.js +24 -0
- package/build/types.js +56 -1
- package/build/unifyEnv.js +46 -1
- package/build/useCategory-cfc702f5.js +299 -0
- package/build/useHealthToolCache-43a7014d.js +19 -0
- package/build/useIsInit-89535012.js +13 -0
- package/build/useOutsideClick-c6813964.js +49 -0
- package/build/usePlacesAutocomplete-297de092.js +84 -0
- package/build/useScrollbarSize-0fa31aa7.js +64 -0
- package/build/useTranslations-e1853417.js +32 -0
- package/build/useUniqueId-11369116.js +44 -0
- package/build/utils-52113753.js +384 -0
- package/build/utils-64bd0c42.js +143 -0
- package/build/utils-661411f6.js +1171 -0
- package/build/utils-e1513cbc.js +25 -0
- package/build/vaccination.js +891 -40
- package/package.json +4 -5
- package/build/BMI_BOYS.percentile.monthly-c56b0165.js +0 -1
- package/build/BMI_BOYS.percentile.weekly-64287e04.js +0 -1
- package/build/BMI_BOYS.percentile.yearly-8db65d54.js +0 -1
- package/build/BMI_BOYS.zscore.monthly-f12389cd.js +0 -1
- package/build/BMI_BOYS.zscore.weekly-fff37a57.js +0 -1
- package/build/BMI_BOYS.zscore.yearly-a19b57eb.js +0 -1
- package/build/BMI_GIRLS.percentile.monthly-a4b36d7d.js +0 -1
- package/build/BMI_GIRLS.percentile.weekly-b6089202.js +0 -1
- package/build/BMI_GIRLS.percentile.yearly-0d340818.js +0 -1
- package/build/BMI_GIRLS.zscore.monthly-fd5b57c0.js +0 -1
- package/build/BMI_GIRLS.zscore.weekly-d4577f50.js +0 -1
- package/build/BMI_GIRLS.zscore.yearly-e40b8a7d.js +0 -1
- package/build/ChevronDown-602ce39e.js +0 -1
- package/build/HEAD CIRCUM_BOYS.percentile.monthly-2e4c5776.js +0 -1
- package/build/HEAD CIRCUM_BOYS.percentile.weekly-fc5728a5.js +0 -1
- package/build/HEAD CIRCUM_BOYS.percentile.yearly-6bfab277.js +0 -1
- package/build/HEAD CIRCUM_BOYS.zscore.monthly-6af7ce44.js +0 -1
- package/build/HEAD CIRCUM_BOYS.zscore.weekly-9adb819b.js +0 -1
- package/build/HEAD CIRCUM_BOYS.zscore.yearly-9a6cdbcf.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.percentile.monthly-e7bfe9c6.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.percentile.weekly-9f17e019.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.percentile.yearly-8a59f541.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.zscore.monthly-b7ddb16c.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.zscore.weekly-72701c55.js +0 -1
- package/build/HEAD CIRCUM_GIRLS.zscore.yearly-dd94bded.js +0 -1
- package/build/HEIGHT_BOYS.percentile.monthly-b890068c.js +0 -1
- package/build/HEIGHT_BOYS.percentile.weekly-a1aa5130.js +0 -1
- package/build/HEIGHT_BOYS.percentile.yearly-5727d920.js +0 -1
- package/build/HEIGHT_BOYS.zscore.monthly-13b70aa6.js +0 -1
- package/build/HEIGHT_BOYS.zscore.weekly-3e1d7f23.js +0 -1
- package/build/HEIGHT_BOYS.zscore.yearly-a956102d.js +0 -1
- package/build/HEIGHT_GIRLS.percentile.monthly-da5ec01b.js +0 -1
- package/build/HEIGHT_GIRLS.percentile.weekly-e6205d32.js +0 -1
- package/build/HEIGHT_GIRLS.percentile.yearly-caefa502.js +0 -1
- package/build/HEIGHT_GIRLS.zscore.monthly-102ba473.js +0 -1
- package/build/HEIGHT_GIRLS.zscore.weekly-db4f710b.js +0 -1
- package/build/HEIGHT_GIRLS.zscore.yearly-36465920.js +0 -1
- package/build/Subot-4751194d.js +0 -1
- package/build/Visible-9497c463.js +0 -1
- package/build/WEIGHT_BOYS.percentile.monthly-554d0361.js +0 -1
- package/build/WEIGHT_BOYS.percentile.weekly-8e5334b8.js +0 -1
- package/build/WEIGHT_BOYS.percentile.yearly-536e1ccb.js +0 -1
- package/build/WEIGHT_BOYS.zscore.monthly-01eccee1.js +0 -1
- package/build/WEIGHT_BOYS.zscore.weekly-ee8f2c6b.js +0 -1
- package/build/WEIGHT_BOYS.zscore.yearly-0aea2749.js +0 -1
- package/build/WEIGHT_GIRLS.percentile.monthly-7abf9d06.js +0 -1
- package/build/WEIGHT_GIRLS.percentile.weekly-f9b6e963.js +0 -1
- package/build/WEIGHT_GIRLS.percentile.yearly-254865a5.js +0 -1
- package/build/WEIGHT_GIRLS.zscore.monthly-909f7417.js +0 -1
- package/build/WEIGHT_GIRLS.zscore.weekly-e62cd084.js +0 -1
- package/build/WEIGHT_GIRLS.zscore.yearly-8d6e5405.js +0 -1
- package/build/constants-00e06f68.js +0 -108
- package/build/constants-51251306.js +0 -1
- package/build/cookieHelper-7d519a72.js +0 -1
- package/build/core-ba3af3e2.js +0 -1
- package/build/dataTransform-1805eae3.js +0 -1
- package/build/esm/BMI_BOYS.percentile.monthly-6272f835.js +0 -1
- package/build/esm/BMI_BOYS.percentile.weekly-80d18f47.js +0 -1
- package/build/esm/BMI_BOYS.percentile.yearly-a7e5b5f6.js +0 -1
- package/build/esm/BMI_BOYS.zscore.monthly-d3658f97.js +0 -1
- package/build/esm/BMI_BOYS.zscore.weekly-6e6708dc.js +0 -1
- package/build/esm/BMI_BOYS.zscore.yearly-b8400c9d.js +0 -1
- package/build/esm/BMI_GIRLS.percentile.monthly-98586b46.js +0 -1
- package/build/esm/BMI_GIRLS.percentile.weekly-7c1511b0.js +0 -1
- package/build/esm/BMI_GIRLS.percentile.yearly-ea667f90.js +0 -1
- package/build/esm/BMI_GIRLS.zscore.monthly-3a4fd1a6.js +0 -1
- package/build/esm/BMI_GIRLS.zscore.weekly-cc1de097.js +0 -1
- package/build/esm/BMI_GIRLS.zscore.yearly-6dd1a364.js +0 -1
- package/build/esm/ChevronDown-4e59cac6.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.percentile.monthly-bd0965ae.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.percentile.weekly-db1053f7.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.percentile.yearly-cd38b622.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.zscore.monthly-d7f88a95.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.zscore.weekly-76f7db79.js +0 -1
- package/build/esm/HEAD CIRCUM_BOYS.zscore.yearly-3ce70f8e.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.monthly-b2e678ae.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.weekly-8e2664bb.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.percentile.yearly-f5c075a9.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.monthly-6f87849e.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.weekly-48da0aaa.js +0 -1
- package/build/esm/HEAD CIRCUM_GIRLS.zscore.yearly-4eea437b.js +0 -1
- package/build/esm/HEIGHT_BOYS.percentile.monthly-d1a8cc8e.js +0 -1
- package/build/esm/HEIGHT_BOYS.percentile.weekly-2b6cfe6c.js +0 -1
- package/build/esm/HEIGHT_BOYS.percentile.yearly-9e78afc3.js +0 -1
- package/build/esm/HEIGHT_BOYS.zscore.monthly-5292d78a.js +0 -1
- package/build/esm/HEIGHT_BOYS.zscore.weekly-fbdee645.js +0 -1
- package/build/esm/HEIGHT_BOYS.zscore.yearly-c11a8f1b.js +0 -1
- package/build/esm/HEIGHT_GIRLS.percentile.monthly-8e11e2dc.js +0 -1
- package/build/esm/HEIGHT_GIRLS.percentile.weekly-dc3965cb.js +0 -1
- package/build/esm/HEIGHT_GIRLS.percentile.yearly-490f7b4e.js +0 -1
- package/build/esm/HEIGHT_GIRLS.zscore.monthly-e3531c32.js +0 -1
- package/build/esm/HEIGHT_GIRLS.zscore.weekly-36a16a66.js +0 -1
- package/build/esm/HEIGHT_GIRLS.zscore.yearly-61736bba.js +0 -1
- package/build/esm/Subot-4642c5bf.js +0 -1
- package/build/esm/Visible-ff7d225c.js +0 -1
- package/build/esm/WEIGHT_BOYS.percentile.monthly-0cfe7ecd.js +0 -1
- package/build/esm/WEIGHT_BOYS.percentile.weekly-89802113.js +0 -1
- package/build/esm/WEIGHT_BOYS.percentile.yearly-0eb40972.js +0 -1
- package/build/esm/WEIGHT_BOYS.zscore.monthly-7f8c5a15.js +0 -1
- package/build/esm/WEIGHT_BOYS.zscore.weekly-3dcfa8ce.js +0 -1
- package/build/esm/WEIGHT_BOYS.zscore.yearly-98ce1ea0.js +0 -1
- package/build/esm/WEIGHT_GIRLS.percentile.monthly-df98e335.js +0 -1
- package/build/esm/WEIGHT_GIRLS.percentile.weekly-63fff42a.js +0 -1
- package/build/esm/WEIGHT_GIRLS.percentile.yearly-8db8cdd0.js +0 -1
- package/build/esm/WEIGHT_GIRLS.zscore.monthly-15c83c6d.js +0 -1
- package/build/esm/WEIGHT_GIRLS.zscore.weekly-747a55ec.js +0 -1
- package/build/esm/WEIGHT_GIRLS.zscore.yearly-197dc52d.js +0 -1
- package/build/esm/constants-6ecfa77c.js +0 -1
- package/build/esm/constants-f7c80032.js +0 -108
- package/build/esm/cookieHelper-4f089e3c.js +0 -1
- package/build/esm/core-80112758.js +0 -1
- package/build/esm/dataTransform-0fa341bb.js +0 -1
- package/build/esm/getDynamicHealthTool-a4c9d6dd.js +0 -1
- package/build/esm/getSocialList-4e48deba.js +0 -1
- package/build/esm/index-13dc1f44.js +0 -1
- package/build/esm/index-13e62563.js +0 -137
- package/build/esm/index-1e7ad007.js +0 -1
- package/build/esm/index-24557f2b.js +0 -1
- package/build/esm/index-252cb964.js +0 -1
- package/build/esm/index-2e99f941.js +0 -1
- package/build/esm/index-3452fed2.js +0 -1
- package/build/esm/index-3aff939b.js +0 -1
- package/build/esm/index-459e0362.js +0 -1
- package/build/esm/index-45dcd965.js +0 -1
- package/build/esm/index-486b71cd.js +0 -1
- package/build/esm/index-5408f5a4.js +0 -113
- package/build/esm/index-5e1af23a.js +0 -1
- package/build/esm/index-79ef3a30.js +0 -1
- package/build/esm/index-7c77273a.js +0 -1
- package/build/esm/index-823fd7c0.js +0 -117
- package/build/esm/index-8c77d7e0.js +0 -1
- package/build/esm/index-93e5b4f3.js +0 -1
- package/build/esm/index-9c7b9011.js +0 -2748
- package/build/esm/index-9e5956c2.js +0 -1
- package/build/esm/index-a83aad1c.js +0 -375
- package/build/esm/index-b7cc3ca2.js +0 -1
- package/build/esm/index-bf11f9e9.js +0 -50
- package/build/esm/index-ce3d38fd.js +0 -1
- package/build/esm/index-d27a0e25.js +0 -1
- package/build/esm/index-e21276e3.js +0 -1
- package/build/esm/index-f9514788.js +0 -177
- package/build/esm/index-fd04ccb7.js +0 -1430
- package/build/esm/index.styles-94af560f.js +0 -817
- package/build/esm/isProduction-00695d80.js +0 -1
- package/build/esm/localizeNumberFormat-8355a44f.js +0 -1
- package/build/esm/normalizeLink-1c194268.js +0 -1
- package/build/esm/number-1347eb7b.js +0 -1
- package/build/esm/paths-749b4b53.js +0 -1
- package/build/esm/routing-2b284b30.js +0 -1
- package/build/esm/theme-3db3c9a8.js +0 -1
- package/build/esm/translationsContext-6d2efd65.js +0 -1
- package/build/esm/tslib.es6-266309d1.js +0 -1
- package/build/esm/types-6d397125.js +0 -3004
- package/build/esm/types-850814a7.js +0 -785
- package/build/esm/types-d3da37d2.js +0 -1
- package/build/esm/useCategory-f5f74749.js +0 -1
- package/build/esm/useHealthToolCache-f1488032.js +0 -1
- package/build/esm/useIsInit-9661c5f5.js +0 -1
- package/build/esm/useOutsideClick-0704b383.js +0 -1
- package/build/esm/usePlacesAutocomplete-0733ec49.js +0 -1
- package/build/esm/useScrollbarSize-90b179a5.js +0 -1
- package/build/esm/useTranslations-df1b3bb8.js +0 -1
- package/build/esm/useUniqueId-03fbaecd.js +0 -1
- package/build/esm/utils-3d2e3f0f.js +0 -141
- package/build/esm/utils-5b4e60da.js +0 -1
- package/build/esm/utils-970ce0c0.js +0 -8
- package/build/esm/utils-b87ec473.js +0 -1
- package/build/getDynamicHealthTool-31f44ca1.js +0 -1
- package/build/getSocialList-29c0a6e8.js +0 -1
- package/build/index-1714c81c.js +0 -2748
- package/build/index-238813a4.js +0 -375
- package/build/index-2438163d.js +0 -1430
- package/build/index-29d302f4.js +0 -137
- package/build/index-3184ae4e.js +0 -1
- package/build/index-34b6bd24.js +0 -1
- package/build/index-35192783.js +0 -1
- package/build/index-41d684a8.js +0 -50
- package/build/index-4a8c8ce6.js +0 -1
- package/build/index-58e0d49f.js +0 -1
- package/build/index-64d2f812.js +0 -1
- package/build/index-85c621a2.js +0 -113
- package/build/index-90f4bc02.js +0 -1
- package/build/index-9a845847.js +0 -117
- package/build/index-9ed509d1.js +0 -1
- package/build/index-aa495d24.js +0 -1
- package/build/index-ad5cf64d.js +0 -1
- package/build/index-b21a1d96.js +0 -1
- package/build/index-b320255d.js +0 -1
- package/build/index-b9af15da.js +0 -1
- package/build/index-bd4b31bf.js +0 -1
- package/build/index-bf81cb71.js +0 -1
- package/build/index-c3cbb8f3.js +0 -1
- package/build/index-d25afe2f.js +0 -1
- package/build/index-e7c1ff53.js +0 -177
- package/build/index-ed8656f9.js +0 -1
- package/build/index-f6217f73.js +0 -1
- package/build/index-f7088d57.js +0 -1
- package/build/index.styles-2ecb9c85.js +0 -817
- package/build/isProduction-28d96804.js +0 -1
- package/build/localizeNumberFormat-22b2d7aa.js +0 -1
- package/build/normalizeLink-594ccff1.js +0 -1
- package/build/number-cf06dcc0.js +0 -1
- package/build/paths-ed72ecb8.js +0 -1
- package/build/routing-f2edd0d0.js +0 -1
- package/build/theme-f2b8aad7.js +0 -1
- package/build/translationsContext-4c4c33c4.js +0 -1
- package/build/tslib.es6-ceb091fd.js +0 -1
- package/build/types-49f0543a.js +0 -785
- package/build/types-5b303b71.js +0 -1
- package/build/types-bfd12e24.js +0 -3004
- package/build/useCategory-94d60dab.js +0 -1
- package/build/useHealthToolCache-7307d240.js +0 -1
- package/build/useIsInit-c3cf1925.js +0 -1
- package/build/useOutsideClick-15fef824.js +0 -1
- package/build/usePlacesAutocomplete-6ab0181b.js +0 -1
- package/build/useScrollbarSize-ab332673.js +0 -1
- package/build/useTranslations-233c68bc.js +0 -1
- package/build/useUniqueId-46834e18.js +0 -1
- package/build/utils-13ea4f2f.js +0 -8
- package/build/utils-45e691a3.js +0 -1
- package/build/utils-bee8be92.js +0 -141
- package/build/utils-d5766c73.js +0 -1
|
@@ -0,0 +1,3446 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var tslib_es6 = require('./tslib.es6-65e312a5.js');
|
|
4
|
+
var React = require('react');
|
|
5
|
+
var useTranslations = require('./useTranslations-e1853417.js');
|
|
6
|
+
var debounce = require('lodash/debounce');
|
|
7
|
+
var constants = require('./constants-8b8bc19f.js');
|
|
8
|
+
var index$1 = require('./index-020e6908.js');
|
|
9
|
+
var styled = require('styled-components');
|
|
10
|
+
var index$2 = require('./index-bc4f4c33.js');
|
|
11
|
+
var theme = require('./theme-fa910869.js');
|
|
12
|
+
var shuffle = require('lodash/shuffle');
|
|
13
|
+
var useOutsideClick = require('./useOutsideClick-c6813964.js');
|
|
14
|
+
var utils = require('./utils-64bd0c42.js');
|
|
15
|
+
var Skeleton = require('react-loading-skeleton');
|
|
16
|
+
var paths = require('./paths-a5643d9e.js');
|
|
17
|
+
var core = require('@mantine/core');
|
|
18
|
+
var index = require('./index-5553f9e1.js');
|
|
19
|
+
var cookieHelper = require('./cookieHelper-5c9f4bb8.js');
|
|
20
|
+
var index$3 = require('./index-12c07f71.js');
|
|
21
|
+
var core$1 = require('@hhgtech/icons/core');
|
|
22
|
+
var ChevronDown = require('./ChevronDown-275f1ab5.js');
|
|
23
|
+
var formatString = require('string-format');
|
|
24
|
+
|
|
25
|
+
function _interopDefault (e) { return e && e.__esModule ? e : { 'default': e }; }
|
|
26
|
+
|
|
27
|
+
var React__default = /*#__PURE__*/_interopDefault(React);
|
|
28
|
+
var debounce__default = /*#__PURE__*/_interopDefault(debounce);
|
|
29
|
+
var styled__default = /*#__PURE__*/_interopDefault(styled);
|
|
30
|
+
var shuffle__default = /*#__PURE__*/_interopDefault(shuffle);
|
|
31
|
+
var Skeleton__default = /*#__PURE__*/_interopDefault(Skeleton);
|
|
32
|
+
var formatString__default = /*#__PURE__*/_interopDefault(formatString);
|
|
33
|
+
|
|
34
|
+
function useGeolocation() {
|
|
35
|
+
const [permission, setPermission] = React.useState(() => {
|
|
36
|
+
if (typeof window === 'undefined') {
|
|
37
|
+
return 'unset';
|
|
38
|
+
}
|
|
39
|
+
if (cookieHelper.getCookie(index.USER_GEOLOCATION_COORDINATES_COOKIE)) {
|
|
40
|
+
return 'granted';
|
|
41
|
+
}
|
|
42
|
+
const blocked = !location.protocol.includes('https') && location.hostname !== 'localhost';
|
|
43
|
+
if (!navigator.geolocation || blocked) {
|
|
44
|
+
return 'denied';
|
|
45
|
+
}
|
|
46
|
+
return 'unset';
|
|
47
|
+
});
|
|
48
|
+
const [coordinates, setCoordinates] = React.useState(() => {
|
|
49
|
+
if (typeof window === 'undefined') {
|
|
50
|
+
return null;
|
|
51
|
+
}
|
|
52
|
+
const cookie = cookieHelper.getCookie(index.USER_GEOLOCATION_COORDINATES_COOKIE);
|
|
53
|
+
if (cookie) {
|
|
54
|
+
try {
|
|
55
|
+
return JSON.parse(cookie);
|
|
56
|
+
}
|
|
57
|
+
catch (err) {
|
|
58
|
+
console.log(err);
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
return null;
|
|
62
|
+
});
|
|
63
|
+
const request = React.useCallback(function request() {
|
|
64
|
+
// setPermission()
|
|
65
|
+
if (navigator.geolocation) {
|
|
66
|
+
navigator.geolocation.getCurrentPosition((position) => {
|
|
67
|
+
const gps = {
|
|
68
|
+
lat: `${Math.round(position.coords.latitude * 10000000) / 10000000}`,
|
|
69
|
+
lng: `${Math.round(position.coords.longitude * 10000000) / 10000000}`,
|
|
70
|
+
};
|
|
71
|
+
cookieHelper.setCookie(index.USER_GEOLOCATION_COORDINATES_COOKIE, JSON.stringify(gps), {
|
|
72
|
+
minutes: 15,
|
|
73
|
+
});
|
|
74
|
+
setCoordinates(gps);
|
|
75
|
+
setPermission('granted');
|
|
76
|
+
}, () => {
|
|
77
|
+
cookieHelper.deleteCookie(index.USER_GEOLOCATION_COORDINATES_COOKIE);
|
|
78
|
+
setPermission('denied');
|
|
79
|
+
});
|
|
80
|
+
}
|
|
81
|
+
}, []);
|
|
82
|
+
return React.useMemo(() => ({
|
|
83
|
+
geoLocationPermission: permission,
|
|
84
|
+
geoLocationCoordinates: coordinates,
|
|
85
|
+
requestGeoLocation: request,
|
|
86
|
+
}), [permission, coordinates]);
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
const StyledSearchBarWrapper$1 = styled__default["default"].div ``;
|
|
90
|
+
const StyledSearchBarMobileWrapper = styled__default["default"].div `
|
|
91
|
+
--searchbar-z-index: 305;
|
|
92
|
+
&[data-is-modal='true'] {
|
|
93
|
+
position: fixed;
|
|
94
|
+
left: 0;
|
|
95
|
+
right: 0;
|
|
96
|
+
top: 0;
|
|
97
|
+
height: var(--mobile-care-searchbar-height, 100%);
|
|
98
|
+
overflow-y: auto;
|
|
99
|
+
-webkit-overflow-scrolling: touch;
|
|
100
|
+
background-color: white;
|
|
101
|
+
z-index: var(--searchbar-z-index);
|
|
102
|
+
}
|
|
103
|
+
`;
|
|
104
|
+
const StyledSearchBarMobileModalHeader = styled__default["default"].section ``;
|
|
105
|
+
const StyledHiddenInputMobile = styled__default["default"].input `
|
|
106
|
+
position: fixed;
|
|
107
|
+
left: -100%;
|
|
108
|
+
top: -100%;
|
|
109
|
+
`;
|
|
110
|
+
const StyledInput = styled__default["default"](index$1.Input) `
|
|
111
|
+
#booking-search-bar & {
|
|
112
|
+
input {
|
|
113
|
+
font-size: 16px;
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
`;
|
|
117
|
+
const CareSearchGlobalStyles = styled.createGlobalStyle `
|
|
118
|
+
.care-popup-open {
|
|
119
|
+
overflow: hidden;
|
|
120
|
+
position: fixed;
|
|
121
|
+
&::before {
|
|
122
|
+
content: '';
|
|
123
|
+
inset: 0;
|
|
124
|
+
position: absolute;
|
|
125
|
+
background-color: white;
|
|
126
|
+
min-height: 100vh;
|
|
127
|
+
min-width: 100vw;
|
|
128
|
+
z-index: 2;
|
|
129
|
+
}
|
|
130
|
+
}
|
|
131
|
+
`;
|
|
132
|
+
|
|
133
|
+
const ClearIcon = ({ className, color }) => (React__default["default"].createElement("svg", { className: className, width: "24", height: "24", viewBox: "0 0 24 24", fill: "none" },
|
|
134
|
+
React__default["default"].createElement("rect", { x: "4", y: "4", width: "16", height: "16", rx: "8", fill: "white" }),
|
|
135
|
+
React__default["default"].createElement("path", { fillRule: "evenodd", clipRule: "evenodd", d: "M12 20C16.4183 20 20 16.4183 20 12C20 7.58172 16.4183 4 12 4C7.58172 4 4 7.58172 4 12C4 16.4183 7.58172 20 12 20ZM8.29289 8.29289C8.68342 7.90237 9.31658 7.90237 9.70711 8.29289L12 10.5858L14.2929 8.29289C14.6834 7.90237 15.3166 7.90237 15.7071 8.29289C16.0976 8.68342 16.0976 9.31658 15.7071 9.70711L13.4142 12L15.7071 14.2929C16.0976 14.6834 16.0976 15.3166 15.7071 15.7071C15.3166 16.0976 14.6834 16.0976 14.2929 15.7071L12 13.4142L9.70711 15.7071C9.31658 16.0976 8.68342 16.0976 8.29289 15.7071C7.90237 15.3166 7.90237 14.6834 8.29289 14.2929L10.5858 12L8.29289 9.70711C7.90237 9.31658 7.90237 8.68342 8.29289 8.29289Z", fill: color || 'currentColor' })));
|
|
136
|
+
const CloseIcon = ({ className, color }) => (React__default["default"].createElement("svg", { className: className, width: "24", height: "24", viewBox: "0 0 24 24", fill: "none" },
|
|
137
|
+
React__default["default"].createElement("path", { d: "M18 6L6 18", stroke: color || 'currentColor', strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" }),
|
|
138
|
+
React__default["default"].createElement("path", { d: "M6 6L18 18", stroke: color || 'currentColor', strokeWidth: "2", strokeLinecap: "round", strokeLinejoin: "round" })));
|
|
139
|
+
const PinIcon = ({ className, color }) => (React__default["default"].createElement("svg", { width: "14", height: "20", viewBox: "0 0 14 20", className: className },
|
|
140
|
+
React__default["default"].createElement("path", { d: "M7 0C3.134 0 0 3.134 0 7C0 10.966 4.404 16.82 6.226 19.071C6.626 19.565 7.374 19.565 7.774 19.071C9.596 16.82 14 10.966 14 7C14 3.134 10.866 0 7 0ZM7 9.5C5.619 9.5 4.5 8.381 4.5 7C4.5 5.619 5.619 4.5 7 4.5C8.381 4.5 9.5 5.619 9.5 7C9.5 8.381 8.381 9.5 7 9.5Z", fill: color || 'currentColor' })));
|
|
141
|
+
const MagnifierIcon = ({ className, color }) => (React__default["default"].createElement("svg", { className: className, width: "24", height: "24", viewBox: "0 0 24 24", fill: "none" },
|
|
142
|
+
React__default["default"].createElement("path", { d: "M11 18C14.866 18 18 14.866 18 11C18 7.13401 14.866 4 11 4C7.13401 4 4 7.13401 4 11C4 14.866 7.13401 18 11 18Z", stroke: color || 'currentColor', strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" }),
|
|
143
|
+
React__default["default"].createElement("path", { d: "M20 20L16 16", stroke: color || 'currentColor', strokeWidth: "1.5", strokeLinecap: "round", strokeLinejoin: "round" })));
|
|
144
|
+
const DefaultThumbnailAny = ({ width, height, }) => (React__default["default"].createElement("svg", { width: width || 30, height: height || 30, viewBox: "0 0 30 30", fill: "none" },
|
|
145
|
+
React__default["default"].createElement("circle", { cx: "15", cy: "15", r: "15", fill: "#F7F9FC" })));
|
|
146
|
+
const DefaultThumbnailDoctor = ({ width, height, }) => (React__default["default"].createElement("svg", { width: width || 32, height: height || 32, viewBox: "0 0 32 32", fill: "none" },
|
|
147
|
+
React__default["default"].createElement("g", { clipPath: "url(#clip0_14712_400114)" },
|
|
148
|
+
React__default["default"].createElement("rect", { width: "32", height: "32", rx: "16", fill: "#E4E8EC" }),
|
|
149
|
+
React__default["default"].createElement("path", { d: "M22.065 9.58305C22.1108 9.80952 22.1431 10.0396 22.1614 10.2722C22.3769 13.0522 22.5858 16.1276 22.5727 17.618C22.5306 20.5688 19.708 21.1325 19.4564 21.1769L19.4495 21.5357L19.5228 23.9014C20.8688 23.9341 22.203 24.1759 23.4772 24.6196C24.5264 24.9739 25.4827 25.5591 26.2757 26.332C27.0688 27.105 27.6783 28.0461 28.0594 29.0858L31.9886 39.2068C31.91 39.3048 30.6939 39.6356 29.4888 39.944C30.1695 42.3315 30.4582 44.8142 30.3432 47.2953C30.2991 48.2666 30.1816 49.264 29.7245 50.1211C29.4508 50.6342 29.0319 51.0912 28.5296 51.3753C28.5099 51.4347 28.4864 51.4928 28.4593 51.5495C28.4293 51.6146 28.3908 51.6756 28.3448 51.7307C28.3293 51.7772 28.3232 51.8406 28.3162 51.9135C28.3004 52.0779 28.2799 52.2909 28.1362 52.4685C28.001 52.6373 27.8519 52.7945 27.6905 52.9386C27.6905 52.9386 27.092 52.9667 26.4133 52.9845L26.458 58.4088H5.7492L6.30965 52.9523L5.66093 53.1637C5.07664 53.3528 4.45628 53.4028 3.84925 53.3099C3.24222 53.2169 2.66526 52.9835 2.1643 52.6283C1.61489 52.2388 1.17445 51.715 0.884966 51.1068C0.595484 50.4987 0.46662 49.8266 0.510669 49.1545L0.644528 47.1369L1.41503 38.3366L1.81323 38.4135L-0.914307 37.8437L-0.402886 36.5663C-0.407359 36.5645 -0.411803 36.5627 -0.416214 36.5608C-0.410804 36.56 -0.40538 36.5594 -0.399946 36.5589L2.05995 30.4146C3.00034 28.0825 4.7421 26.1624 6.97187 24.9999C8.56171 24.176 10.3028 23.6861 12.0882 23.5597L11.788 16.5865C11.1882 16.6507 10.0095 16.5266 9.96087 14.954C9.91229 13.3824 11.0457 13.3171 11.6507 13.3961L11.6445 13.2523C11.5785 12.8433 11.5088 12.439 11.4577 12.2132C11.3782 11.8628 11.2611 11.4953 11.1419 11.1207C10.8794 10.2967 10.6061 9.43855 10.697 8.65293C10.697 8.65293 10.6909 8.00438 11.4565 7.24044C11.3707 6.86644 11.3686 6.47786 11.4507 6.10258C11.5366 5.70965 11.7125 5.34199 11.9645 5.02848C12.2165 4.71497 12.5377 4.46414 12.9029 4.29569C13.2682 4.12725 13.6675 4.04577 14.0696 4.05766C14.2277 4.06393 14.3849 4.08493 14.5418 4.10589C14.7932 4.13945 15.0439 4.17294 15.2971 4.14581C15.7708 4.09409 16.177 3.83884 16.5862 3.58167C16.8357 3.42492 17.0863 3.26745 17.354 3.15494C17.9119 2.93744 18.5266 2.91281 19.1002 3.08497C19.6738 3.25713 20.1733 3.61619 20.5192 4.105C20.5943 4.21716 20.6621 4.33678 20.7298 4.45631C20.9035 4.76299 21.077 5.06915 21.373 5.24769C21.5927 5.38236 21.8482 5.42658 22.1057 5.47114C22.2633 5.49842 22.4216 5.52582 22.5728 5.57417C23.0267 5.71015 23.3999 6.0411 23.6319 6.45436C23.6327 6.40753 23.6317 6.36062 23.629 6.31374C23.6502 6.3657 23.6623 6.42092 23.6649 6.47698C23.6661 6.49165 23.667 6.50632 23.6677 6.521C23.8246 6.82609 23.9058 7.17114 23.8885 7.51347C23.8544 7.93447 23.7053 8.33801 23.4574 8.68001C23.2096 9.02201 22.8725 9.28933 22.483 9.45278C22.3469 9.50712 22.2071 9.55061 22.065 9.58305Z", fill: "white" })),
|
|
150
|
+
React__default["default"].createElement("defs", null,
|
|
151
|
+
React__default["default"].createElement("clipPath", { id: "clip0_14712_400114" },
|
|
152
|
+
React__default["default"].createElement("rect", { width: "32", height: "32", rx: "16", fill: "white" })))));
|
|
153
|
+
const DefaultThumbnailService = ({ width, height, }) => (React__default["default"].createElement("svg", { width: width || 30, height: height || 30, viewBox: "0 0 30 30", fill: "none" },
|
|
154
|
+
React__default["default"].createElement("circle", { cx: "15", cy: "15", r: "15", fill: "#F7F9FC" }),
|
|
155
|
+
React__default["default"].createElement("path", { d: "M14.9998 6.66663C12.2752 6.66663 9.85335 7.97848 8.33317 9.99996H10.5988C11.8 8.94527 13.3625 8.33329 14.9998 8.33329C16.6372 8.33329 18.1997 8.94527 19.4009 9.99996H21.6665C20.1463 7.97848 17.7244 6.66663 14.9998 6.66663ZM7.7863 10.8333C7.07666 13.0403 6.6665 15.5989 6.6665 18.3333C6.6665 20.0846 6.82601 21.7675 7.13525 23.3333H22.8644C23.1737 21.7675 23.3332 20.0846 23.3332 18.3333C23.3332 15.5989 22.923 13.0403 22.2134 10.8333H7.7863ZM14.9998 13.3333C17.3013 13.3333 19.1665 15.1985 19.1665 17.5C19.1665 19.8014 17.3013 21.6666 14.9998 21.6666C12.6984 21.6666 10.8332 19.8014 10.8332 17.5C10.8332 15.1985 12.6984 13.3333 14.9998 13.3333ZM14.1665 15V16.6666H12.4998V18.3333H14.1665V20H15.8332V18.3333H17.4998V16.6666H15.8332V15H14.1665Z", fill: "#BFC5CC" })));
|
|
156
|
+
|
|
157
|
+
const StyledLiSkeleton$1 = styled__default["default"].li `
|
|
158
|
+
display: flex;
|
|
159
|
+
align-items: center;
|
|
160
|
+
gap: 12px;
|
|
161
|
+
padding: 8px 16px;
|
|
162
|
+
|
|
163
|
+
> :first-child {
|
|
164
|
+
flex: 1;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
> :nth-child(2) {
|
|
168
|
+
flex: 6;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
& + li::before {
|
|
172
|
+
content: '';
|
|
173
|
+
position: absolute;
|
|
174
|
+
left: 18px;
|
|
175
|
+
right: 18px;
|
|
176
|
+
top: 0;
|
|
177
|
+
height: 1px;
|
|
178
|
+
background-color: ${theme.theme.colors.neutral100};
|
|
179
|
+
}
|
|
180
|
+
`;
|
|
181
|
+
const LiSkeleton = ({ count, className }) => {
|
|
182
|
+
return (React__default["default"].createElement(React__default["default"].Fragment, null, [...Array(count)].map((__v, i) => (React__default["default"].createElement(StyledLiSkeleton$1, { className: className, key: i },
|
|
183
|
+
React__default["default"].createElement(Skeleton__default["default"], { count: 1, height: 32 }),
|
|
184
|
+
React__default["default"].createElement(Skeleton__default["default"], { count: 1, height: 24 }))))));
|
|
185
|
+
};
|
|
186
|
+
|
|
187
|
+
const checkMarkIconUrl = `url("data:image/svg+xml,%3Csvg width='19' height='14' viewBox='0 0 19 14' fill='none' xmlns='http://www.w3.org/2000/svg'%3E%3Cpath d='M16.9803 0.990669C16.7205 0.99841 16.4739 1.10699 16.2928 1.2934L5.99984 11.5864L2.70687 8.2934C2.61473 8.19743 2.50436 8.12081 2.38223 8.06802C2.2601 8.01524 2.12867 7.98735 1.99563 7.986C1.86259 7.98464 1.73061 8.00985 1.60743 8.06014C1.48426 8.11043 1.37235 8.18479 1.27827 8.27887C1.1842 8.37295 1.10983 8.48485 1.05954 8.60803C1.00926 8.73121 0.98405 8.86318 0.985403 8.99622C0.986757 9.12926 1.01464 9.26069 1.06743 9.38282C1.12021 9.50495 1.19684 9.61532 1.29281 9.70747L5.29281 13.7075C5.48035 13.8949 5.73467 14.0002 5.99984 14.0002C6.26501 14.0002 6.51933 13.8949 6.70687 13.7075L17.7069 2.70747C17.8514 2.567 17.9501 2.38616 17.99 2.18864C18.03 1.99112 18.0093 1.78614 17.9308 1.60055C17.8523 1.41497 17.7195 1.25744 17.5499 1.14861C17.3803 1.03978 17.1817 0.984729 16.9803 0.990669Z' fill='%232685F1'/%3E%3C/svg%3E%0A")`;
|
|
188
|
+
const StyledLocationResultsWrapper = styled__default["default"].div `
|
|
189
|
+
display: flex;
|
|
190
|
+
position: absolute;
|
|
191
|
+
top: 48px;
|
|
192
|
+
min-width: 100%;
|
|
193
|
+
box-shadow: 0px 24px 32px rgba(0, 0, 0, 0.04),
|
|
194
|
+
0px 16px 24px rgba(0, 0, 0, 0.04), 0px 4px 8px rgba(0, 0, 0, 0.04),
|
|
195
|
+
0px 0px 1px rgba(0, 0, 0, 0.04);
|
|
196
|
+
border-radius: ${theme.theme.borderRadius};
|
|
197
|
+
background-color: white;
|
|
198
|
+
z-index: 30;
|
|
199
|
+
|
|
200
|
+
${utils.MediaQueries.tdDown} {
|
|
201
|
+
position: relative;
|
|
202
|
+
top: 0;
|
|
203
|
+
box-shadow: initial;
|
|
204
|
+
}
|
|
205
|
+
`;
|
|
206
|
+
const StyledLocationResultsList = styled__default["default"].ul `
|
|
207
|
+
width: 100%;
|
|
208
|
+
max-height: 600px;
|
|
209
|
+
overflow-y: auto;
|
|
210
|
+
`;
|
|
211
|
+
const StyledPinIcon$1 = styled__default["default"](PinIcon) `
|
|
212
|
+
width: 12px;
|
|
213
|
+
height: 18px;
|
|
214
|
+
`;
|
|
215
|
+
const StyledLocationItem$1 = styled__default["default"].li `
|
|
216
|
+
position: relative;
|
|
217
|
+
cursor: pointer;
|
|
218
|
+
padding: 12px 18px;
|
|
219
|
+
display: flex;
|
|
220
|
+
align-items: center;
|
|
221
|
+
gap: 14px;
|
|
222
|
+
overflow: hidden;
|
|
223
|
+
|
|
224
|
+
${({ isSelected }) => isSelected &&
|
|
225
|
+
`
|
|
226
|
+
&::after {
|
|
227
|
+
content: ${checkMarkIconUrl};
|
|
228
|
+
top: 50%;
|
|
229
|
+
right: 18px;
|
|
230
|
+
position: absolute;
|
|
231
|
+
transform: translateY(-50%);
|
|
232
|
+
}
|
|
233
|
+
`}
|
|
234
|
+
|
|
235
|
+
& + li::before {
|
|
236
|
+
content: '';
|
|
237
|
+
position: absolute;
|
|
238
|
+
left: 18px;
|
|
239
|
+
right: 18px;
|
|
240
|
+
top: 0;
|
|
241
|
+
height: 1px;
|
|
242
|
+
background-color: ${theme.theme.colors.neutral100};
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
&:not([data-is-denied='true']):hover {
|
|
246
|
+
background-color: ${theme.theme.colors.neutral50};
|
|
247
|
+
}
|
|
248
|
+
|
|
249
|
+
&:last-child:hover {
|
|
250
|
+
border-bottom-right-radius: 6px;
|
|
251
|
+
border-bottom-left-radius: 6px;
|
|
252
|
+
}
|
|
253
|
+
|
|
254
|
+
&:first-child:hover {
|
|
255
|
+
border-top-right-radius: 6px;
|
|
256
|
+
border-top-left-radius: 6px;
|
|
257
|
+
}
|
|
258
|
+
|
|
259
|
+
&[data-is-denied='true'] {
|
|
260
|
+
cursor: not-allowed;
|
|
261
|
+
}
|
|
262
|
+
`;
|
|
263
|
+
const StyledLiSkeleton = styled__default["default"](LiSkeleton) `
|
|
264
|
+
&:first-child {
|
|
265
|
+
padding-top: 18px;
|
|
266
|
+
}
|
|
267
|
+
`;
|
|
268
|
+
|
|
269
|
+
const LocationResults = ({ cities, isLoading, onLocationClick, selectedLocation, }) => {
|
|
270
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
271
|
+
const renderContent = () => {
|
|
272
|
+
if (isLoading) {
|
|
273
|
+
return React__default["default"].createElement(StyledLiSkeleton, { count: 5 });
|
|
274
|
+
}
|
|
275
|
+
if (!cities || cities.length < 1) {
|
|
276
|
+
return (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
277
|
+
React__default["default"].createElement(StyledLocationItem$1, { "data-is-denied": "true" },
|
|
278
|
+
React__default["default"].createElement(index$2.Text, { size: "sm", color: "#ccc" }, t('booking.searchBar.noResults')))));
|
|
279
|
+
}
|
|
280
|
+
return (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
281
|
+
React__default["default"].createElement(StyledLocationItem$1, { key: "all-location", role: "button", tabIndex: 0, onClick: () => {
|
|
282
|
+
var _a;
|
|
283
|
+
if (onLocationClick) {
|
|
284
|
+
onLocationClick({
|
|
285
|
+
name: t('booking.searchBar.allLocations'),
|
|
286
|
+
id: constants.ID_OPTION_ALL_LOCATION,
|
|
287
|
+
slug: (_a = constants.LOCALIZED_SLUGS[locale]) === null || _a === void 0 ? void 0 : _a.ALL,
|
|
288
|
+
});
|
|
289
|
+
}
|
|
290
|
+
} },
|
|
291
|
+
React__default["default"].createElement(StyledPinIcon$1, { color: theme.theme.colors.neutral400 }),
|
|
292
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, t('booking.searchBar.allLocations'))),
|
|
293
|
+
cities.map((city) => (React__default["default"].createElement(StyledLocationItem$1, { key: city.id, onClick: (evt) => {
|
|
294
|
+
evt.nativeEvent.stopImmediatePropagation();
|
|
295
|
+
if (onLocationClick) {
|
|
296
|
+
onLocationClick(city);
|
|
297
|
+
}
|
|
298
|
+
}, role: "button", tabIndex: 0, "aria-label": `Select ${city.name} as location`, isSelected: (selectedLocation === null || selectedLocation === void 0 ? void 0 : selectedLocation.id) === city.id },
|
|
299
|
+
React__default["default"].createElement(StyledPinIcon$1, { color: theme.theme.colors.neutral400 }),
|
|
300
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, city.name))))));
|
|
301
|
+
};
|
|
302
|
+
return (React__default["default"].createElement(StyledLocationResultsWrapper, { "data-testid": "location-search-results" },
|
|
303
|
+
React__default["default"].createElement(StyledLocationResultsList, null, renderContent())));
|
|
304
|
+
};
|
|
305
|
+
|
|
306
|
+
const EVENT_NAMES = {
|
|
307
|
+
TYPE_CHARACTER: 'TYPE_CHARACTER',
|
|
308
|
+
REMOVE_CHARACTER: 'REMOVE_CHARACTER',
|
|
309
|
+
REMOVE_ALL: 'REMOVE_ALL',
|
|
310
|
+
REMOVE_LAST_VISIBLE_NODE: 'REMOVE_LAST_VISIBLE_NODE',
|
|
311
|
+
PAUSE_FOR: 'PAUSE_FOR',
|
|
312
|
+
CHANGE_DELETE_SPEED: 'CHANGE_DELETE_SPEED',
|
|
313
|
+
CHANGE_DELAY: 'CHANGE_DELAY',
|
|
314
|
+
PASTE_STRING: 'PASTE_STRING',
|
|
315
|
+
};
|
|
316
|
+
const getRandomInteger = (min, max) => {
|
|
317
|
+
return Math.floor(Math.random() * (max - min + 1)) + min;
|
|
318
|
+
};
|
|
319
|
+
const VISIBLE_NODE_TYPES = {
|
|
320
|
+
TEXT_NODE: 'TEXT_NODE',
|
|
321
|
+
};
|
|
322
|
+
class Typewriter {
|
|
323
|
+
constructor(options) {
|
|
324
|
+
this.state = {
|
|
325
|
+
lastFrameTime: null,
|
|
326
|
+
pauseUntil: null,
|
|
327
|
+
eventQueue: [],
|
|
328
|
+
eventLoop: null,
|
|
329
|
+
eventLoopPaused: false,
|
|
330
|
+
reverseCalledEvents: [],
|
|
331
|
+
calledEvents: [],
|
|
332
|
+
visibleNodes: [],
|
|
333
|
+
initialOptions: null,
|
|
334
|
+
};
|
|
335
|
+
this.options = {
|
|
336
|
+
strings: null,
|
|
337
|
+
delay: 'natural',
|
|
338
|
+
pauseFor: 1500,
|
|
339
|
+
deleteSpeed: 'natural',
|
|
340
|
+
loop: false,
|
|
341
|
+
autoStart: false,
|
|
342
|
+
stringSplitter: null,
|
|
343
|
+
onCreateTextNode: null,
|
|
344
|
+
onRemoveNode: null,
|
|
345
|
+
};
|
|
346
|
+
this.start = () => {
|
|
347
|
+
this.state.eventLoopPaused = false;
|
|
348
|
+
this.runEventLoop();
|
|
349
|
+
return this;
|
|
350
|
+
};
|
|
351
|
+
this.pause = () => {
|
|
352
|
+
this.state.eventLoopPaused = true;
|
|
353
|
+
return this;
|
|
354
|
+
};
|
|
355
|
+
this.stop = () => {
|
|
356
|
+
if (this.state.eventLoop) {
|
|
357
|
+
window.cancelAnimationFrame(this.state.eventLoop);
|
|
358
|
+
this.state.eventLoop = null;
|
|
359
|
+
}
|
|
360
|
+
return this;
|
|
361
|
+
};
|
|
362
|
+
this.pauseFor = (ms) => {
|
|
363
|
+
this.addEventToQueue(EVENT_NAMES.PAUSE_FOR, { ms });
|
|
364
|
+
return this;
|
|
365
|
+
};
|
|
366
|
+
this.typeOutAllStrings = () => {
|
|
367
|
+
if (typeof this.options.strings === 'string') {
|
|
368
|
+
this.typeString(this.options.strings).pauseFor(this.options.pauseFor);
|
|
369
|
+
return this;
|
|
370
|
+
}
|
|
371
|
+
this.options.strings.forEach((string) => {
|
|
372
|
+
this.typeString(string)
|
|
373
|
+
.pauseFor(this.options.pauseFor)
|
|
374
|
+
.deleteAll(this.options.deleteSpeed);
|
|
375
|
+
});
|
|
376
|
+
return this;
|
|
377
|
+
};
|
|
378
|
+
this.typeString = (string, node = null) => {
|
|
379
|
+
if (string) {
|
|
380
|
+
const { stringSplitter } = this.options || {};
|
|
381
|
+
const characters = typeof stringSplitter === 'function'
|
|
382
|
+
? stringSplitter(string)
|
|
383
|
+
: string.split('');
|
|
384
|
+
this.typeCharacters(characters, node);
|
|
385
|
+
}
|
|
386
|
+
return this;
|
|
387
|
+
};
|
|
388
|
+
this.pasteString = (string, node = null) => {
|
|
389
|
+
if (string) {
|
|
390
|
+
this.addEventToQueue(EVENT_NAMES.PASTE_STRING, {
|
|
391
|
+
character: string,
|
|
392
|
+
node,
|
|
393
|
+
});
|
|
394
|
+
}
|
|
395
|
+
return this;
|
|
396
|
+
};
|
|
397
|
+
this.deleteAll = (speed = 'natural') => {
|
|
398
|
+
this.addEventToQueue(EVENT_NAMES.REMOVE_ALL, { speed });
|
|
399
|
+
return this;
|
|
400
|
+
};
|
|
401
|
+
this.changeDeleteSpeed = (speed) => {
|
|
402
|
+
if (!speed) {
|
|
403
|
+
throw new Error('Must provide new delete speed');
|
|
404
|
+
}
|
|
405
|
+
this.addEventToQueue(EVENT_NAMES.CHANGE_DELETE_SPEED, { speed });
|
|
406
|
+
return this;
|
|
407
|
+
};
|
|
408
|
+
this.changeDelay = (delay) => {
|
|
409
|
+
if (!delay) {
|
|
410
|
+
throw new Error('Must provide new delay');
|
|
411
|
+
}
|
|
412
|
+
this.addEventToQueue(EVENT_NAMES.CHANGE_DELAY, { delay });
|
|
413
|
+
return this;
|
|
414
|
+
};
|
|
415
|
+
this.deleteChars = (amount) => {
|
|
416
|
+
if (!amount) {
|
|
417
|
+
throw new Error('Must provide amount of characters to delete');
|
|
418
|
+
}
|
|
419
|
+
for (let i = 0; i < amount; i++) {
|
|
420
|
+
this.addEventToQueue(EVENT_NAMES.REMOVE_CHARACTER);
|
|
421
|
+
}
|
|
422
|
+
return this;
|
|
423
|
+
};
|
|
424
|
+
this.typeCharacters = (characters, node = null) => {
|
|
425
|
+
if (!characters || !Array.isArray(characters)) {
|
|
426
|
+
throw new Error('Characters must be an array');
|
|
427
|
+
}
|
|
428
|
+
characters.forEach((character) => {
|
|
429
|
+
this.addEventToQueue(EVENT_NAMES.TYPE_CHARACTER, { character, node });
|
|
430
|
+
});
|
|
431
|
+
return this;
|
|
432
|
+
};
|
|
433
|
+
this.removeCharacters = (characters) => {
|
|
434
|
+
if (!characters || !Array.isArray(characters)) {
|
|
435
|
+
throw new Error('Characters must be an array');
|
|
436
|
+
}
|
|
437
|
+
characters.forEach(() => {
|
|
438
|
+
this.addEventToQueue(EVENT_NAMES.REMOVE_CHARACTER);
|
|
439
|
+
});
|
|
440
|
+
return this;
|
|
441
|
+
};
|
|
442
|
+
this.addEventToQueue = (eventName, eventArgs, prepend = false) => {
|
|
443
|
+
return this.addEventToStateProperty(eventName, eventArgs, prepend, 'eventQueue');
|
|
444
|
+
};
|
|
445
|
+
this.addReverseCalledEvent = (eventName, eventArgs, prepend = false) => {
|
|
446
|
+
const { loop } = this.options;
|
|
447
|
+
if (!loop) {
|
|
448
|
+
return this;
|
|
449
|
+
}
|
|
450
|
+
return this.addEventToStateProperty(eventName, eventArgs, prepend, 'reverseCalledEvents');
|
|
451
|
+
};
|
|
452
|
+
this.addEventToStateProperty = (eventName, eventArgs, prepend = false, property) => {
|
|
453
|
+
const eventItem = {
|
|
454
|
+
eventName,
|
|
455
|
+
eventArgs: eventArgs || {},
|
|
456
|
+
};
|
|
457
|
+
if (prepend) {
|
|
458
|
+
this.state[property] = [eventItem, ...this.state[property]];
|
|
459
|
+
}
|
|
460
|
+
else {
|
|
461
|
+
this.state[property] = [...this.state[property], eventItem];
|
|
462
|
+
}
|
|
463
|
+
return this;
|
|
464
|
+
};
|
|
465
|
+
this.runEventLoop = () => {
|
|
466
|
+
if (!this.state.lastFrameTime) {
|
|
467
|
+
this.state.lastFrameTime = Date.now();
|
|
468
|
+
}
|
|
469
|
+
// Setup variables to calculate if this frame should run
|
|
470
|
+
const nowTime = Date.now();
|
|
471
|
+
const delta = nowTime - this.state.lastFrameTime;
|
|
472
|
+
if (!this.state.eventQueue.length) {
|
|
473
|
+
if (!this.options.loop) {
|
|
474
|
+
return;
|
|
475
|
+
}
|
|
476
|
+
// Reset event queue if we are looping
|
|
477
|
+
this.state.eventQueue = [...this.state.calledEvents];
|
|
478
|
+
this.state.calledEvents = [];
|
|
479
|
+
this.options = Object.assign({}, this.state.initialOptions);
|
|
480
|
+
}
|
|
481
|
+
// Request next frame
|
|
482
|
+
this.state.eventLoop = window.requestAnimationFrame(this.runEventLoop);
|
|
483
|
+
// Check if event loop is paused
|
|
484
|
+
if (this.state.eventLoopPaused) {
|
|
485
|
+
return;
|
|
486
|
+
}
|
|
487
|
+
// Check if state has pause until time
|
|
488
|
+
if (this.state.pauseUntil) {
|
|
489
|
+
// Check if event loop should be paused
|
|
490
|
+
if (nowTime < this.state.pauseUntil) {
|
|
491
|
+
return;
|
|
492
|
+
}
|
|
493
|
+
// Reset pause time
|
|
494
|
+
this.state.pauseUntil = null;
|
|
495
|
+
}
|
|
496
|
+
// Make a clone of event queue
|
|
497
|
+
const eventQueue = [...this.state.eventQueue];
|
|
498
|
+
// Get first event from queue
|
|
499
|
+
const currentEvent = eventQueue.shift();
|
|
500
|
+
// Setup delay variable
|
|
501
|
+
let delay = 0;
|
|
502
|
+
// Check if frame should run or be
|
|
503
|
+
// skipped based on fps interval
|
|
504
|
+
if (currentEvent.eventName === EVENT_NAMES.REMOVE_LAST_VISIBLE_NODE ||
|
|
505
|
+
currentEvent.eventName === EVENT_NAMES.REMOVE_CHARACTER) {
|
|
506
|
+
delay =
|
|
507
|
+
this.options.deleteSpeed === 'natural'
|
|
508
|
+
? getRandomInteger(40, 80)
|
|
509
|
+
: this.options.deleteSpeed;
|
|
510
|
+
}
|
|
511
|
+
else {
|
|
512
|
+
delay =
|
|
513
|
+
this.options.delay === 'natural'
|
|
514
|
+
? getRandomInteger(120, 160)
|
|
515
|
+
: this.options.delay;
|
|
516
|
+
}
|
|
517
|
+
if (delta <= delay) {
|
|
518
|
+
return;
|
|
519
|
+
}
|
|
520
|
+
// Get current event args
|
|
521
|
+
const { eventName, eventArgs } = currentEvent;
|
|
522
|
+
// Run item from event loop
|
|
523
|
+
switch (eventName) {
|
|
524
|
+
case EVENT_NAMES.PASTE_STRING:
|
|
525
|
+
case EVENT_NAMES.TYPE_CHARACTER: {
|
|
526
|
+
const { character } = eventArgs;
|
|
527
|
+
const textNode = document.createTextNode(character);
|
|
528
|
+
let textNodeToUse = textNode;
|
|
529
|
+
if (this.options.onCreateTextNode &&
|
|
530
|
+
typeof this.options.onCreateTextNode === 'function') {
|
|
531
|
+
textNodeToUse = this.options.onCreateTextNode(character, textNode);
|
|
532
|
+
}
|
|
533
|
+
this.state.visibleNodes = [
|
|
534
|
+
...this.state.visibleNodes,
|
|
535
|
+
{
|
|
536
|
+
type: VISIBLE_NODE_TYPES.TEXT_NODE,
|
|
537
|
+
character,
|
|
538
|
+
node: textNodeToUse,
|
|
539
|
+
},
|
|
540
|
+
];
|
|
541
|
+
break;
|
|
542
|
+
}
|
|
543
|
+
case EVENT_NAMES.REMOVE_CHARACTER: {
|
|
544
|
+
eventQueue.unshift({
|
|
545
|
+
eventName: EVENT_NAMES.REMOVE_LAST_VISIBLE_NODE,
|
|
546
|
+
eventArgs: { removingCharacterNode: true },
|
|
547
|
+
});
|
|
548
|
+
break;
|
|
549
|
+
}
|
|
550
|
+
case EVENT_NAMES.PAUSE_FOR: {
|
|
551
|
+
const { ms } = currentEvent.eventArgs;
|
|
552
|
+
this.state.pauseUntil = Date.now() + parseInt(ms);
|
|
553
|
+
break;
|
|
554
|
+
}
|
|
555
|
+
case EVENT_NAMES.REMOVE_ALL: {
|
|
556
|
+
const { visibleNodes } = this.state;
|
|
557
|
+
const { speed } = eventArgs;
|
|
558
|
+
const removeAllEventItems = [];
|
|
559
|
+
if (speed) {
|
|
560
|
+
removeAllEventItems.push({
|
|
561
|
+
eventName: EVENT_NAMES.CHANGE_DELETE_SPEED,
|
|
562
|
+
eventArgs: { speed, temp: true },
|
|
563
|
+
});
|
|
564
|
+
}
|
|
565
|
+
for (let i = 0, length = visibleNodes.length; i < length; i++) {
|
|
566
|
+
removeAllEventItems.push({
|
|
567
|
+
eventName: EVENT_NAMES.REMOVE_LAST_VISIBLE_NODE,
|
|
568
|
+
eventArgs: { removingCharacterNode: false },
|
|
569
|
+
});
|
|
570
|
+
}
|
|
571
|
+
if (speed) {
|
|
572
|
+
removeAllEventItems.push({
|
|
573
|
+
eventName: EVENT_NAMES.CHANGE_DELETE_SPEED,
|
|
574
|
+
eventArgs: { speed: this.options.deleteSpeed, temp: true },
|
|
575
|
+
});
|
|
576
|
+
}
|
|
577
|
+
eventQueue.unshift(...removeAllEventItems);
|
|
578
|
+
break;
|
|
579
|
+
}
|
|
580
|
+
case EVENT_NAMES.REMOVE_LAST_VISIBLE_NODE: {
|
|
581
|
+
if (this.state.visibleNodes.length) {
|
|
582
|
+
const { node, character } = this.state.visibleNodes.pop();
|
|
583
|
+
if (this.options.onRemoveNode &&
|
|
584
|
+
typeof this.options.onRemoveNode === 'function') {
|
|
585
|
+
this.options.onRemoveNode({
|
|
586
|
+
node,
|
|
587
|
+
character,
|
|
588
|
+
});
|
|
589
|
+
}
|
|
590
|
+
if (node) {
|
|
591
|
+
node.parentNode.removeChild(node);
|
|
592
|
+
}
|
|
593
|
+
}
|
|
594
|
+
break;
|
|
595
|
+
}
|
|
596
|
+
case EVENT_NAMES.CHANGE_DELETE_SPEED: {
|
|
597
|
+
this.options.deleteSpeed = currentEvent.eventArgs.speed;
|
|
598
|
+
break;
|
|
599
|
+
}
|
|
600
|
+
case EVENT_NAMES.CHANGE_DELAY: {
|
|
601
|
+
this.options.delay = currentEvent.eventArgs.delay;
|
|
602
|
+
break;
|
|
603
|
+
}
|
|
604
|
+
}
|
|
605
|
+
// Add que item to called queue if we are looping
|
|
606
|
+
if (this.options.loop) {
|
|
607
|
+
if (currentEvent.eventName !== EVENT_NAMES.REMOVE_LAST_VISIBLE_NODE &&
|
|
608
|
+
!(currentEvent.eventArgs && currentEvent.eventArgs.temp)) {
|
|
609
|
+
this.state.calledEvents = [...this.state.calledEvents, currentEvent];
|
|
610
|
+
}
|
|
611
|
+
}
|
|
612
|
+
// Replace state event queue with cloned queue
|
|
613
|
+
this.state.eventQueue = eventQueue;
|
|
614
|
+
// Set last frame time so it can be used to calculate next frame
|
|
615
|
+
this.state.lastFrameTime = nowTime;
|
|
616
|
+
};
|
|
617
|
+
if (options) {
|
|
618
|
+
this.options = Object.assign(Object.assign({}, this.options), options);
|
|
619
|
+
}
|
|
620
|
+
this.state.initialOptions = Object.assign({}, this.options);
|
|
621
|
+
this.init();
|
|
622
|
+
}
|
|
623
|
+
init() {
|
|
624
|
+
this.addEventToQueue(EVENT_NAMES.REMOVE_ALL, null, true);
|
|
625
|
+
if (this.options.autoStart === true && this.options.strings) {
|
|
626
|
+
this.typeOutAllStrings().start();
|
|
627
|
+
}
|
|
628
|
+
}
|
|
629
|
+
}
|
|
630
|
+
|
|
631
|
+
function useAnimatedPlaceholder({ inputRef, wrapperRef, disabled, }) {
|
|
632
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
633
|
+
const values = React.useMemo(() => {
|
|
634
|
+
if (disabled) {
|
|
635
|
+
return [];
|
|
636
|
+
}
|
|
637
|
+
const shuffleKeys = [
|
|
638
|
+
'booking.searchBar.placeholder.hospital',
|
|
639
|
+
'booking.searchBar.placeholder.doctor',
|
|
640
|
+
];
|
|
641
|
+
if (locale !== 'zh-TW') {
|
|
642
|
+
shuffleKeys.push('booking.searchBar.placeholder.specialty', 'booking.searchBar.placeholder.service');
|
|
643
|
+
}
|
|
644
|
+
return shuffle__default["default"](shuffleKeys).map((s) => t(s));
|
|
645
|
+
}, [t, locale]);
|
|
646
|
+
React.useEffect(() => {
|
|
647
|
+
if (disabled) {
|
|
648
|
+
return;
|
|
649
|
+
}
|
|
650
|
+
const input = getInput();
|
|
651
|
+
if (input) {
|
|
652
|
+
input.placeholder = '';
|
|
653
|
+
new Typewriter({
|
|
654
|
+
strings: values,
|
|
655
|
+
autoStart: true,
|
|
656
|
+
loop: true,
|
|
657
|
+
delay: 32,
|
|
658
|
+
deleteSpeed: 32,
|
|
659
|
+
pauseFor: 1500,
|
|
660
|
+
onCreateTextNode: customNodeCreator,
|
|
661
|
+
onRemoveNode: onRemoveNode,
|
|
662
|
+
});
|
|
663
|
+
}
|
|
664
|
+
}, [inputRef, wrapperRef]);
|
|
665
|
+
function customNodeCreator(character) {
|
|
666
|
+
const input = getInput();
|
|
667
|
+
if (input) {
|
|
668
|
+
input.placeholder = input.placeholder + character;
|
|
669
|
+
}
|
|
670
|
+
return null;
|
|
671
|
+
}
|
|
672
|
+
function onRemoveNode() {
|
|
673
|
+
const input = getInput();
|
|
674
|
+
if (input) {
|
|
675
|
+
input.placeholder = input.placeholder.slice(0, -1);
|
|
676
|
+
}
|
|
677
|
+
}
|
|
678
|
+
function getInput() {
|
|
679
|
+
if (inputRef && inputRef.current) {
|
|
680
|
+
return inputRef.current;
|
|
681
|
+
}
|
|
682
|
+
else if (wrapperRef && wrapperRef.current) {
|
|
683
|
+
return wrapperRef.current.querySelector('input') || null;
|
|
684
|
+
}
|
|
685
|
+
return null;
|
|
686
|
+
}
|
|
687
|
+
return;
|
|
688
|
+
}
|
|
689
|
+
|
|
690
|
+
const StyledFakeInputSearchMobile = styled__default["default"].div `
|
|
691
|
+
user-select: none;
|
|
692
|
+
input {
|
|
693
|
+
pointer-events: none;
|
|
694
|
+
background-color: white;
|
|
695
|
+
}
|
|
696
|
+
`;
|
|
697
|
+
function MobileFakeInput({ focused, value = '', onClick, trackingAttributes, inputSearchPlaceholder, }) {
|
|
698
|
+
const { t } = useTranslations.useTranslations();
|
|
699
|
+
const wrapperRef = React.useRef(null);
|
|
700
|
+
useAnimatedPlaceholder({ wrapperRef, disabled: !!inputSearchPlaceholder });
|
|
701
|
+
const gaAttributes = React.useMemo(() => {
|
|
702
|
+
if (trackingAttributes) {
|
|
703
|
+
return {
|
|
704
|
+
'data-event-category': trackingAttributes.dataEventCategory,
|
|
705
|
+
'data-event-action': trackingAttributes.dataEventAction,
|
|
706
|
+
'data-event-label': trackingAttributes.dataEventLabel,
|
|
707
|
+
};
|
|
708
|
+
}
|
|
709
|
+
else {
|
|
710
|
+
return {};
|
|
711
|
+
}
|
|
712
|
+
}, [trackingAttributes]);
|
|
713
|
+
return (React__default["default"].createElement(StyledFakeInputSearchMobile, Object.assign({ onClick: () => onClick && onClick(), ref: wrapperRef }, gaAttributes),
|
|
714
|
+
React__default["default"].createElement(StyledInput, { inputClassName: focused === 'location' ? 'focused' : undefined, name: "booking-search-placeholder", displayIcon: React__default["default"].createElement(MagnifierIcon, { color: theme.theme.colors.gray400 }), placeholder: t('booking.searchBar.searchInput.placeholder'), value: value, size: "md" })));
|
|
715
|
+
}
|
|
716
|
+
|
|
717
|
+
const StyledTopBar = styled__default["default"].header `
|
|
718
|
+
display: flex;
|
|
719
|
+
height: 64px;
|
|
720
|
+
align-items: center;
|
|
721
|
+
justify-content: space-between;
|
|
722
|
+
margin: 0 auto;
|
|
723
|
+
position: sticky;
|
|
724
|
+
z-index: 99;
|
|
725
|
+
background-color: white;
|
|
726
|
+
top: 0;
|
|
727
|
+
left: 0;
|
|
728
|
+
`;
|
|
729
|
+
const StyledTopBarHeaderRight = styled__default["default"].div `
|
|
730
|
+
display: inline-flex;
|
|
731
|
+
flex: 1;
|
|
732
|
+
justify-content: flex-end;
|
|
733
|
+
cursor: pointer;
|
|
734
|
+
text-decoration: underline;
|
|
735
|
+
`;
|
|
736
|
+
const StyledTopBarIcon = styled__default["default"].div `
|
|
737
|
+
display: flex;
|
|
738
|
+
align-items: center;
|
|
739
|
+
margin-left: 16px;
|
|
740
|
+
cursor: pointer;
|
|
741
|
+
`;
|
|
742
|
+
const StyledTopbarHeading = styled__default["default"].div `
|
|
743
|
+
width: 100%;
|
|
744
|
+
margin-left: 24px;
|
|
745
|
+
`;
|
|
746
|
+
const StyledTopbarHeadingText = styled__default["default"](index$2.Text) `
|
|
747
|
+
color: ${theme.theme.colors.secondaryDark};
|
|
748
|
+
text-align: start;
|
|
749
|
+
`;
|
|
750
|
+
|
|
751
|
+
const MobileTopBar = ({ className, onLeftClick, headingText, onRightClick, iconLeft, textRight, }) => {
|
|
752
|
+
return (React__default["default"].createElement(StyledTopBar, { className: className },
|
|
753
|
+
React__default["default"].createElement(StyledTopBarIcon, { onClick: onLeftClick }, iconLeft || React__default["default"].createElement(CloseIcon, { color: theme.theme.colors.gray800 })),
|
|
754
|
+
React__default["default"].createElement(StyledTopbarHeading, null,
|
|
755
|
+
React__default["default"].createElement(StyledTopbarHeadingText, { size: "md", weight: "bold" }, headingText)),
|
|
756
|
+
React__default["default"].createElement(StyledTopBarHeaderRight, { onClick: onRightClick }, textRight && React__default["default"].createElement("p", null, textRight))));
|
|
757
|
+
};
|
|
758
|
+
|
|
759
|
+
const SEARCH_KEYWORD_MIN_LENGTH$1 = {
|
|
760
|
+
'en-PH': 3,
|
|
761
|
+
'tl-PH': 2,
|
|
762
|
+
'id-ID': 3,
|
|
763
|
+
'vi-VN': 2,
|
|
764
|
+
'zh-TW': 0,
|
|
765
|
+
'ms-MY': 2,
|
|
766
|
+
};
|
|
767
|
+
|
|
768
|
+
const initialState$1 = {
|
|
769
|
+
isMobile: false,
|
|
770
|
+
isDebug: false,
|
|
771
|
+
navigateTo: null,
|
|
772
|
+
geoLocationPermission: 'unset',
|
|
773
|
+
geoLocationCoordinates: null,
|
|
774
|
+
focused: 'none',
|
|
775
|
+
searchLocationKeywords: '',
|
|
776
|
+
searchKeywords: '',
|
|
777
|
+
selectedLocation: null,
|
|
778
|
+
defaultCity: null,
|
|
779
|
+
initialCities: [],
|
|
780
|
+
cities: [],
|
|
781
|
+
searchResults: [],
|
|
782
|
+
initialSearchResults: [],
|
|
783
|
+
isLoadingCities: false,
|
|
784
|
+
isLoadingSearchResults: false,
|
|
785
|
+
isMobileModalOpened: false,
|
|
786
|
+
initialSelectedCity: null,
|
|
787
|
+
autoCompleteDisabled: false,
|
|
788
|
+
inputSearchPlaceholder: '',
|
|
789
|
+
locale: 'vi-VN',
|
|
790
|
+
};
|
|
791
|
+
var ActionTypes$1;
|
|
792
|
+
(function (ActionTypes) {
|
|
793
|
+
ActionTypes["NavigateTo"] = "navigate to url";
|
|
794
|
+
ActionTypes["ClickOutsideInputLocation"] = "click outside input location";
|
|
795
|
+
ActionTypes["ClickOutsideInputSearch"] = "click outside input search";
|
|
796
|
+
ActionTypes["SelectCurrentLocation"] = "select current location";
|
|
797
|
+
ActionTypes["FocusInputLocation"] = "focus input location";
|
|
798
|
+
ActionTypes["FocusInputSearch"] = "focus input search";
|
|
799
|
+
ActionTypes["ChangeInputLocation"] = "change input location";
|
|
800
|
+
ActionTypes["ChangeInputSearch"] = "change input search";
|
|
801
|
+
ActionTypes["ClearInputLocation"] = "clear input location";
|
|
802
|
+
ActionTypes["ClearInputSearch"] = "clear input search";
|
|
803
|
+
ActionTypes["SelectLocation"] = "select location";
|
|
804
|
+
ActionTypes["FetchCitiesStart"] = "fetch cities start";
|
|
805
|
+
ActionTypes["FetchCitiesFinish"] = "fetch cities finish";
|
|
806
|
+
ActionTypes["FetchSearchResultsStart"] = "fetch search results start";
|
|
807
|
+
ActionTypes["FetchSearchResultsComplete"] = "fetch search results complete";
|
|
808
|
+
ActionTypes["FetchSearchResultsFinish"] = "fetch search results finish";
|
|
809
|
+
ActionTypes["FetchCitiesByGeoIpComplete"] = "fetch cities by geo IP finish";
|
|
810
|
+
ActionTypes["FetchCitiesByKeywordComplete"] = "fetch cities by keyword finish";
|
|
811
|
+
ActionTypes["DisplayInitialCities"] = "display initial cities";
|
|
812
|
+
ActionTypes["DisplayInitialSearchResults"] = "display initial search results";
|
|
813
|
+
ActionTypes["GrantGeoLocationPermission"] = "grant geolocation permission";
|
|
814
|
+
ActionTypes["DenyGeoLocationPermission"] = "deny geolocation permission";
|
|
815
|
+
ActionTypes["OpenMobileModal"] = "open mobile modal";
|
|
816
|
+
ActionTypes["CloseMobileModal"] = "close mobile modal";
|
|
817
|
+
ActionTypes["UpdateInitialSearchValue"] = "update initial search value";
|
|
818
|
+
ActionTypes["SelectSearchResult"] = "select search result";
|
|
819
|
+
ActionTypes["SetInputSearchPlaceholder"] = "set input search placeholder";
|
|
820
|
+
})(ActionTypes$1 || (ActionTypes$1 = {}));
|
|
821
|
+
function resetSearchLocationKeywords$1(state) {
|
|
822
|
+
const { selectedLocation, searchLocationKeywords } = state;
|
|
823
|
+
if (selectedLocation && searchLocationKeywords !== selectedLocation.name) {
|
|
824
|
+
return Object.assign(Object.assign({}, state), { searchLocationKeywords: selectedLocation.name });
|
|
825
|
+
}
|
|
826
|
+
return state;
|
|
827
|
+
}
|
|
828
|
+
function reducer$1(state, action) {
|
|
829
|
+
var _a;
|
|
830
|
+
if (state.isDebug) {
|
|
831
|
+
console.log('bookingSearchBar', { action, state });
|
|
832
|
+
}
|
|
833
|
+
switch (action.type) {
|
|
834
|
+
case ActionTypes$1.NavigateTo:
|
|
835
|
+
return Object.assign(Object.assign({}, state), { navigateTo: action.payload, focused: 'none', isMobileModalOpened: false });
|
|
836
|
+
case ActionTypes$1.ClickOutsideInputLocation: {
|
|
837
|
+
if (state.isMobile || state.focused !== 'location') {
|
|
838
|
+
return state;
|
|
839
|
+
}
|
|
840
|
+
return resetSearchLocationKeywords$1(Object.assign(Object.assign({}, state), { focused: 'none' }));
|
|
841
|
+
}
|
|
842
|
+
case ActionTypes$1.ClickOutsideInputSearch: {
|
|
843
|
+
if (state.isMobile || state.focused !== 'search') {
|
|
844
|
+
return state;
|
|
845
|
+
}
|
|
846
|
+
return Object.assign(Object.assign({}, state), { focused: 'none' });
|
|
847
|
+
}
|
|
848
|
+
case ActionTypes$1.FocusInputLocation: {
|
|
849
|
+
const nextState = Object.assign(Object.assign({}, state), { focused: 'location' });
|
|
850
|
+
if (((_a = state.selectedLocation) === null || _a === void 0 ? void 0 : _a.id) === constants.ID_OPTION_CURRENT_LOCATION) {
|
|
851
|
+
nextState.searchLocationKeywords = '';
|
|
852
|
+
}
|
|
853
|
+
return nextState;
|
|
854
|
+
}
|
|
855
|
+
case ActionTypes$1.FocusInputSearch:
|
|
856
|
+
const nextState = Object.assign(Object.assign({}, state), { focused: 'search' });
|
|
857
|
+
if (state.isMobile) {
|
|
858
|
+
return resetSearchLocationKeywords$1(nextState);
|
|
859
|
+
}
|
|
860
|
+
return nextState;
|
|
861
|
+
case ActionTypes$1.ChangeInputLocation:
|
|
862
|
+
return Object.assign(Object.assign({}, state), { searchLocationKeywords: action.payload });
|
|
863
|
+
case ActionTypes$1.ChangeInputSearch: {
|
|
864
|
+
const keyword = action.payload;
|
|
865
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: keyword, isLoadingSearchResults: keyword.trim().length > SEARCH_KEYWORD_MIN_LENGTH$1[state.locale] });
|
|
866
|
+
}
|
|
867
|
+
case ActionTypes$1.SelectCurrentLocation:
|
|
868
|
+
return Object.assign(Object.assign({}, state), { focused: 'none', selectedLocation: action.payload, searchLocationKeywords: action.payload.name });
|
|
869
|
+
case ActionTypes$1.ClearInputLocation:
|
|
870
|
+
return Object.assign(Object.assign({}, state), { focused: 'location', cities: state.initialCities, searchLocationKeywords: '' });
|
|
871
|
+
case ActionTypes$1.ClearInputSearch:
|
|
872
|
+
return Object.assign(Object.assign({}, state), { focused: 'search', searchKeywords: '' });
|
|
873
|
+
case ActionTypes$1.SelectLocation:
|
|
874
|
+
return Object.assign(Object.assign({}, state), { focused: 'none', selectedLocation: action.payload, searchLocationKeywords: action.payload.name });
|
|
875
|
+
case ActionTypes$1.SelectSearchResult:
|
|
876
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: action.payload.name, isMobileModalOpened: false, focused: 'none', navigateTo: action.payload.url });
|
|
877
|
+
case ActionTypes$1.FetchCitiesStart:
|
|
878
|
+
return Object.assign(Object.assign({}, state), { isLoadingCities: true });
|
|
879
|
+
case ActionTypes$1.FetchCitiesFinish:
|
|
880
|
+
return Object.assign(Object.assign({}, state), { isLoadingCities: false });
|
|
881
|
+
case ActionTypes$1.FetchSearchResultsStart:
|
|
882
|
+
return Object.assign(Object.assign({}, state), { isLoadingSearchResults: true });
|
|
883
|
+
case ActionTypes$1.FetchSearchResultsFinish:
|
|
884
|
+
return Object.assign(Object.assign({}, state), { isLoadingSearchResults: false });
|
|
885
|
+
case ActionTypes$1.FetchSearchResultsComplete: {
|
|
886
|
+
const nextState = Object.assign(Object.assign({}, state), { searchResults: action.payload });
|
|
887
|
+
if (state.initialSearchResults.length === 0) {
|
|
888
|
+
nextState.initialSearchResults = action.payload;
|
|
889
|
+
}
|
|
890
|
+
return nextState;
|
|
891
|
+
}
|
|
892
|
+
case ActionTypes$1.FetchCitiesByGeoIpComplete: {
|
|
893
|
+
let { cities } = action.payload;
|
|
894
|
+
const { default: defaultCity } = action.payload;
|
|
895
|
+
cities = cities.filter((c) => c.id !== defaultCity.id);
|
|
896
|
+
cities.unshift(defaultCity);
|
|
897
|
+
if (state.initialSelectedCity &&
|
|
898
|
+
!cities.find((c) => c.id === state.initialSelectedCity.id)) {
|
|
899
|
+
cities.unshift(state.initialSelectedCity);
|
|
900
|
+
}
|
|
901
|
+
const nextState = Object.assign(Object.assign({}, state), { defaultCity, initialCities: cities, cities });
|
|
902
|
+
if (state.geoLocationPermission === 'denied' &&
|
|
903
|
+
!state.initialSelectedCity) {
|
|
904
|
+
nextState.selectedLocation = defaultCity;
|
|
905
|
+
nextState.searchLocationKeywords = defaultCity.name;
|
|
906
|
+
}
|
|
907
|
+
return nextState;
|
|
908
|
+
}
|
|
909
|
+
case ActionTypes$1.FetchCitiesByKeywordComplete:
|
|
910
|
+
return Object.assign(Object.assign({}, state), { cities: action.payload });
|
|
911
|
+
case ActionTypes$1.DisplayInitialCities:
|
|
912
|
+
return Object.assign(Object.assign({}, state), { cities: state.initialCities });
|
|
913
|
+
case ActionTypes$1.DisplayInitialSearchResults:
|
|
914
|
+
return Object.assign(Object.assign({}, state), { searchResults: state.initialSearchResults, isLoadingSearchResults: false });
|
|
915
|
+
case ActionTypes$1.GrantGeoLocationPermission:
|
|
916
|
+
return Object.assign(Object.assign({}, state), { geoLocationPermission: 'granted', geoLocationCoordinates: action.payload });
|
|
917
|
+
case ActionTypes$1.DenyGeoLocationPermission:
|
|
918
|
+
return Object.assign(Object.assign({}, state), { geoLocationPermission: 'denied', geoLocationCoordinates: null });
|
|
919
|
+
case ActionTypes$1.OpenMobileModal:
|
|
920
|
+
return Object.assign(Object.assign({}, state), { isMobileModalOpened: true });
|
|
921
|
+
case ActionTypes$1.CloseMobileModal:
|
|
922
|
+
return Object.assign(Object.assign({}, state), { isMobileModalOpened: false });
|
|
923
|
+
case ActionTypes$1.UpdateInitialSearchValue:
|
|
924
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: action.payload });
|
|
925
|
+
case ActionTypes$1.SetInputSearchPlaceholder:
|
|
926
|
+
return Object.assign(Object.assign({}, state), { inputSearchPlaceholder: action.payload });
|
|
927
|
+
default:
|
|
928
|
+
return state;
|
|
929
|
+
}
|
|
930
|
+
}
|
|
931
|
+
|
|
932
|
+
const StyledSearchBarInputsWrapper = styled__default["default"].div `
|
|
933
|
+
display: flex;
|
|
934
|
+
gap: 16px;
|
|
935
|
+
${utils.MediaQueries.mbDown} {
|
|
936
|
+
flex-direction: column;
|
|
937
|
+
padding: 14px;
|
|
938
|
+
background-color: ${theme.theme.colors.primary50};
|
|
939
|
+
|
|
940
|
+
input {
|
|
941
|
+
filter: drop-shadow(0px 4px 8px rgba(0, 0, 0, 0.04))
|
|
942
|
+
drop-shadow(0px 0px 2px rgba(0, 0, 0, 0.06))
|
|
943
|
+
drop-shadow(0px 0px 1px rgba(0, 0, 0, 0.04));
|
|
944
|
+
}
|
|
945
|
+
}
|
|
946
|
+
|
|
947
|
+
input {
|
|
948
|
+
background-color: white;
|
|
949
|
+
}
|
|
950
|
+
`;
|
|
951
|
+
const StyledInputWrapper = styled__default["default"].div `
|
|
952
|
+
position: relative;
|
|
953
|
+
`;
|
|
954
|
+
const StyledInputLocationWrapper = styled__default["default"](StyledInputWrapper) `
|
|
955
|
+
flex: 1;
|
|
956
|
+
`;
|
|
957
|
+
const StyledInputSearchWrapper = styled__default["default"](StyledInputWrapper) `
|
|
958
|
+
flex: 2;
|
|
959
|
+
`;
|
|
960
|
+
const StyledClearIcon = styled__default["default"](ClearIcon) `
|
|
961
|
+
display: none;
|
|
962
|
+
&.shown {
|
|
963
|
+
display: block;
|
|
964
|
+
}
|
|
965
|
+
`;
|
|
966
|
+
|
|
967
|
+
const SearchIcon = () => (React__default["default"].createElement("svg", { width: "18", height: "18", viewBox: "0 0 18 18" },
|
|
968
|
+
React__default["default"].createElement("path", { fillRule: "evenodd", clipRule: "evenodd", d: "M2.97887 8.15493C2.97887 5.29627 5.29627 2.97887 8.15493 2.97887C11.0136 2.97887 13.331 5.29627 13.331 8.15493C13.331 11.0136 11.0136 13.331 8.15493 13.331C5.29627 13.331 2.97887 11.0136 2.97887 8.15493ZM8.15493 1.5C4.47951 1.5 1.5 4.47951 1.5 8.15493C1.5 11.8303 4.47951 14.8099 8.15493 14.8099C9.72624 14.8099 11.1704 14.2653 12.3089 13.3546L15.2377 16.2834C15.5265 16.5722 15.9947 16.5722 16.2834 16.2834C16.5722 15.9947 16.5722 15.5265 16.2834 15.2377L13.3546 12.3089C14.2653 11.1704 14.8099 9.72624 14.8099 8.15493C14.8099 4.47951 11.8303 1.5 8.15493 1.5Z", fill: "white" })));
|
|
969
|
+
const StyledSearchIcon = styled__default["default"].button `
|
|
970
|
+
min-height: 100%;
|
|
971
|
+
border-radius: 6px;
|
|
972
|
+
background-color: ${theme.theme.colors.primaryBase};
|
|
973
|
+
display: flex;
|
|
974
|
+
justify-content: center;
|
|
975
|
+
align-items: center;
|
|
976
|
+
gap: 11px;
|
|
977
|
+
cursor: pointer;
|
|
978
|
+
flex: 0.3;
|
|
979
|
+
|
|
980
|
+
${utils.MediaQueries.mbDown} {
|
|
981
|
+
--margin: 16px;
|
|
982
|
+
min-height: 44px;
|
|
983
|
+
margin: var(--margin);
|
|
984
|
+
width: calc(100% - var(--margin) * 2);
|
|
985
|
+
position: absolute;
|
|
986
|
+
bottom: 0;
|
|
987
|
+
}
|
|
988
|
+
|
|
989
|
+
&:hover {
|
|
990
|
+
background-color: ${theme.theme.colors.primaryHover};
|
|
991
|
+
}
|
|
992
|
+
|
|
993
|
+
&:active {
|
|
994
|
+
background-color: ${theme.theme.colors.primaryActive};
|
|
995
|
+
}
|
|
996
|
+
|
|
997
|
+
&:focus-visible {
|
|
998
|
+
outline: 1px solid black;
|
|
999
|
+
}
|
|
1000
|
+
`;
|
|
1001
|
+
const StyledText$1 = styled__default["default"](index$2.Text) `
|
|
1002
|
+
font-weight: ${theme.theme.sizes.fwSemiBold};
|
|
1003
|
+
`;
|
|
1004
|
+
const SearchButton = ({ onClick }) => {
|
|
1005
|
+
const { t } = useTranslations.useTranslations();
|
|
1006
|
+
const title = t('booking.searchBar.searchButton');
|
|
1007
|
+
return (React__default["default"].createElement(StyledSearchIcon, { onClick: onClick, title: title },
|
|
1008
|
+
React__default["default"].createElement(SearchIcon, null),
|
|
1009
|
+
React__default["default"].createElement(StyledText$1, { size: "s3", color: "white" }, title)));
|
|
1010
|
+
};
|
|
1011
|
+
|
|
1012
|
+
function SearchInputs$1({ isMobile, state, dispatch, debouncedFetchCitiesByKeyword, debouncedFetchSearchResults, focusLocationInput, focusSearchInput, renderLocationResults, renderSearchResults, locationTrackingAttributes, trackingAttributes, onSearch, initalSearchValue, }) {
|
|
1013
|
+
const inputLocationWrapperRef = React.useRef(null);
|
|
1014
|
+
const inputSearchWrapperRef = React.useRef(null);
|
|
1015
|
+
const { focused, searchLocationKeywords, geoLocationPermission, selectedLocation, searchKeywords, inputSearchPlaceholder, } = state;
|
|
1016
|
+
const { t } = useTranslations.useTranslations();
|
|
1017
|
+
useAnimatedPlaceholder({
|
|
1018
|
+
wrapperRef: inputSearchWrapperRef,
|
|
1019
|
+
disabled: !!inputSearchPlaceholder,
|
|
1020
|
+
});
|
|
1021
|
+
useOutsideClick.useOutsideClick(inputLocationWrapperRef, () => {
|
|
1022
|
+
if (!isMobile) {
|
|
1023
|
+
dispatch({ type: ActionTypes$1.ClickOutsideInputLocation });
|
|
1024
|
+
}
|
|
1025
|
+
});
|
|
1026
|
+
useOutsideClick.useOutsideClick(inputSearchWrapperRef, () => {
|
|
1027
|
+
if (!isMobile) {
|
|
1028
|
+
dispatch({ type: ActionTypes$1.ClickOutsideInputSearch });
|
|
1029
|
+
}
|
|
1030
|
+
});
|
|
1031
|
+
function handleLocationInputClear() {
|
|
1032
|
+
dispatch({ type: ActionTypes$1.ClearInputLocation });
|
|
1033
|
+
debouncedFetchCitiesByKeyword.cancel();
|
|
1034
|
+
focusLocationInput();
|
|
1035
|
+
}
|
|
1036
|
+
function handleSearchInputClear() {
|
|
1037
|
+
dispatch({ type: ActionTypes$1.ClearInputSearch });
|
|
1038
|
+
debouncedFetchSearchResults.cancel();
|
|
1039
|
+
debouncedFetchSearchResults('', state);
|
|
1040
|
+
focusSearchInput();
|
|
1041
|
+
}
|
|
1042
|
+
const searchInputPinIconColor = React.useMemo(() => {
|
|
1043
|
+
if (geoLocationPermission === 'granted' &&
|
|
1044
|
+
(selectedLocation === null || selectedLocation === void 0 ? void 0 : selectedLocation.id) === constants.ID_OPTION_CURRENT_LOCATION) {
|
|
1045
|
+
return theme.theme.colors.primaryBase;
|
|
1046
|
+
}
|
|
1047
|
+
else {
|
|
1048
|
+
return theme.theme.colors.gray400;
|
|
1049
|
+
}
|
|
1050
|
+
}, [geoLocationPermission, selectedLocation]);
|
|
1051
|
+
const handleSearchInputChange = React.useCallback(function handleSearchInputChange(value) {
|
|
1052
|
+
dispatch({ type: ActionTypes$1.ChangeInputSearch, payload: value });
|
|
1053
|
+
if (typeof onSearch === 'function') {
|
|
1054
|
+
return;
|
|
1055
|
+
}
|
|
1056
|
+
if (value.trim().length > SEARCH_KEYWORD_MIN_LENGTH$1[state.locale] ||
|
|
1057
|
+
initalSearchValue) {
|
|
1058
|
+
debouncedFetchSearchResults(value.trim(), state);
|
|
1059
|
+
}
|
|
1060
|
+
else {
|
|
1061
|
+
debouncedFetchSearchResults.cancel();
|
|
1062
|
+
dispatch({ type: ActionTypes$1.DisplayInitialSearchResults });
|
|
1063
|
+
}
|
|
1064
|
+
}, [dispatch, state]);
|
|
1065
|
+
const handleSearchLocationInputChange = React.useCallback(function handleSearchLocationInputChange(value) {
|
|
1066
|
+
dispatch({ type: ActionTypes$1.ChangeInputLocation, payload: value });
|
|
1067
|
+
if (value.trim().length > SEARCH_KEYWORD_MIN_LENGTH$1[state.locale]) {
|
|
1068
|
+
debouncedFetchCitiesByKeyword(value.trim());
|
|
1069
|
+
}
|
|
1070
|
+
else {
|
|
1071
|
+
debouncedFetchCitiesByKeyword.cancel();
|
|
1072
|
+
dispatch({ type: ActionTypes$1.DisplayInitialCities });
|
|
1073
|
+
}
|
|
1074
|
+
}, [debouncedFetchCitiesByKeyword, dispatch]);
|
|
1075
|
+
const handleKeyPress = (e) => {
|
|
1076
|
+
if (state.autoCompleteDisabled && e.key === 'Enter' && onSearch) {
|
|
1077
|
+
onSearch({
|
|
1078
|
+
cityId: state.selectedLocation.id,
|
|
1079
|
+
keyword: searchKeywords,
|
|
1080
|
+
});
|
|
1081
|
+
}
|
|
1082
|
+
};
|
|
1083
|
+
return (React__default["default"].createElement(StyledSearchBarInputsWrapper, null,
|
|
1084
|
+
React__default["default"].createElement(StyledInputLocationWrapper, { ref: inputLocationWrapperRef },
|
|
1085
|
+
React__default["default"].createElement(StyledInput, { inputClassName: focused === 'location' ? 'focused' : undefined, placeholder: t('booking.searchBar.locationPlaceholder'), autoComplete: "off", name: "search-location", displayIcon: React__default["default"].createElement(PinIcon, { className: "location-pin-icon", color: searchInputPinIconColor }), actionIcon: React__default["default"].createElement(StyledClearIcon, { color: theme.theme.colors.gray300, className: searchLocationKeywords !== '' ? 'shown' : '' }), onActionClick: handleLocationInputClear, value: searchLocationKeywords, onChange: handleSearchLocationInputChange, onFocus: () => dispatch({ type: ActionTypes$1.FocusInputLocation }), size: "md", trackingAttributes: locationTrackingAttributes }),
|
|
1086
|
+
!isMobile && renderLocationResults()),
|
|
1087
|
+
React__default["default"].createElement(StyledInputSearchWrapper, { ref: inputSearchWrapperRef },
|
|
1088
|
+
React__default["default"].createElement(StyledInput, { placeholder: inputSearchPlaceholder ||
|
|
1089
|
+
t('booking.searchBar.searchInput.placeholder'), autoComplete: "off", name: "search-results", actionIcon: React__default["default"].createElement(StyledClearIcon, { color: theme.theme.colors.gray300, className: searchKeywords !== '' ? 'shown' : '' }), onActionClick: handleSearchInputClear, value: searchKeywords, onChange: handleSearchInputChange, onFocus: () => dispatch({ type: ActionTypes$1.FocusInputSearch }), inputClassName: focused === 'search' ? 'focused' : undefined, size: "md", trackingAttributes: trackingAttributes, onKeyPress: handleKeyPress, enterKeyHint: state.autoCompleteDisabled ? 'search' : undefined }),
|
|
1090
|
+
!isMobile && renderSearchResults()),
|
|
1091
|
+
state.autoCompleteDisabled && !state.isMobile && (React__default["default"].createElement(SearchButton, { onClick: () => {
|
|
1092
|
+
onSearch({
|
|
1093
|
+
cityId: state.selectedLocation.id,
|
|
1094
|
+
keyword: searchKeywords,
|
|
1095
|
+
});
|
|
1096
|
+
} }))));
|
|
1097
|
+
}
|
|
1098
|
+
|
|
1099
|
+
const DoctorIcon$1 = () => (React__default["default"].createElement("svg", { width: "14", height: "18", viewBox: "0 0 14 18" },
|
|
1100
|
+
React__default["default"].createElement("path", { d: "M7.00004 0.666992C5.29757 0.666992 3.64067 0.813476 2.52087 1.03158C1.73311 1.18457 1.16671 1.86816 1.16671 2.6722V4.83366C1.16671 5.29264 1.54106 5.66699 2.00004 5.66699H12C12.459 5.66699 12.8334 5.29264 12.8334 4.83366V2.69824C12.8334 1.89421 12.267 1.21061 11.4792 1.05762C10.3562 0.839518 8.69275 0.666992 7.00004 0.666992ZM6.16671 1.50033H7.83337V2.33366H8.66671V4.00033H7.83337V4.83366H6.16671V4.00033H5.33337V2.33366H6.16671V1.50033ZM1.42712 6.50033C1.3197 6.89421 1.24158 7.32389 1.19275 7.77637C1.14718 8.18001 1.05603 9.25423 1.06254 9.36491C0.603556 9.72624 0.333374 10.2861 0.333374 10.9014C0.333374 11.8356 0.977906 12.6364 1.84379 12.8285C2.74548 15.0192 4.55212 17.3337 7.00004 17.3337C9.44796 17.3337 11.2546 14.9964 12.1563 12.8024C13.0222 12.6136 13.6667 11.8356 13.6667 10.9014C13.6667 10.2861 13.3965 9.72624 12.9375 9.36491C12.9441 9.25423 12.8562 8.16048 12.8073 7.75033C12.7552 7.30436 12.6804 6.89095 12.573 6.50033H5.35942C6.52804 8.20606 9.27543 7.18717 11.0365 7.62012C11.5736 8.79199 11.1667 10.4326 11.1667 10.4326L11.8177 10.641C11.9121 10.6702 12 10.7549 12 10.9014C12 11.0576 11.8861 11.1943 11.6875 11.1878L11.0105 11.0837L10.7761 11.7347C9.96554 14.0492 8.4128 15.667 7.00004 15.667C5.58728 15.667 4.03455 14.0492 3.224 11.7347L2.96358 11.0837L2.26046 11.1878C2.11723 11.1878 2.00004 11.0576 2.00004 10.9014C2.00004 10.7549 2.08793 10.6702 2.18233 10.641L2.83337 10.4326C2.73246 10.5531 2.4102 8.7041 2.83337 8.03678C3.59184 7.5127 4.2266 7.87728 5.12504 6.50033H1.42712ZM5.17712 9.05241C4.57166 9.05241 4.08337 9.55371 4.08337 10.1722C4.08337 10.7907 4.57166 11.292 5.17712 11.292C5.78259 11.292 6.27087 10.7907 6.27087 10.1722C6.27087 9.55371 5.78259 9.05241 5.17712 9.05241ZM8.82296 9.05241C8.21749 9.05241 7.72921 9.55371 7.72921 10.1722C7.72921 10.7907 8.21749 11.292 8.82296 11.292C9.42843 11.292 9.91671 10.7907 9.91671 10.1722C9.91671 9.55371 9.42843 9.05241 8.82296 9.05241Z", fill: "#9AA2AC" })));
|
|
1101
|
+
const ServiceIcon$1 = () => (React__default["default"].createElement("svg", { width: "18", height: "18", viewBox: "0 0 18 18" },
|
|
1102
|
+
React__default["default"].createElement("path", { d: "M8.99996 0.666992C6.27535 0.666992 3.85348 1.97884 2.33329 4.00033H4.59892C5.80009 2.94564 7.36259 2.33366 8.99996 2.33366C10.6373 2.33366 12.1998 2.94564 13.401 4.00033H15.6666C14.1464 1.97884 11.7246 0.666992 8.99996 0.666992ZM1.78642 4.83366C1.07678 7.04069 0.666626 9.59928 0.666626 12.3337C0.666626 14.085 0.826131 15.7679 1.13538 17.3337H16.8645C17.1738 15.7679 17.3333 14.085 17.3333 12.3337C17.3333 9.59928 16.9231 7.04069 16.2135 4.83366H1.78642ZM8.99996 7.33366C11.3014 7.33366 13.1666 9.19889 13.1666 11.5003C13.1666 13.8018 11.3014 15.667 8.99996 15.667C6.69853 15.667 4.83329 13.8018 4.83329 11.5003C4.83329 9.19889 6.69853 7.33366 8.99996 7.33366ZM8.16663 9.00033V10.667H6.49996V12.3337H8.16663V14.0003H9.83329V12.3337H11.5V10.667H9.83329V9.00033H8.16663Z", fill: "#9AA2AC" })));
|
|
1103
|
+
const HospitalIcon$1 = () => (React__default["default"].createElement("svg", { width: "16", height: "17", viewBox: "0 0 16 17" },
|
|
1104
|
+
React__default["default"].createElement("path", { d: "M8 0.666992L0.5 5.63533V14.8337C0.5 15.7545 1.24583 16.5003 2.16667 16.5003H13.8333C14.7542 16.5003 15.5 15.7545 15.5 14.8337V5.63533L8 0.666992ZM11.3333 10.667H8.83333V13.167H7.16667V10.667H4.66667V9.00033H7.16667V6.50033H8.83333V9.00033H11.3333V10.667Z", fill: "#9AA2AC" })));
|
|
1105
|
+
const SpecialtyIcon$1 = () => (React__default["default"].createElement("svg", { width: "16", height: "16", viewBox: "0 0 16 16" },
|
|
1106
|
+
React__default["default"].createElement("path", { d: "M3.83333 0.5C2.94928 0.5 2.10143 0.851189 1.47631 1.47631C0.851189 2.10143 0.5 2.94928 0.5 3.83333C0.5 4.71739 0.851189 5.56523 1.47631 6.19036C2.10143 6.81548 2.94928 7.16667 3.83333 7.16667C4.71739 7.16667 5.56523 6.81548 6.19036 6.19036C6.81548 5.56523 7.16667 4.71739 7.16667 3.83333C7.16667 2.94928 6.81548 2.10143 6.19036 1.47631C5.56523 0.851189 4.71739 0.5 3.83333 0.5V0.5ZM10.5 0.5C9.57917 0.5 8.83333 1.24583 8.83333 2.16667V5.5C8.83333 6.42083 9.57917 7.16667 10.5 7.16667H13.8333C14.7542 7.16667 15.5 6.42083 15.5 5.5V2.16667C15.5 1.24583 14.7542 0.5 13.8333 0.5H10.5ZM3.83333 8.83333C2.94928 8.83333 2.10143 9.18452 1.47631 9.80964C0.851189 10.4348 0.5 11.2826 0.5 12.1667C0.5 13.0507 0.851189 13.8986 1.47631 14.5237C2.10143 15.1488 2.94928 15.5 3.83333 15.5C4.71739 15.5 5.56523 15.1488 6.19036 14.5237C6.81548 13.8986 7.16667 13.0507 7.16667 12.1667C7.16667 11.2826 6.81548 10.4348 6.19036 9.80964C5.56523 9.18452 4.71739 8.83333 3.83333 8.83333V8.83333ZM12.1667 8.83333C11.2826 8.83333 10.4348 9.18452 9.80964 9.80964C9.18452 10.4348 8.83333 11.2826 8.83333 12.1667C8.83333 13.0507 9.18452 13.8986 9.80964 14.5237C10.4348 15.1488 11.2826 15.5 12.1667 15.5C13.0507 15.5 13.8986 15.1488 14.5237 14.5237C15.1488 13.8986 15.5 13.0507 15.5 12.1667C15.5 11.2826 15.1488 10.4348 14.5237 9.80964C13.8986 9.18452 13.0507 8.83333 12.1667 8.83333V8.83333Z", fill: "#9AA2AC" })));
|
|
1107
|
+
|
|
1108
|
+
const StyledTypeHeader = styled__default["default"].header `
|
|
1109
|
+
display: flex;
|
|
1110
|
+
justify-content: space-between;
|
|
1111
|
+
padding: 12px 24px;
|
|
1112
|
+
background-color: ${theme.theme.colors.neutral50};
|
|
1113
|
+
box-shadow: inset 0px 1px 0px #e4e8ec;
|
|
1114
|
+
`;
|
|
1115
|
+
const StyledInfoWrapper = styled__default["default"].div `
|
|
1116
|
+
display: grid;
|
|
1117
|
+
flex: 2;
|
|
1118
|
+
align-items: center;
|
|
1119
|
+
gap: 16px;
|
|
1120
|
+
grid-template-columns: 16px 1fr;
|
|
1121
|
+
`;
|
|
1122
|
+
const StyledTypeName = styled__default["default"].p `
|
|
1123
|
+
color: ${theme.theme.colors.neutral800};
|
|
1124
|
+
font-size: 14px;
|
|
1125
|
+
font-weight: ${theme.theme.sizes.fwSemiBold};
|
|
1126
|
+
letter-spacing: -0.2px;
|
|
1127
|
+
line-height: 22px;
|
|
1128
|
+
`;
|
|
1129
|
+
const StyledSeeMoreButton = styled__default["default"].button `
|
|
1130
|
+
flex: 1;
|
|
1131
|
+
cursor: pointer;
|
|
1132
|
+
text-align: end;
|
|
1133
|
+
`;
|
|
1134
|
+
const StyledResultsContainer = styled__default["default"].section `
|
|
1135
|
+
padding: 12px 16px;
|
|
1136
|
+
--rowGap: 16px;
|
|
1137
|
+
--graphicSize: 32px;
|
|
1138
|
+
|
|
1139
|
+
${utils.MediaQueries.tdUp} {
|
|
1140
|
+
--rowGap: 8px;
|
|
1141
|
+
}
|
|
1142
|
+
`;
|
|
1143
|
+
const StyledItemsWrapper = styled__default["default"].ul `
|
|
1144
|
+
--gap: 16px;
|
|
1145
|
+
${utils.MediaQueries.tdUp} {
|
|
1146
|
+
--gap: 8px;
|
|
1147
|
+
}
|
|
1148
|
+
|
|
1149
|
+
display: grid;
|
|
1150
|
+
overflow: hidden;
|
|
1151
|
+
gap: var(--gap);
|
|
1152
|
+
transition: max-height 0.8s ease-out;
|
|
1153
|
+
|
|
1154
|
+
${({ isMore }) => isMore &&
|
|
1155
|
+
`
|
|
1156
|
+
height: auto;
|
|
1157
|
+
max-height: 0;
|
|
1158
|
+
margin-top: var(--gap);
|
|
1159
|
+
`}
|
|
1160
|
+
|
|
1161
|
+
${({ isShown }) => isShown &&
|
|
1162
|
+
`
|
|
1163
|
+
max-height: 600px;
|
|
1164
|
+
`}
|
|
1165
|
+
|
|
1166
|
+
@media (prefers-reduced-motion) {
|
|
1167
|
+
transition: none;
|
|
1168
|
+
}
|
|
1169
|
+
|
|
1170
|
+
${utils.MediaQueries.tdUp} {
|
|
1171
|
+
grid-template-columns: 1fr 1fr;
|
|
1172
|
+
}
|
|
1173
|
+
`;
|
|
1174
|
+
const StyledSeeMore = styled__default["default"](index$2.Text) `
|
|
1175
|
+
margin-top: 12px;
|
|
1176
|
+
margin-bottom: 8px;
|
|
1177
|
+
cursor: pointer;
|
|
1178
|
+
text-align: start;
|
|
1179
|
+
text-transform: capitalize;
|
|
1180
|
+
`;
|
|
1181
|
+
|
|
1182
|
+
const StyledResult = styled__default["default"].li `
|
|
1183
|
+
display: flex;
|
|
1184
|
+
align-items: center;
|
|
1185
|
+
gap: var(--rowGap);
|
|
1186
|
+
cursor: pointer;
|
|
1187
|
+
&.not-nav {
|
|
1188
|
+
cursor: default;
|
|
1189
|
+
}
|
|
1190
|
+
`;
|
|
1191
|
+
const StyledRoundedIconWrapper = styled__default["default"].div `
|
|
1192
|
+
--wrapper-size: var(--graphicSize);
|
|
1193
|
+
border-radius: calc(var(--wrapper-size) / 2);
|
|
1194
|
+
background-color: var(--neutral50);
|
|
1195
|
+
width: var(--wrapper-size);
|
|
1196
|
+
height: var(--wrapper-size);
|
|
1197
|
+
aspect-ratio: 1/1;
|
|
1198
|
+
overflow: hidden;
|
|
1199
|
+
|
|
1200
|
+
${({ type }) => type &&
|
|
1201
|
+
type === 'doctors' &&
|
|
1202
|
+
`
|
|
1203
|
+
border-radius: calc(var(--graphicSize) / 2);
|
|
1204
|
+
`}
|
|
1205
|
+
|
|
1206
|
+
img {
|
|
1207
|
+
width: var(--graphicSize);
|
|
1208
|
+
height: var(--graphicSize);
|
|
1209
|
+
${({ type }) => type && type === 'doctors'
|
|
1210
|
+
? `
|
|
1211
|
+
|
|
1212
|
+
object-fit: cover;
|
|
1213
|
+
`
|
|
1214
|
+
: `
|
|
1215
|
+
object-fit: contain;
|
|
1216
|
+
`}
|
|
1217
|
+
}
|
|
1218
|
+
|
|
1219
|
+
&:focus-visible {
|
|
1220
|
+
outline: 1px solid ${theme.theme.colors.gray600};
|
|
1221
|
+
}
|
|
1222
|
+
`;
|
|
1223
|
+
const StyledText = styled__default["default"](index$2.Text) `
|
|
1224
|
+
line-height: 22px;
|
|
1225
|
+
letter-spacing: -0.2px;
|
|
1226
|
+
|
|
1227
|
+
${utils.MediaQueries.tdUp} {
|
|
1228
|
+
&[data-size='p3'] {
|
|
1229
|
+
font-size: 14px;
|
|
1230
|
+
}
|
|
1231
|
+
}
|
|
1232
|
+
`;
|
|
1233
|
+
const StyledPictureWrapper = styled__default["default"].figure `
|
|
1234
|
+
max-width: var(--graphicSize);
|
|
1235
|
+
min-width: var(--graphicSize);
|
|
1236
|
+
`;
|
|
1237
|
+
const StyledLocationPin = styled__default["default"].svg `
|
|
1238
|
+
margin: 0 auto;
|
|
1239
|
+
display: block;
|
|
1240
|
+
`;
|
|
1241
|
+
const StyledImageSkeletonWrapper = styled__default["default"].div `
|
|
1242
|
+
display: grid;
|
|
1243
|
+
place-items: center;
|
|
1244
|
+
`;
|
|
1245
|
+
|
|
1246
|
+
const defaultThumbnailByType = {
|
|
1247
|
+
doctors: DefaultThumbnailDoctor,
|
|
1248
|
+
services: DefaultThumbnailService,
|
|
1249
|
+
};
|
|
1250
|
+
const ResultSectionItem = ({ type, item, imageUrl, className, onClickItem, }) => {
|
|
1251
|
+
const onKeyDown = (e) => {
|
|
1252
|
+
if (e.key === 'Enter' || e.key === 'Space') {
|
|
1253
|
+
if (onClickItem) {
|
|
1254
|
+
onClickItem(item);
|
|
1255
|
+
}
|
|
1256
|
+
}
|
|
1257
|
+
};
|
|
1258
|
+
const defaultThumbnail = React.useMemo(() => {
|
|
1259
|
+
const Cmp = defaultThumbnailByType[type] || DefaultThumbnailAny;
|
|
1260
|
+
return React__default["default"].createElement(Cmp, { width: 32, height: type === 'services' ? 32 : 24 });
|
|
1261
|
+
}, [type]);
|
|
1262
|
+
return (React__default["default"].createElement(StyledResult, { onClick: () => onClickItem && onClickItem(item), onKeyDown: onKeyDown, tabIndex: 0, role: "button", className: className },
|
|
1263
|
+
React__default["default"].createElement(StyledPictureWrapper, null, type === 'hospitals' ? (React__default["default"].createElement(StyledLocationPin, { width: "12", height: "16", viewBox: "0 0 12 16" },
|
|
1264
|
+
React__default["default"].createElement("path", { fillRule: "evenodd", clipRule: "evenodd", d: "M0.75 5.94873C0.75 3.04623 3.0975 0.69873 6 0.69873C8.9025 0.69873 11.25 3.04623 11.25 5.94873C11.25 9.07623 7.935 13.3887 6.5775 15.0312C6.2775 15.3912 5.73 15.3912 5.43 15.0312C4.065 13.3887 0.75 9.07623 0.75 5.94873ZM4.125 5.94873C4.125 6.98373 4.965 7.82373 6 7.82373C7.035 7.82373 7.875 6.98373 7.875 5.94873C7.875 4.91373 7.035 4.07373 6 4.07373C4.965 4.07373 4.125 4.91373 4.125 5.94873Z", fill: "#9AA2AC" }))) : (React__default["default"].createElement(StyledRoundedIconWrapper, { type: type }, imageUrl ? (React__default["default"].createElement("img", { src: imageUrl, width: 32, height: type === 'services' ? 32 : 24, loading: "lazy" })) : (defaultThumbnail)))),
|
|
1265
|
+
React__default["default"].createElement(StyledText, { color: theme.theme.colors.gray800, size: "p3" }, item.name)));
|
|
1266
|
+
};
|
|
1267
|
+
|
|
1268
|
+
const ResultSection = ({ type, data, state, dispatch, itemsToShow, itemsToShowDesktop, isMobile, isLoading, keyword, isNavResultItem, }) => {
|
|
1269
|
+
const [seeMoreOpen, setSeeMoreOpen] = React.useState(false);
|
|
1270
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
1271
|
+
const { selectedLocation, searchKeywords } = state;
|
|
1272
|
+
const slugs = React.useMemo(() => constants.LOCALIZED_SLUGS[locale], [locale]);
|
|
1273
|
+
const isMalay = locale === 'ms-MY';
|
|
1274
|
+
const typeInformation = React.useMemo(() => {
|
|
1275
|
+
return {
|
|
1276
|
+
doctors: {
|
|
1277
|
+
name: t('booking.searchPopup.doctors'),
|
|
1278
|
+
icon: React__default["default"].createElement(DoctorIcon$1, null),
|
|
1279
|
+
slug: slugs.DOCTOR,
|
|
1280
|
+
},
|
|
1281
|
+
services: {
|
|
1282
|
+
name: t('booking.searchPopup.services'),
|
|
1283
|
+
icon: React__default["default"].createElement(ServiceIcon$1, null),
|
|
1284
|
+
slug: slugs.SERVICE,
|
|
1285
|
+
},
|
|
1286
|
+
hospitals: {
|
|
1287
|
+
name: t('booking.searchPopup.hospitals'),
|
|
1288
|
+
icon: React__default["default"].createElement(HospitalIcon$1, null),
|
|
1289
|
+
slug: slugs.HOSPITAL,
|
|
1290
|
+
},
|
|
1291
|
+
specialties: {
|
|
1292
|
+
name: t('booking.searchPopup.specialties'),
|
|
1293
|
+
icon: React__default["default"].createElement(SpecialtyIcon$1, null),
|
|
1294
|
+
slug: slugs.SPECIALTIES,
|
|
1295
|
+
},
|
|
1296
|
+
};
|
|
1297
|
+
}, [type, slugs]);
|
|
1298
|
+
const typeSlug = React.useMemo(() => typeInformation[type].slug, [typeInformation]);
|
|
1299
|
+
const showItemCount = isMobile ? itemsToShow : itemsToShowDesktop;
|
|
1300
|
+
function onClickItem(item) {
|
|
1301
|
+
let url = '';
|
|
1302
|
+
switch (type) {
|
|
1303
|
+
case 'specialties':
|
|
1304
|
+
url = `/${selectedLocation.slug}/${typeInformation.doctors.slug}/${item.slug}`;
|
|
1305
|
+
break;
|
|
1306
|
+
case 'services':
|
|
1307
|
+
url = `/${selectedLocation.slug}/${typeSlug}/${item.slug}`;
|
|
1308
|
+
break;
|
|
1309
|
+
case 'doctors':
|
|
1310
|
+
case 'hospitals':
|
|
1311
|
+
url = `/${typeSlug}/${item.slug}-${item.id}`;
|
|
1312
|
+
break;
|
|
1313
|
+
}
|
|
1314
|
+
if (url) {
|
|
1315
|
+
dispatch({
|
|
1316
|
+
type: ActionTypes$1.SelectSearchResult,
|
|
1317
|
+
payload: { name: item.name, url },
|
|
1318
|
+
});
|
|
1319
|
+
}
|
|
1320
|
+
}
|
|
1321
|
+
function renderItem(item) {
|
|
1322
|
+
return (React__default["default"].createElement(ResultSectionItem, { key: item.id, item: item, type: type, imageUrl: item.logo || item.avatar || item.thumbnail, className: !isNavResultItem ? 'not-nav' : '', onClickItem: isNavResultItem && onClickItem }));
|
|
1323
|
+
}
|
|
1324
|
+
function onSeeAllClick() {
|
|
1325
|
+
let url = '';
|
|
1326
|
+
switch (type) {
|
|
1327
|
+
case 'specialties':
|
|
1328
|
+
url = `/${typeSlug}`;
|
|
1329
|
+
break;
|
|
1330
|
+
case 'services':
|
|
1331
|
+
case 'doctors':
|
|
1332
|
+
case 'hospitals':
|
|
1333
|
+
url = `/${selectedLocation.slug}/${typeSlug}`;
|
|
1334
|
+
break;
|
|
1335
|
+
}
|
|
1336
|
+
if (url) {
|
|
1337
|
+
dispatch({ type: ActionTypes$1.NavigateTo, payload: url });
|
|
1338
|
+
}
|
|
1339
|
+
}
|
|
1340
|
+
function onClickSearchByKeyword() {
|
|
1341
|
+
const { slug: typeSlug } = typeInformation[type];
|
|
1342
|
+
const url = `/${selectedLocation.slug}/${typeSlug}?q=${searchKeywords}`;
|
|
1343
|
+
dispatch({ type: ActionTypes$1.NavigateTo, payload: url });
|
|
1344
|
+
}
|
|
1345
|
+
return (React__default["default"].createElement("section", null,
|
|
1346
|
+
React__default["default"].createElement(StyledTypeHeader, null,
|
|
1347
|
+
React__default["default"].createElement(StyledInfoWrapper, null,
|
|
1348
|
+
typeInformation[type].icon,
|
|
1349
|
+
React__default["default"].createElement(StyledTypeName, null, typeInformation[type].name)),
|
|
1350
|
+
(keyword.trim().length <= SEARCH_KEYWORD_MIN_LENGTH$1[locale] ||
|
|
1351
|
+
isMalay) && (React__default["default"].createElement(StyledSeeMoreButton, { onClick: onSeeAllClick },
|
|
1352
|
+
React__default["default"].createElement(index$2.Text, { size: "p3", color: theme.theme.colors.primaryBase }, t('booking.searchPopup.seeAll'))))),
|
|
1353
|
+
(isLoading || (data && data.length > 0)) && (React__default["default"].createElement(StyledResultsContainer, null,
|
|
1354
|
+
React__default["default"].createElement(StyledItemsWrapper, null,
|
|
1355
|
+
isLoading &&
|
|
1356
|
+
Array(2)
|
|
1357
|
+
.fill(undefined)
|
|
1358
|
+
.map((_, i) => (React__default["default"].createElement(StyledResult, { key: type + 'loading' + i },
|
|
1359
|
+
React__default["default"].createElement(StyledPictureWrapper, null,
|
|
1360
|
+
React__default["default"].createElement(StyledImageSkeletonWrapper, null,
|
|
1361
|
+
React__default["default"].createElement(Skeleton__default["default"], { height: 14, width: type === 'hospitals' ? 12 : 32, style: {
|
|
1362
|
+
maxWidth: 'var(--graphicSize)',
|
|
1363
|
+
minHeight: 'var(--graphicSize)',
|
|
1364
|
+
} }))),
|
|
1365
|
+
React__default["default"].createElement(Skeleton__default["default"], { width: 120, height: 24 })))),
|
|
1366
|
+
!isLoading &&
|
|
1367
|
+
data &&
|
|
1368
|
+
data.length > 0 &&
|
|
1369
|
+
data.slice(0, showItemCount).map(renderItem)),
|
|
1370
|
+
React__default["default"].createElement(StyledItemsWrapper, { isShown: seeMoreOpen, isMore: true }, data.slice(showItemCount, -1).map(renderItem)),
|
|
1371
|
+
type === 'specialties' &&
|
|
1372
|
+
showItemCount < data.length &&
|
|
1373
|
+
!isLoading && (React__default["default"].createElement("button", { onClick: () => setSeeMoreOpen(!seeMoreOpen) },
|
|
1374
|
+
React__default["default"].createElement(StyledSeeMore, { size: "p3", color: theme.theme.colors.primaryBase }, seeMoreOpen
|
|
1375
|
+
? t('booking.searchPopup.seeLessSpecialties')
|
|
1376
|
+
: t('booking.searchPopup.seeMoreSpecialties')))),
|
|
1377
|
+
type !== 'specialties' &&
|
|
1378
|
+
(showItemCount < data.length || isMalay) &&
|
|
1379
|
+
!isLoading &&
|
|
1380
|
+
keyword.trim().length > SEARCH_KEYWORD_MIN_LENGTH$1[locale] && (React__default["default"].createElement("button", { onClick: onClickSearchByKeyword },
|
|
1381
|
+
React__default["default"].createElement(StyledSeeMore, { size: "p3", color: theme.theme.colors.primaryBase }, t(`booking.searchPopup.searchIn.${type}`, {
|
|
1382
|
+
name: keyword,
|
|
1383
|
+
})))))),
|
|
1384
|
+
!isLoading && (data === null || data === void 0 ? void 0 : data.length) === 0 && (React__default["default"].createElement(StyledResultsContainer, null,
|
|
1385
|
+
React__default["default"].createElement(index$2.Text, { size: "sm", color: theme.theme.colors.gray400 }, t('booking.searchBar.noResults'))))));
|
|
1386
|
+
};
|
|
1387
|
+
|
|
1388
|
+
const StyledSection = styled__default["default"].section `
|
|
1389
|
+
background-color: white;
|
|
1390
|
+
border-radius: 4px;
|
|
1391
|
+
position: absolute;
|
|
1392
|
+
width: 100%;
|
|
1393
|
+
z-index: 30;
|
|
1394
|
+
|
|
1395
|
+
${utils.MediaQueries.tdUp} {
|
|
1396
|
+
box-shadow: 0px 24px 32px rgba(0, 0, 0, 0.04),
|
|
1397
|
+
0px 16px 24px rgba(0, 0, 0, 0.04), 0px 4px 8px rgba(0, 0, 0, 0.04),
|
|
1398
|
+
0px 0px 1px rgba(0, 0, 0, 0.04);
|
|
1399
|
+
}
|
|
1400
|
+
`;
|
|
1401
|
+
const SearchResults = ({ data, state, dispatch, isMobile, isLoading, keyword, hideResults, isNavResultItem, }) => {
|
|
1402
|
+
return (React__default["default"].createElement(StyledSection, null, data &&
|
|
1403
|
+
data.map((data) => {
|
|
1404
|
+
if (hideResults && hideResults.includes(data.type)) {
|
|
1405
|
+
return React__default["default"].createElement(React__default["default"].Fragment, null);
|
|
1406
|
+
}
|
|
1407
|
+
return (React__default["default"].createElement(ResultSection, { type: data.type, state: state, dispatch: dispatch, itemsToShow: 2, itemsToShowDesktop: 4, key: data.type, data: data.results, isMobile: isMobile, isLoading: isLoading, keyword: keyword, isNavResultItem: isNavResultItem }));
|
|
1408
|
+
})));
|
|
1409
|
+
};
|
|
1410
|
+
|
|
1411
|
+
const getApiPath = (path, params, locale) => {
|
|
1412
|
+
return formatString__default["default"](path, Object.assign(Object.assign({}, params), { domain: index.domainLocales[locale || 'en-PH'] }));
|
|
1413
|
+
};
|
|
1414
|
+
|
|
1415
|
+
function useSearchBarApi$1({ dispatch, careApiDomain, locale = 'vi-VN', }) {
|
|
1416
|
+
const fetchCitiesApi = React.useCallback(function fetchCitiesApi(path, params = {}) {
|
|
1417
|
+
const url = `${careApiDomain}${path}`;
|
|
1418
|
+
dispatch({ type: ActionTypes$1.FetchCitiesStart });
|
|
1419
|
+
return fetch(getApiPath(url, params, locale), { method: 'GET' })
|
|
1420
|
+
.then((res) => res.json())
|
|
1421
|
+
.then((data) => {
|
|
1422
|
+
if (data._status !== 1 || !data._data) {
|
|
1423
|
+
console.log('error loading cities', data);
|
|
1424
|
+
return Promise.reject(data);
|
|
1425
|
+
}
|
|
1426
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
1427
|
+
})
|
|
1428
|
+
.finally(() => dispatch({ type: ActionTypes$1.FetchCitiesFinish }));
|
|
1429
|
+
}, [locale]);
|
|
1430
|
+
const fetchCitiesByLocation = React.useCallback(function fetchCitiesByLocation({ coordinates }) {
|
|
1431
|
+
let params = {};
|
|
1432
|
+
const moreParams = {};
|
|
1433
|
+
if (coordinates) {
|
|
1434
|
+
params = {
|
|
1435
|
+
lat: coordinates.lat,
|
|
1436
|
+
lng: coordinates.lng,
|
|
1437
|
+
};
|
|
1438
|
+
}
|
|
1439
|
+
if (locale === 'ms-MY') {
|
|
1440
|
+
moreParams.noPaging = 1;
|
|
1441
|
+
}
|
|
1442
|
+
const requests = [
|
|
1443
|
+
fetchCitiesApi(paths.PATHS.GET_CITY_BY_IP, Object.assign(Object.assign({}, params), moreParams)),
|
|
1444
|
+
];
|
|
1445
|
+
if (locale === 'zh-TW') {
|
|
1446
|
+
requests.push(fetchCitiesApi(paths.PATHS.GET_CITIES_LIST, { noPaging: 1 }));
|
|
1447
|
+
}
|
|
1448
|
+
return Promise.all(requests)
|
|
1449
|
+
.then(([data1, data2]) => {
|
|
1450
|
+
const data = Object.assign({}, data1);
|
|
1451
|
+
if (data2) {
|
|
1452
|
+
const citiesIds = data.cities.map((c) => c.id);
|
|
1453
|
+
data.cities = data.cities.concat(data2.cities.filter((c) => !citiesIds.includes(c.id)));
|
|
1454
|
+
}
|
|
1455
|
+
dispatch({
|
|
1456
|
+
type: ActionTypes$1.FetchCitiesByGeoIpComplete,
|
|
1457
|
+
payload: data,
|
|
1458
|
+
});
|
|
1459
|
+
})
|
|
1460
|
+
.catch((err) => console.error('error loading cities by location', err));
|
|
1461
|
+
}, [locale, careApiDomain, dispatch]);
|
|
1462
|
+
const fetchCitiesByKeyword = React.useCallback(function fetchCitiesByKeyword(keyword) {
|
|
1463
|
+
return fetchCitiesApi(paths.PATHS.GET_CITIES_LIST, { keyword })
|
|
1464
|
+
.then((data) => {
|
|
1465
|
+
dispatch({
|
|
1466
|
+
type: ActionTypes$1.FetchCitiesByKeywordComplete,
|
|
1467
|
+
payload: data.cities,
|
|
1468
|
+
});
|
|
1469
|
+
})
|
|
1470
|
+
.catch((err) => console.error('error loading cities by keyword', err));
|
|
1471
|
+
}, [locale, careApiDomain, dispatch]);
|
|
1472
|
+
const fetchSearchResults = React.useCallback(function fetchSearchResults(searchKeywords, state) {
|
|
1473
|
+
const url = `${careApiDomain}${paths.PATHS.GET_SEARCH_V2}`;
|
|
1474
|
+
dispatch({ type: ActionTypes$1.FetchSearchResultsStart });
|
|
1475
|
+
const { defaultCity, selectedLocation, geoLocationCoordinates } = state;
|
|
1476
|
+
let cityId = '';
|
|
1477
|
+
if (!selectedLocation || !defaultCity) {
|
|
1478
|
+
dispatch({ type: ActionTypes$1.FetchSearchResultsFinish });
|
|
1479
|
+
return;
|
|
1480
|
+
}
|
|
1481
|
+
const isCurrentLocationSelected = selectedLocation.id === constants.ID_OPTION_CURRENT_LOCATION;
|
|
1482
|
+
if (isCurrentLocationSelected) {
|
|
1483
|
+
if (!geoLocationCoordinates) {
|
|
1484
|
+
cityId = defaultCity.id;
|
|
1485
|
+
}
|
|
1486
|
+
}
|
|
1487
|
+
else if (selectedLocation.id === constants.ID_OPTION_ALL_LOCATION) {
|
|
1488
|
+
cityId = '';
|
|
1489
|
+
}
|
|
1490
|
+
else {
|
|
1491
|
+
cityId = selectedLocation.id;
|
|
1492
|
+
}
|
|
1493
|
+
const lat = (geoLocationCoordinates === null || geoLocationCoordinates === void 0 ? void 0 : geoLocationCoordinates.lat) || '';
|
|
1494
|
+
const lng = (geoLocationCoordinates === null || geoLocationCoordinates === void 0 ? void 0 : geoLocationCoordinates.lng) || '';
|
|
1495
|
+
return fetch(getApiPath(url, {
|
|
1496
|
+
domain: careApiDomain,
|
|
1497
|
+
searchType: 'global',
|
|
1498
|
+
keyword: searchKeywords.trim().length > SEARCH_KEYWORD_MIN_LENGTH$1[locale]
|
|
1499
|
+
? searchKeywords.trim()
|
|
1500
|
+
: '',
|
|
1501
|
+
city: cityId === constants.ID_OPTION_CURRENT_LOCATION ? '' : cityId,
|
|
1502
|
+
lat,
|
|
1503
|
+
lng,
|
|
1504
|
+
}, locale), {
|
|
1505
|
+
method: 'GET',
|
|
1506
|
+
headers: {
|
|
1507
|
+
accept: 'version=2.0.0.0',
|
|
1508
|
+
},
|
|
1509
|
+
})
|
|
1510
|
+
.then((res) => res.json())
|
|
1511
|
+
.then((data) => {
|
|
1512
|
+
if (data._status !== 1 || !data._data) {
|
|
1513
|
+
return Promise.reject(data);
|
|
1514
|
+
}
|
|
1515
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
1516
|
+
})
|
|
1517
|
+
.then((results) => dispatch({
|
|
1518
|
+
type: ActionTypes$1.FetchSearchResultsComplete,
|
|
1519
|
+
payload: results,
|
|
1520
|
+
}))
|
|
1521
|
+
.catch((error) => {
|
|
1522
|
+
console.log('error loading search results', { url, error });
|
|
1523
|
+
})
|
|
1524
|
+
.finally(() => dispatch({ type: ActionTypes$1.FetchSearchResultsFinish }));
|
|
1525
|
+
}, [locale, careApiDomain, dispatch]);
|
|
1526
|
+
return {
|
|
1527
|
+
fetchCitiesByLocation,
|
|
1528
|
+
fetchCitiesByKeyword,
|
|
1529
|
+
fetchSearchResults,
|
|
1530
|
+
};
|
|
1531
|
+
}
|
|
1532
|
+
|
|
1533
|
+
const BookingSearchBar = ({ isMobile, careApiDomain, geoLocationPermission: geoLocationPermissionFromProps, geoLocationCoordinates: geoLocationCoordinatesFromProps, initialSelectedCity: initialSelectedCityFromProps, initialSearchValue = '', careFrontDomain = '/care', isDebug = false, askForGeolocationPermission = false, gaTrackingSearchBar, gaTrackingLocationSearch, autoCompleteDisabled = false, inputSearchPlaceholder = '', isOptionAllLocation = false, hideResults = [], isNavResultItem = true, routerPush, onGeoLocationPermissionChange, onSearch, onChangeLocation, }) => {
|
|
1534
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
1535
|
+
const wrapperRef = React.useRef(null);
|
|
1536
|
+
const hiddenInputRef = React.useRef(null);
|
|
1537
|
+
const [viewportHeight, setViewportHeight] = React.useState(undefined);
|
|
1538
|
+
const [isNavResultPage, setIsNavResultPage] = React.useState(false);
|
|
1539
|
+
const { geoLocationPermission: geoLocationPermissionFromHook, geoLocationCoordinates: geoLocationCoordinatesFromHook, requestGeoLocation, } = useGeolocation();
|
|
1540
|
+
const [state, dispatch] = React.useReducer(reducer$1, initialState$1, (s) => (Object.assign(Object.assign({}, s), { isDebug,
|
|
1541
|
+
isMobile, geoLocationPermission: geoLocationPermissionFromProps ||
|
|
1542
|
+
geoLocationPermissionFromHook ||
|
|
1543
|
+
'unset', geoLocationCoordinates: geoLocationCoordinatesFromProps ||
|
|
1544
|
+
geoLocationCoordinatesFromHook ||
|
|
1545
|
+
null, searchKeywords: initialSearchValue, initialSelectedCity: initialSelectedCityFromProps || null, selectedLocation: initialSelectedCityFromProps || s.selectedLocation || null, searchLocationKeywords: (initialSelectedCityFromProps === null || initialSelectedCityFromProps === void 0 ? void 0 : initialSelectedCityFromProps.name) || s.searchLocationKeywords, autoCompleteDisabled,
|
|
1546
|
+
inputSearchPlaceholder,
|
|
1547
|
+
locale })));
|
|
1548
|
+
const { navigateTo, focused, isLoadingCities, cities, searchKeywords, geoLocationPermission, selectedLocation, initialSelectedCity, defaultCity, searchResults, isLoadingSearchResults, isMobileModalOpened, inputSearchPlaceholder: inputSearchPlaceholderState, } = state;
|
|
1549
|
+
const { fetchCitiesByLocation, fetchCitiesByKeyword, fetchSearchResults } = useSearchBarApi$1({
|
|
1550
|
+
dispatch,
|
|
1551
|
+
locale,
|
|
1552
|
+
careApiDomain,
|
|
1553
|
+
});
|
|
1554
|
+
const currentLocationCityItem = React.useMemo(() => {
|
|
1555
|
+
var _a;
|
|
1556
|
+
return ({
|
|
1557
|
+
id: constants.ID_OPTION_CURRENT_LOCATION,
|
|
1558
|
+
name: t('booking.searchBar.currentLocation'),
|
|
1559
|
+
slug: (_a = constants.LOCALIZED_SLUGS[locale]) === null || _a === void 0 ? void 0 : _a.CURRENT,
|
|
1560
|
+
});
|
|
1561
|
+
}, [t, locale]);
|
|
1562
|
+
const debouncedFetchCitiesByKeyword = React.useMemo(() => debounce__default["default"](fetchCitiesByKeyword, 400), [fetchCitiesByKeyword]);
|
|
1563
|
+
const debouncedFetchSearchResults = React.useMemo(() => debounce__default["default"](fetchSearchResults, 400), [fetchSearchResults]);
|
|
1564
|
+
React.useEffect(() => {
|
|
1565
|
+
if (initialSearchValue !== '' &&
|
|
1566
|
+
initialSearchValue !== state.searchKeywords) {
|
|
1567
|
+
dispatch({
|
|
1568
|
+
type: ActionTypes$1.UpdateInitialSearchValue,
|
|
1569
|
+
payload: initialSearchValue,
|
|
1570
|
+
});
|
|
1571
|
+
}
|
|
1572
|
+
}, [initialSearchValue]);
|
|
1573
|
+
React.useEffect(() => {
|
|
1574
|
+
if (askForGeolocationPermission &&
|
|
1575
|
+
(selectedLocation === null || selectedLocation === void 0 ? void 0 : selectedLocation.id) === constants.ID_OPTION_CURRENT_LOCATION &&
|
|
1576
|
+
geoLocationPermission === 'unset') {
|
|
1577
|
+
requestGeoLocation();
|
|
1578
|
+
}
|
|
1579
|
+
}, [askForGeolocationPermission, selectedLocation, geoLocationPermission]);
|
|
1580
|
+
React.useEffect(() => {
|
|
1581
|
+
if (!geoLocationPermissionFromProps &&
|
|
1582
|
+
geoLocationPermission !== geoLocationPermissionFromHook) {
|
|
1583
|
+
if (geoLocationPermissionFromHook === 'granted' &&
|
|
1584
|
+
geoLocationCoordinatesFromHook) {
|
|
1585
|
+
dispatch({
|
|
1586
|
+
type: ActionTypes$1.GrantGeoLocationPermission,
|
|
1587
|
+
payload: geoLocationCoordinatesFromHook,
|
|
1588
|
+
});
|
|
1589
|
+
}
|
|
1590
|
+
else if (geoLocationPermissionFromHook === 'denied') {
|
|
1591
|
+
dispatch({ type: ActionTypes$1.DenyGeoLocationPermission });
|
|
1592
|
+
}
|
|
1593
|
+
}
|
|
1594
|
+
}, [
|
|
1595
|
+
geoLocationPermission,
|
|
1596
|
+
geoLocationPermissionFromHook,
|
|
1597
|
+
geoLocationCoordinatesFromHook,
|
|
1598
|
+
geoLocationPermissionFromProps,
|
|
1599
|
+
]);
|
|
1600
|
+
React.useEffect(() => {
|
|
1601
|
+
if (navigateTo) {
|
|
1602
|
+
if (routerPush) {
|
|
1603
|
+
routerPush(navigateTo);
|
|
1604
|
+
}
|
|
1605
|
+
else {
|
|
1606
|
+
window.location.href = `${careFrontDomain}${navigateTo}`;
|
|
1607
|
+
}
|
|
1608
|
+
}
|
|
1609
|
+
}, [navigateTo]);
|
|
1610
|
+
const selectCurrentLocation = React.useCallback(function selectCurrentLocation() {
|
|
1611
|
+
dispatch({
|
|
1612
|
+
type: ActionTypes$1.SelectCurrentLocation,
|
|
1613
|
+
payload: currentLocationCityItem,
|
|
1614
|
+
});
|
|
1615
|
+
}, [t, dispatch]);
|
|
1616
|
+
React.useEffect(() => {
|
|
1617
|
+
var _a;
|
|
1618
|
+
if (geoLocationPermission !== 'denied' && !initialSelectedCity) {
|
|
1619
|
+
dispatch({
|
|
1620
|
+
type: ActionTypes$1.SelectLocation,
|
|
1621
|
+
payload: {
|
|
1622
|
+
name: t('booking.searchBar.allLocations'),
|
|
1623
|
+
id: constants.ID_OPTION_ALL_LOCATION,
|
|
1624
|
+
slug: (_a = constants.LOCALIZED_SLUGS[locale]) === null || _a === void 0 ? void 0 : _a.ALL,
|
|
1625
|
+
},
|
|
1626
|
+
});
|
|
1627
|
+
}
|
|
1628
|
+
if (onGeoLocationPermissionChange) {
|
|
1629
|
+
onGeoLocationPermissionChange(geoLocationPermission, state.geoLocationCoordinates);
|
|
1630
|
+
}
|
|
1631
|
+
if (isMobile && geoLocationPermission === 'granted' && selectedLocation) {
|
|
1632
|
+
dispatch({ type: ActionTypes$1.FocusInputSearch });
|
|
1633
|
+
}
|
|
1634
|
+
fetchCitiesByLocation({ coordinates: state.geoLocationCoordinates });
|
|
1635
|
+
}, [geoLocationPermission]);
|
|
1636
|
+
React.useEffect(() => {
|
|
1637
|
+
if (selectedLocation && defaultCity) {
|
|
1638
|
+
fetchSearchResults(state.searchKeywords, state);
|
|
1639
|
+
}
|
|
1640
|
+
}, [selectedLocation, defaultCity]);
|
|
1641
|
+
React.useEffect(() => {
|
|
1642
|
+
if (inputSearchPlaceholder !== inputSearchPlaceholderState) {
|
|
1643
|
+
dispatch({
|
|
1644
|
+
type: ActionTypes$1.SetInputSearchPlaceholder,
|
|
1645
|
+
payload: inputSearchPlaceholder,
|
|
1646
|
+
});
|
|
1647
|
+
}
|
|
1648
|
+
}, [inputSearchPlaceholder, inputSearchPlaceholderState]);
|
|
1649
|
+
React.useEffect(() => {
|
|
1650
|
+
if (isMobileModalOpened) {
|
|
1651
|
+
document.body.classList.add('care-popup-open');
|
|
1652
|
+
}
|
|
1653
|
+
else {
|
|
1654
|
+
document.body.classList.remove('care-popup-open');
|
|
1655
|
+
}
|
|
1656
|
+
}, [isMobileModalOpened]);
|
|
1657
|
+
const handleLocationClick = React.useCallback(function handleLocationClick(city) {
|
|
1658
|
+
if (locale === 'ms-MY') {
|
|
1659
|
+
setIsNavResultPage(true);
|
|
1660
|
+
}
|
|
1661
|
+
dispatch({ type: ActionTypes$1.SelectLocation, payload: city });
|
|
1662
|
+
if (locale !== 'ms-MY') {
|
|
1663
|
+
focusSearchInput();
|
|
1664
|
+
}
|
|
1665
|
+
if (onChangeLocation) {
|
|
1666
|
+
onChangeLocation(city);
|
|
1667
|
+
}
|
|
1668
|
+
}, [t, dispatch]);
|
|
1669
|
+
function handleCurrentLocationClick() {
|
|
1670
|
+
if (locale === 'ms-MY') {
|
|
1671
|
+
setIsNavResultPage(true);
|
|
1672
|
+
}
|
|
1673
|
+
if (isMobile && state.geoLocationPermission !== 'granted') {
|
|
1674
|
+
requestGeoLocation();
|
|
1675
|
+
}
|
|
1676
|
+
else {
|
|
1677
|
+
selectCurrentLocation();
|
|
1678
|
+
if (locale !== 'ms-MY') {
|
|
1679
|
+
focusSearchInput();
|
|
1680
|
+
}
|
|
1681
|
+
}
|
|
1682
|
+
}
|
|
1683
|
+
function handleMobileFakeInputClick() {
|
|
1684
|
+
var _a;
|
|
1685
|
+
return tslib_es6.__awaiter(this, void 0, void 0, function* () {
|
|
1686
|
+
if (hiddenInputRef.current) {
|
|
1687
|
+
hiddenInputRef.current.focus();
|
|
1688
|
+
}
|
|
1689
|
+
dispatch({ type: ActionTypes$1.OpenMobileModal });
|
|
1690
|
+
yield Promise.resolve();
|
|
1691
|
+
if (wrapperRef.current) {
|
|
1692
|
+
(_a = wrapperRef.current
|
|
1693
|
+
.querySelector('input[name="search-location"]')) === null || _a === void 0 ? void 0 : _a.focus();
|
|
1694
|
+
}
|
|
1695
|
+
});
|
|
1696
|
+
}
|
|
1697
|
+
function focusLocationInput() {
|
|
1698
|
+
var _a;
|
|
1699
|
+
if (wrapperRef.current) {
|
|
1700
|
+
(_a = wrapperRef.current
|
|
1701
|
+
.querySelector('input[name="search-location"]')) === null || _a === void 0 ? void 0 : _a.focus();
|
|
1702
|
+
}
|
|
1703
|
+
}
|
|
1704
|
+
function focusSearchInput() {
|
|
1705
|
+
var _a;
|
|
1706
|
+
if (wrapperRef.current) {
|
|
1707
|
+
(_a = wrapperRef.current
|
|
1708
|
+
.querySelector('input[name="search-results"]')) === null || _a === void 0 ? void 0 : _a.focus();
|
|
1709
|
+
}
|
|
1710
|
+
}
|
|
1711
|
+
function handleMobileTopBarClose() {
|
|
1712
|
+
dispatch({ type: ActionTypes$1.CloseMobileModal });
|
|
1713
|
+
}
|
|
1714
|
+
function renderLocationResults() {
|
|
1715
|
+
if (focused !== 'location') {
|
|
1716
|
+
return null;
|
|
1717
|
+
}
|
|
1718
|
+
return (React__default["default"].createElement(LocationResults, { isLoading: isLoadingCities, cities: cities, onLocationClick: handleLocationClick, onCurrentLocationClick: handleCurrentLocationClick, isLocationLoading: isLoadingCities, geoLocationPermission: geoLocationPermission, selectedLocation: selectedLocation, isOptionAllLocation: isOptionAllLocation }));
|
|
1719
|
+
}
|
|
1720
|
+
function renderSearchResults() {
|
|
1721
|
+
if (focused !== 'search') {
|
|
1722
|
+
return null;
|
|
1723
|
+
}
|
|
1724
|
+
if (state.autoCompleteDisabled) {
|
|
1725
|
+
if (!isMobile) {
|
|
1726
|
+
return null;
|
|
1727
|
+
}
|
|
1728
|
+
return (React__default["default"].createElement(SearchButton, { onClick: () => {
|
|
1729
|
+
onSearch({
|
|
1730
|
+
cityId: state.selectedLocation.id,
|
|
1731
|
+
keyword: searchKeywords,
|
|
1732
|
+
});
|
|
1733
|
+
handleMobileTopBarClose();
|
|
1734
|
+
} }));
|
|
1735
|
+
}
|
|
1736
|
+
return (React__default["default"].createElement(SearchResults, { data: searchResults, state: state, dispatch: dispatch, isMobile: false, keyword: searchKeywords, isLoading: isLoadingSearchResults, hideResults: hideResults, isNavResultItem: isNavResultItem }));
|
|
1737
|
+
}
|
|
1738
|
+
function renderSearchInputs() {
|
|
1739
|
+
return (React__default["default"].createElement(SearchInputs$1, { isMobile: isMobile, state: state, dispatch: dispatch, debouncedFetchCitiesByKeyword: debouncedFetchCitiesByKeyword, debouncedFetchSearchResults: debouncedFetchSearchResults, focusLocationInput: focusLocationInput, focusSearchInput: focusSearchInput, renderLocationResults: renderLocationResults, renderSearchResults: renderSearchResults, trackingAttributes: gaTrackingSearchBar, locationTrackingAttributes: gaTrackingLocationSearch, onSearch: onSearch, initalSearchValue: initialSearchValue }));
|
|
1740
|
+
}
|
|
1741
|
+
React.useEffect(() => {
|
|
1742
|
+
if (window.visualViewport) {
|
|
1743
|
+
const resizeHandler = (evt) => {
|
|
1744
|
+
const viewport = evt.target;
|
|
1745
|
+
setViewportHeight(viewport === null || viewport === void 0 ? void 0 : viewport.height);
|
|
1746
|
+
};
|
|
1747
|
+
window.visualViewport.addEventListener('resize', resizeHandler, {
|
|
1748
|
+
passive: true,
|
|
1749
|
+
});
|
|
1750
|
+
return () => {
|
|
1751
|
+
window.visualViewport.removeEventListener('resize', resizeHandler);
|
|
1752
|
+
};
|
|
1753
|
+
}
|
|
1754
|
+
}, [setViewportHeight]);
|
|
1755
|
+
React.useEffect(() => {
|
|
1756
|
+
// Apply for ms-MY. Navigation to result page after selected location
|
|
1757
|
+
if (selectedLocation && isNavResultPage && locale === 'ms-MY') {
|
|
1758
|
+
const url = `/${selectedLocation.slug}/hospital`;
|
|
1759
|
+
dispatch({ type: ActionTypes$1.NavigateTo, payload: url });
|
|
1760
|
+
setIsNavResultPage(false);
|
|
1761
|
+
}
|
|
1762
|
+
}, [isNavResultPage, locale, selectedLocation]);
|
|
1763
|
+
if (isMobile) {
|
|
1764
|
+
return (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
1765
|
+
React__default["default"].createElement(CareSearchGlobalStyles, null),
|
|
1766
|
+
React__default["default"].createElement(StyledHiddenInputMobile, { ref: hiddenInputRef }),
|
|
1767
|
+
React__default["default"].createElement(StyledSearchBarMobileWrapper, { id: "booking-search-bar", ref: wrapperRef, "data-is-modal": isMobile && isMobileModalOpened, style: {
|
|
1768
|
+
'--mobile-care-searchbar-height': isMobileModalOpened && viewportHeight
|
|
1769
|
+
? `${viewportHeight}px`
|
|
1770
|
+
: '100%',
|
|
1771
|
+
} }, !isMobileModalOpened ? (React__default["default"].createElement(MobileFakeInput, { onClick: handleMobileFakeInputClick, focused: focused, value: searchKeywords, trackingAttributes: gaTrackingSearchBar, inputSearchPlaceholder: inputSearchPlaceholder })) : (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
1772
|
+
React__default["default"].createElement(StyledSearchBarMobileModalHeader, null,
|
|
1773
|
+
React__default["default"].createElement(MobileTopBar, { headingText: t('booking.searchBar.searchButton'), onLeftClick: handleMobileTopBarClose }),
|
|
1774
|
+
renderSearchInputs()),
|
|
1775
|
+
renderLocationResults(),
|
|
1776
|
+
renderSearchResults())))));
|
|
1777
|
+
}
|
|
1778
|
+
return (React__default["default"].createElement(StyledSearchBarWrapper$1, { id: "booking-search-bar", ref: wrapperRef }, renderSearchInputs()));
|
|
1779
|
+
};
|
|
1780
|
+
|
|
1781
|
+
const StyledSearchBarWrapper = styled__default["default"].div ``;
|
|
1782
|
+
const StyleWrapperContainer = styled__default["default"].div `
|
|
1783
|
+
background-color: ${theme.theme.colors.neutral50};
|
|
1784
|
+
padding-bottom: 1px;
|
|
1785
|
+
${utils.MediaQueries.mbDown} {
|
|
1786
|
+
padding: 0 16px 10px;
|
|
1787
|
+
}
|
|
1788
|
+
`;
|
|
1789
|
+
const StyleSearchInputContainer = styled__default["default"](index$3.Container) `
|
|
1790
|
+
padding: 0 16px;
|
|
1791
|
+
|
|
1792
|
+
${utils.MediaQueries.mbDown} {
|
|
1793
|
+
padding: 0;
|
|
1794
|
+
}
|
|
1795
|
+
`;
|
|
1796
|
+
const StyleSearchContent = styled__default["default"].div `
|
|
1797
|
+
padding: 24px 56px;
|
|
1798
|
+
border-radius: 0px 0px 16px 16px;
|
|
1799
|
+
background-color: ${theme.theme.colors.white};
|
|
1800
|
+
box-shadow: 0px 0px 1px 0px rgba(0, 0, 0, 0.04),
|
|
1801
|
+
0px 0px 2px 0px rgba(0, 0, 0, 0.06), 0px 4px 8px 0px rgba(0, 0, 0, 0.04);
|
|
1802
|
+
|
|
1803
|
+
${utils.MediaQueries.mbDown} {
|
|
1804
|
+
padding: 16px 16px;
|
|
1805
|
+
border-radius: 0px 0px 12px 12px;
|
|
1806
|
+
}
|
|
1807
|
+
|
|
1808
|
+
.flex-search-input {
|
|
1809
|
+
flex-direction: row;
|
|
1810
|
+
${utils.MediaQueries.mbDown} {
|
|
1811
|
+
flex-direction: column;
|
|
1812
|
+
}
|
|
1813
|
+
}
|
|
1814
|
+
`;
|
|
1815
|
+
|
|
1816
|
+
const SEARCH_KEYWORD_MIN_LENGTH = {
|
|
1817
|
+
'en-PH': 3,
|
|
1818
|
+
'tl-PH': 2,
|
|
1819
|
+
'id-ID': 3,
|
|
1820
|
+
'vi-VN': 2,
|
|
1821
|
+
'zh-TW': 0,
|
|
1822
|
+
'ms-MY': 2,
|
|
1823
|
+
};
|
|
1824
|
+
|
|
1825
|
+
const initialState = {
|
|
1826
|
+
isMobile: false,
|
|
1827
|
+
isDebug: false,
|
|
1828
|
+
navigateTo: null,
|
|
1829
|
+
geoLocationPermission: 'unset',
|
|
1830
|
+
geoLocationCoordinates: null,
|
|
1831
|
+
focused: 'none',
|
|
1832
|
+
focusedSpecialty: 'none',
|
|
1833
|
+
searchLocationKeywords: '',
|
|
1834
|
+
searchSpecialtyKeywords: '',
|
|
1835
|
+
searchKeywords: '',
|
|
1836
|
+
selectedLocation: null,
|
|
1837
|
+
selectedSpecialty: null,
|
|
1838
|
+
defaultCity: null,
|
|
1839
|
+
initialCities: [],
|
|
1840
|
+
cities: [],
|
|
1841
|
+
searchResults: {},
|
|
1842
|
+
initialSearchResults: {},
|
|
1843
|
+
isLoadingCities: false,
|
|
1844
|
+
isLoadingSearchResults: false,
|
|
1845
|
+
isMobileModalOpened: false,
|
|
1846
|
+
initialSelectedCity: null,
|
|
1847
|
+
autoCompleteDisabled: false,
|
|
1848
|
+
inputSearchPlaceholder: '',
|
|
1849
|
+
locale: 'vi-VN',
|
|
1850
|
+
allSpecialties: [],
|
|
1851
|
+
popularKeys: [],
|
|
1852
|
+
};
|
|
1853
|
+
var ActionTypes;
|
|
1854
|
+
(function (ActionTypes) {
|
|
1855
|
+
ActionTypes["NavigateTo"] = "navigate to url";
|
|
1856
|
+
ActionTypes["ClickOutsideInputLocation"] = "click outside input location";
|
|
1857
|
+
ActionTypes["ClickOutsideInputSearch"] = "click outside input search";
|
|
1858
|
+
ActionTypes["ClickOutsideInputSearchSpecialty"] = "click outside input search specialty";
|
|
1859
|
+
ActionTypes["ClickOutsideInputSpecialty"] = "click outside input specialty";
|
|
1860
|
+
ActionTypes["SelectCurrentLocation"] = "select current location";
|
|
1861
|
+
ActionTypes["FocusInputLocation"] = "focus input location";
|
|
1862
|
+
ActionTypes["FocusInputSearch"] = "focus input search";
|
|
1863
|
+
ActionTypes["FocusInputSearchSpecialty"] = "focus input search specialty";
|
|
1864
|
+
ActionTypes["ChangeInputLocation"] = "change input location";
|
|
1865
|
+
ActionTypes["ChangeInputSearch"] = "change input search";
|
|
1866
|
+
ActionTypes["ClearInputLocation"] = "clear input location";
|
|
1867
|
+
ActionTypes["ClearInputSearch"] = "clear input search";
|
|
1868
|
+
ActionTypes["SelectLocation"] = "select location";
|
|
1869
|
+
ActionTypes["SelectSpecialty"] = "select specialty";
|
|
1870
|
+
ActionTypes["FetchCitiesStart"] = "fetch cities start";
|
|
1871
|
+
ActionTypes["FetchCitiesFinish"] = "fetch cities finish";
|
|
1872
|
+
ActionTypes["FetchSearchResultsStart"] = "fetch search results start";
|
|
1873
|
+
ActionTypes["FetchSearchResultsComplete"] = "fetch search results complete";
|
|
1874
|
+
ActionTypes["FetchSearchResultsFinish"] = "fetch search results finish";
|
|
1875
|
+
ActionTypes["FetchCitiesByGeoIpComplete"] = "fetch cities by geo IP finish";
|
|
1876
|
+
ActionTypes["FetchCitiesByKeywordComplete"] = "fetch cities by keyword finish";
|
|
1877
|
+
ActionTypes["DisplayInitialCities"] = "display initial cities";
|
|
1878
|
+
ActionTypes["DisplayInitialSearchResults"] = "display initial search results";
|
|
1879
|
+
ActionTypes["UpdateInitialSearchResults"] = "update initial search results";
|
|
1880
|
+
ActionTypes["GrantGeoLocationPermission"] = "grant geolocation permission";
|
|
1881
|
+
ActionTypes["DenyGeoLocationPermission"] = "deny geolocation permission";
|
|
1882
|
+
ActionTypes["OpenMobileModal"] = "open mobile modal";
|
|
1883
|
+
ActionTypes["CloseMobileModal"] = "close mobile modal";
|
|
1884
|
+
ActionTypes["UpdateInitialSearchValue"] = "update initial search value";
|
|
1885
|
+
ActionTypes["SelectSearchResult"] = "select search result";
|
|
1886
|
+
ActionTypes["SetInputSearchPlaceholder"] = "set input search placeholder";
|
|
1887
|
+
ActionTypes["FocusInputSpecialty"] = "focus input specialty";
|
|
1888
|
+
ActionTypes["FetchAllSpecialties"] = "fetch all specialty";
|
|
1889
|
+
ActionTypes["FetchPopularKeys"] = "fetch popular key by type";
|
|
1890
|
+
})(ActionTypes || (ActionTypes = {}));
|
|
1891
|
+
function resetSearchLocationKeywords(state) {
|
|
1892
|
+
const { selectedLocation, searchLocationKeywords } = state;
|
|
1893
|
+
if (selectedLocation && searchLocationKeywords !== selectedLocation.name) {
|
|
1894
|
+
return Object.assign(Object.assign({}, state), { searchLocationKeywords: selectedLocation.name });
|
|
1895
|
+
}
|
|
1896
|
+
return state;
|
|
1897
|
+
}
|
|
1898
|
+
function reducer(state, action) {
|
|
1899
|
+
var _a, _b;
|
|
1900
|
+
if (state.isDebug) {
|
|
1901
|
+
console.log('bookingSearchBar', { action, state });
|
|
1902
|
+
}
|
|
1903
|
+
switch (action.type) {
|
|
1904
|
+
case ActionTypes.NavigateTo:
|
|
1905
|
+
return Object.assign(Object.assign({}, state), { navigateTo: action.payload, focused: 'none', isMobileModalOpened: false });
|
|
1906
|
+
case ActionTypes.ClickOutsideInputLocation: {
|
|
1907
|
+
if (state.focused !== 'location') {
|
|
1908
|
+
return state;
|
|
1909
|
+
}
|
|
1910
|
+
return resetSearchLocationKeywords(Object.assign(Object.assign({}, state), { focused: 'none' }));
|
|
1911
|
+
}
|
|
1912
|
+
case ActionTypes.ClickOutsideInputSpecialty: {
|
|
1913
|
+
if (state.focused !== 'specialty') {
|
|
1914
|
+
return state;
|
|
1915
|
+
}
|
|
1916
|
+
return resetSearchLocationKeywords(Object.assign(Object.assign({}, state), { focused: 'none' }));
|
|
1917
|
+
}
|
|
1918
|
+
case ActionTypes.ClickOutsideInputSearch: {
|
|
1919
|
+
if (state.focused !== 'search') {
|
|
1920
|
+
return state;
|
|
1921
|
+
}
|
|
1922
|
+
return Object.assign(Object.assign({}, state), { focused: 'none' });
|
|
1923
|
+
}
|
|
1924
|
+
case ActionTypes.ClickOutsideInputSearchSpecialty: {
|
|
1925
|
+
if (state.focusedSpecialty !== 'search') {
|
|
1926
|
+
return state;
|
|
1927
|
+
}
|
|
1928
|
+
return Object.assign(Object.assign({}, state), { focusedSpecialty: 'none' });
|
|
1929
|
+
}
|
|
1930
|
+
case ActionTypes.FocusInputLocation: {
|
|
1931
|
+
const nextState = Object.assign(Object.assign({}, state), { focused: 'location' });
|
|
1932
|
+
if (((_a = state.selectedLocation) === null || _a === void 0 ? void 0 : _a.id) === constants.ID_OPTION_CURRENT_LOCATION) {
|
|
1933
|
+
nextState.searchLocationKeywords = '';
|
|
1934
|
+
}
|
|
1935
|
+
return nextState;
|
|
1936
|
+
}
|
|
1937
|
+
case ActionTypes.FocusInputSpecialty: {
|
|
1938
|
+
const nextState = Object.assign(Object.assign({}, state), { focused: 'specialty' });
|
|
1939
|
+
if (((_b = state.selectedLocation) === null || _b === void 0 ? void 0 : _b.id) === constants.ID_OPTION_CURRENT_LOCATION) {
|
|
1940
|
+
nextState.searchLocationKeywords = '';
|
|
1941
|
+
}
|
|
1942
|
+
return nextState;
|
|
1943
|
+
}
|
|
1944
|
+
case ActionTypes.FocusInputSearch:
|
|
1945
|
+
const nextState = Object.assign(Object.assign({}, state), { focused: 'search' });
|
|
1946
|
+
if (state.isMobile) {
|
|
1947
|
+
return resetSearchLocationKeywords(nextState);
|
|
1948
|
+
}
|
|
1949
|
+
return nextState;
|
|
1950
|
+
case ActionTypes.FocusInputSearchSpecialty: {
|
|
1951
|
+
const nextState = Object.assign(Object.assign({}, state), { focusedSpecialty: 'search' });
|
|
1952
|
+
return nextState;
|
|
1953
|
+
}
|
|
1954
|
+
case ActionTypes.ChangeInputLocation:
|
|
1955
|
+
return Object.assign(Object.assign({}, state), { searchLocationKeywords: action.payload });
|
|
1956
|
+
case ActionTypes.ChangeInputSearch: {
|
|
1957
|
+
const keyword = action.payload;
|
|
1958
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: keyword, isLoadingSearchResults: keyword.trim().length > SEARCH_KEYWORD_MIN_LENGTH[state.locale] });
|
|
1959
|
+
}
|
|
1960
|
+
case ActionTypes.SelectCurrentLocation:
|
|
1961
|
+
return Object.assign(Object.assign({}, state), { focused: 'none', selectedLocation: action.payload, searchLocationKeywords: action.payload.name });
|
|
1962
|
+
case ActionTypes.ClearInputLocation:
|
|
1963
|
+
return Object.assign(Object.assign({}, state), { focused: 'location', cities: state.initialCities, searchLocationKeywords: '' });
|
|
1964
|
+
case ActionTypes.ClearInputSearch:
|
|
1965
|
+
return Object.assign(Object.assign({}, state), { focused: 'search', searchKeywords: '' });
|
|
1966
|
+
case ActionTypes.SelectLocation:
|
|
1967
|
+
return Object.assign(Object.assign({}, state), { focused: 'none', selectedLocation: action.payload, searchLocationKeywords: action.payload.name });
|
|
1968
|
+
case ActionTypes.SelectSpecialty:
|
|
1969
|
+
return Object.assign(Object.assign({}, state), { focused: 'none', selectedSpecialty: action.payload });
|
|
1970
|
+
case ActionTypes.SelectSearchResult:
|
|
1971
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: action.payload.name, isMobileModalOpened: false, focused: 'none', navigateTo: action.payload.url });
|
|
1972
|
+
case ActionTypes.FetchCitiesStart:
|
|
1973
|
+
return Object.assign(Object.assign({}, state), { isLoadingCities: true });
|
|
1974
|
+
case ActionTypes.FetchCitiesFinish:
|
|
1975
|
+
return Object.assign(Object.assign({}, state), { isLoadingCities: false });
|
|
1976
|
+
case ActionTypes.FetchSearchResultsStart:
|
|
1977
|
+
return Object.assign(Object.assign({}, state), { isLoadingSearchResults: true });
|
|
1978
|
+
case ActionTypes.FetchSearchResultsFinish:
|
|
1979
|
+
return Object.assign(Object.assign({}, state), { isLoadingSearchResults: false });
|
|
1980
|
+
case ActionTypes.FetchSearchResultsComplete: {
|
|
1981
|
+
const nextState = Object.assign(Object.assign({}, state), { searchResults: Object.assign(Object.assign({}, state.searchResults), { [action.payload.key]: action.payload.searches }) });
|
|
1982
|
+
return nextState;
|
|
1983
|
+
}
|
|
1984
|
+
case ActionTypes.FetchCitiesByGeoIpComplete: {
|
|
1985
|
+
let { cities } = action.payload;
|
|
1986
|
+
const { default: defaultCity } = action.payload;
|
|
1987
|
+
cities = cities.filter((c) => c.id !== defaultCity.id);
|
|
1988
|
+
if (defaultCity) {
|
|
1989
|
+
cities.unshift(defaultCity);
|
|
1990
|
+
}
|
|
1991
|
+
if (state.initialSelectedCity &&
|
|
1992
|
+
!cities.find((c) => c.id === state.initialSelectedCity.id)) {
|
|
1993
|
+
cities.unshift(state.initialSelectedCity);
|
|
1994
|
+
}
|
|
1995
|
+
const nextState = Object.assign(Object.assign({}, state), { defaultCity, initialCities: cities, cities });
|
|
1996
|
+
if (state.geoLocationPermission === 'denied' &&
|
|
1997
|
+
!state.initialSelectedCity) {
|
|
1998
|
+
nextState.selectedLocation = defaultCity;
|
|
1999
|
+
nextState.searchLocationKeywords = defaultCity.name;
|
|
2000
|
+
}
|
|
2001
|
+
return nextState;
|
|
2002
|
+
}
|
|
2003
|
+
case ActionTypes.FetchCitiesByKeywordComplete:
|
|
2004
|
+
return Object.assign(Object.assign({}, state), { cities: action.payload });
|
|
2005
|
+
case ActionTypes.DisplayInitialCities:
|
|
2006
|
+
return Object.assign(Object.assign({}, state), { cities: state.initialCities });
|
|
2007
|
+
case ActionTypes.DisplayInitialSearchResults:
|
|
2008
|
+
return Object.assign(Object.assign({}, state), { searchResults: state.initialSearchResults, isLoadingSearchResults: false });
|
|
2009
|
+
case ActionTypes.UpdateInitialSearchResults:
|
|
2010
|
+
return Object.assign(Object.assign({}, state), { initialSearchResults: Object.assign(Object.assign({}, state.initialSearchResults), { [action.payload.key]: action.payload.searches }) });
|
|
2011
|
+
case ActionTypes.GrantGeoLocationPermission:
|
|
2012
|
+
return Object.assign(Object.assign({}, state), { geoLocationPermission: 'granted', geoLocationCoordinates: action.payload });
|
|
2013
|
+
case ActionTypes.DenyGeoLocationPermission:
|
|
2014
|
+
return Object.assign(Object.assign({}, state), { geoLocationPermission: 'denied', geoLocationCoordinates: null });
|
|
2015
|
+
case ActionTypes.OpenMobileModal:
|
|
2016
|
+
return Object.assign(Object.assign({}, state), { isMobileModalOpened: true });
|
|
2017
|
+
case ActionTypes.CloseMobileModal:
|
|
2018
|
+
return Object.assign(Object.assign({}, state), { isMobileModalOpened: false });
|
|
2019
|
+
case ActionTypes.UpdateInitialSearchValue:
|
|
2020
|
+
return Object.assign(Object.assign({}, state), { searchKeywords: action.payload });
|
|
2021
|
+
case ActionTypes.SetInputSearchPlaceholder:
|
|
2022
|
+
return Object.assign(Object.assign({}, state), { inputSearchPlaceholder: action.payload });
|
|
2023
|
+
case ActionTypes.FetchAllSpecialties:
|
|
2024
|
+
return Object.assign(Object.assign({}, state), { allSpecialties: action.payload });
|
|
2025
|
+
case ActionTypes.FetchPopularKeys:
|
|
2026
|
+
return Object.assign(Object.assign({}, state), { popularKeys: action.payload });
|
|
2027
|
+
default:
|
|
2028
|
+
return state;
|
|
2029
|
+
}
|
|
2030
|
+
}
|
|
2031
|
+
|
|
2032
|
+
const StyleSearchInputsWrapper = styled__default["default"].div `
|
|
2033
|
+
flex: 1;
|
|
2034
|
+
position: relative;
|
|
2035
|
+
|
|
2036
|
+
${utils.MediaQueries.mbDown} {
|
|
2037
|
+
width: 100%;
|
|
2038
|
+
display: flex;
|
|
2039
|
+
flex-direction: column;
|
|
2040
|
+
gap: 12px;
|
|
2041
|
+
}
|
|
2042
|
+
`;
|
|
2043
|
+
const StyleResultWrapper$2 = styled__default["default"].div `
|
|
2044
|
+
position: absolute;
|
|
2045
|
+
top: calc(100% + 2px);
|
|
2046
|
+
width: 100%;
|
|
2047
|
+
border-radius: 4px;
|
|
2048
|
+
background: ${theme.theme.colors.white};
|
|
2049
|
+
box-shadow: 0px 8px 40px 0px rgba(0, 0, 0, 0.1);
|
|
2050
|
+
z-index: 10;
|
|
2051
|
+
|
|
2052
|
+
${utils.MediaQueries.mbDown} {
|
|
2053
|
+
width: calc(100% + 64px);
|
|
2054
|
+
left: -32px;
|
|
2055
|
+
}
|
|
2056
|
+
`;
|
|
2057
|
+
|
|
2058
|
+
const StyledSearchResultWrapper = styled__default["default"].div ``;
|
|
2059
|
+
const StyleResultHeader = styled__default["default"].div `
|
|
2060
|
+
display: flex;
|
|
2061
|
+
justify-content: space-between;
|
|
2062
|
+
align-item: center;
|
|
2063
|
+
padding: 9px 14px 9px 22px;
|
|
2064
|
+
background: #f7f9fc;
|
|
2065
|
+
|
|
2066
|
+
.title {
|
|
2067
|
+
color: ${theme.theme.colors.gray800};
|
|
2068
|
+
font-size: 14px;
|
|
2069
|
+
font-weight: 600;
|
|
2070
|
+
line-height: 22px;
|
|
2071
|
+
}
|
|
2072
|
+
|
|
2073
|
+
.btn-see-all {
|
|
2074
|
+
color: ${theme.theme.colors.blue600};
|
|
2075
|
+
font-size: 14px;
|
|
2076
|
+
line-height: 22px;
|
|
2077
|
+
cursor: pointer;
|
|
2078
|
+
}
|
|
2079
|
+
`;
|
|
2080
|
+
const StyleResultBody = styled__default["default"].div `
|
|
2081
|
+
padding: 10px 16px;
|
|
2082
|
+
max-height: 400px;
|
|
2083
|
+
overflow: auto;
|
|
2084
|
+
`;
|
|
2085
|
+
const StyleResultItem = styled__default["default"].div `
|
|
2086
|
+
display: flex;
|
|
2087
|
+
gap: 12px;
|
|
2088
|
+
align-items: center;
|
|
2089
|
+
cursor: pointer;
|
|
2090
|
+
|
|
2091
|
+
&:hover {
|
|
2092
|
+
background-color: ${theme.theme.colors.blue50};
|
|
2093
|
+
}
|
|
2094
|
+
.image-item {
|
|
2095
|
+
flex: 0 0 48px;
|
|
2096
|
+
width: 48px;
|
|
2097
|
+
height: 48px;
|
|
2098
|
+
border-radius: 50%;
|
|
2099
|
+
|
|
2100
|
+
img {
|
|
2101
|
+
object-fit: contain;
|
|
2102
|
+
width: 100%;
|
|
2103
|
+
height: 100%;
|
|
2104
|
+
border-radius: 50%;
|
|
2105
|
+
}
|
|
2106
|
+
}
|
|
2107
|
+
.infor {
|
|
2108
|
+
overflow: hidden;
|
|
2109
|
+
padding: 12px 0;
|
|
2110
|
+
flex: 1;
|
|
2111
|
+
border-bottom: 1px solid ${theme.theme.colors.neutral100};
|
|
2112
|
+
.title {
|
|
2113
|
+
color: ${theme.theme.colors.gray800};
|
|
2114
|
+
font-size: 16px;
|
|
2115
|
+
font-weight: 600;
|
|
2116
|
+
line-height: 24px;
|
|
2117
|
+
}
|
|
2118
|
+
.description {
|
|
2119
|
+
overflow: hidden;
|
|
2120
|
+
color: ${theme.theme.colors.gray600};
|
|
2121
|
+
text-overflow: ellipsis;
|
|
2122
|
+
white-space: nowrap;
|
|
2123
|
+
font-size: 12px;
|
|
2124
|
+
line-height: 18px;
|
|
2125
|
+
display: flex;
|
|
2126
|
+
gap: 8px;
|
|
2127
|
+
align-items: center;
|
|
2128
|
+
margin-top: 5px;
|
|
2129
|
+
|
|
2130
|
+
svg {
|
|
2131
|
+
flex: 0 0 16px;
|
|
2132
|
+
}
|
|
2133
|
+
|
|
2134
|
+
.sub-description {
|
|
2135
|
+
overflow: hidden;
|
|
2136
|
+
white-space: nowrap;
|
|
2137
|
+
text-overflow: ellipsis;
|
|
2138
|
+
flex: 1;
|
|
2139
|
+
}
|
|
2140
|
+
}
|
|
2141
|
+
}
|
|
2142
|
+
|
|
2143
|
+
&.last-item {
|
|
2144
|
+
.infor {
|
|
2145
|
+
border-bottom: none;
|
|
2146
|
+
}
|
|
2147
|
+
}
|
|
2148
|
+
`;
|
|
2149
|
+
styled__default["default"].div `
|
|
2150
|
+
padding: 0 16px 16px;
|
|
2151
|
+
|
|
2152
|
+
.search-detail-btn {
|
|
2153
|
+
color: ${theme.theme.colors.blue600};
|
|
2154
|
+
font-size: 14px;
|
|
2155
|
+
line-height: 22px;
|
|
2156
|
+
cursor: pointer;
|
|
2157
|
+
}
|
|
2158
|
+
`;
|
|
2159
|
+
|
|
2160
|
+
const SearchResult = ({ state, type, results, location, isLoading, typeInformation, clientSlug = '', dispatch, }) => {
|
|
2161
|
+
const { locale, t } = useTranslations.useTranslations();
|
|
2162
|
+
const { selectedLocation } = state;
|
|
2163
|
+
const typeSlug = React.useMemo(() => typeInformation[type].slug, [typeInformation, type]);
|
|
2164
|
+
const handleOnClick = (item) => {
|
|
2165
|
+
let url = '';
|
|
2166
|
+
switch (type) {
|
|
2167
|
+
case 'service':
|
|
2168
|
+
url = `/${selectedLocation.slug}/${typeSlug}/${item.slug}`;
|
|
2169
|
+
break;
|
|
2170
|
+
case 'doctor':
|
|
2171
|
+
case 'hospital':
|
|
2172
|
+
url = `/${typeSlug}/${item.slug}-${item.id}`;
|
|
2173
|
+
break;
|
|
2174
|
+
}
|
|
2175
|
+
if (url) {
|
|
2176
|
+
dispatch({
|
|
2177
|
+
type: ActionTypes.NavigateTo,
|
|
2178
|
+
payload: url,
|
|
2179
|
+
});
|
|
2180
|
+
}
|
|
2181
|
+
};
|
|
2182
|
+
const handleSeeAll = () => {
|
|
2183
|
+
let url = `/${selectedLocation.slug}/${typeSlug}`;
|
|
2184
|
+
const slugClientUrl = constants.MAPPING_CLIENT_WITH_SLUG[locale][clientSlug];
|
|
2185
|
+
if (slugClientUrl) {
|
|
2186
|
+
url += `/${slugClientUrl}`;
|
|
2187
|
+
}
|
|
2188
|
+
if ((type === 'doctor' || type === 'hospital') &&
|
|
2189
|
+
state.selectedSpecialty.id > 0) {
|
|
2190
|
+
url += `?specialtyId=${state.selectedSpecialty.id}`;
|
|
2191
|
+
}
|
|
2192
|
+
if (url) {
|
|
2193
|
+
dispatch({ type: ActionTypes.NavigateTo, payload: url });
|
|
2194
|
+
}
|
|
2195
|
+
};
|
|
2196
|
+
return (React__default["default"].createElement(StyledSearchResultWrapper, null,
|
|
2197
|
+
React__default["default"].createElement(StyleResultHeader, null,
|
|
2198
|
+
React__default["default"].createElement("div", { className: "title" }, t('booking.searchResult.description', {
|
|
2199
|
+
search_type: typeInformation[type].name,
|
|
2200
|
+
search_location: location,
|
|
2201
|
+
})),
|
|
2202
|
+
results.length > 0 && (React__default["default"].createElement("div", { className: "btn-see-all", onClick: handleSeeAll }, t('home.seeAll')))),
|
|
2203
|
+
React__default["default"].createElement(StyleResultBody, null,
|
|
2204
|
+
isLoading &&
|
|
2205
|
+
Array(3)
|
|
2206
|
+
.fill(undefined)
|
|
2207
|
+
.map((_, i) => (React__default["default"].createElement(StyleResultItem, { key: type + 'loading' + i, className: i === 2 ? 'last-item' : '' },
|
|
2208
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2209
|
+
React__default["default"].createElement(core.Skeleton, { height: 48, circle: true, mb: "xl", animate: true })),
|
|
2210
|
+
React__default["default"].createElement("div", { className: "infor" },
|
|
2211
|
+
React__default["default"].createElement("div", { className: "title" },
|
|
2212
|
+
React__default["default"].createElement(core.Skeleton, { height: 8, mt: 10, radius: "xl", animate: true })),
|
|
2213
|
+
React__default["default"].createElement("div", { className: "description" },
|
|
2214
|
+
React__default["default"].createElement("div", { className: "sub-description" },
|
|
2215
|
+
React__default["default"].createElement(core.Skeleton, { height: 8, mt: 10, radius: "xl", width: "80%", animate: true }))))))),
|
|
2216
|
+
!isLoading && results && results.length > 0 && (React__default["default"].createElement(React__default["default"].Fragment, null, results.map((item, index) => {
|
|
2217
|
+
var _a, _b;
|
|
2218
|
+
const isLastItem = (results.length > 4 && index === 3) ||
|
|
2219
|
+
(results.length <= 4 && index === results.length - 1);
|
|
2220
|
+
let subDescription = '';
|
|
2221
|
+
if (type === 'hospital') {
|
|
2222
|
+
subDescription = (item === null || item === void 0 ? void 0 : item.address) || '';
|
|
2223
|
+
}
|
|
2224
|
+
if (type === 'doctor') {
|
|
2225
|
+
subDescription = ((_a = item === null || item === void 0 ? void 0 : item.specialties) === null || _a === void 0 ? void 0 : _a.join(', ')) || '';
|
|
2226
|
+
}
|
|
2227
|
+
if (type === 'service') {
|
|
2228
|
+
subDescription = ((_b = item === null || item === void 0 ? void 0 : item.hospital_branch) === null || _b === void 0 ? void 0 : _b.name) || '';
|
|
2229
|
+
}
|
|
2230
|
+
if (index >= 4) {
|
|
2231
|
+
return React__default["default"].createElement(React__default["default"].Fragment, null);
|
|
2232
|
+
}
|
|
2233
|
+
return (React__default["default"].createElement(StyleResultItem, { key: item.id, className: isLastItem ? 'last-item' : '', onClick: () => handleOnClick(item) },
|
|
2234
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2235
|
+
React__default["default"].createElement("img", { src: item.logo || item.avatar, alt: item.name })),
|
|
2236
|
+
React__default["default"].createElement("div", { className: "infor" },
|
|
2237
|
+
React__default["default"].createElement("div", { className: "title" }, item.name),
|
|
2238
|
+
React__default["default"].createElement("div", { className: "description" },
|
|
2239
|
+
typeInformation[type].icon,
|
|
2240
|
+
React__default["default"].createElement("div", { className: "sub-description" }, subDescription)))));
|
|
2241
|
+
}))),
|
|
2242
|
+
!isLoading && (results === null || results === void 0 ? void 0 : results.length) === 0 && (React__default["default"].createElement(index$2.Text, { size: "sm", color: theme.theme.colors.gray400 }, t('booking.searchBar.noResults'))))));
|
|
2243
|
+
};
|
|
2244
|
+
|
|
2245
|
+
const StyleSearchSpecialtyWrapper = styled__default["default"].div `
|
|
2246
|
+
position: relative;
|
|
2247
|
+
|
|
2248
|
+
${utils.MediaQueries.mbDown} {
|
|
2249
|
+
width: 100%;
|
|
2250
|
+
display: flex;
|
|
2251
|
+
flex-direction: column;
|
|
2252
|
+
gap: 12px;
|
|
2253
|
+
}
|
|
2254
|
+
`;
|
|
2255
|
+
const StyleResultWrapper$1 = styled__default["default"].div `
|
|
2256
|
+
position: absolute;
|
|
2257
|
+
top: calc(100% + 2px);
|
|
2258
|
+
width: calc(100% + 100px);
|
|
2259
|
+
border-radius: 4px;
|
|
2260
|
+
background: ${theme.theme.colors.white};
|
|
2261
|
+
box-shadow: 0px 8px 40px 0px rgba(0, 0, 0, 0.1);
|
|
2262
|
+
z-index: 10;
|
|
2263
|
+
max-height: 300px;
|
|
2264
|
+
overflow: auto;
|
|
2265
|
+
|
|
2266
|
+
${utils.MediaQueries.mbDown} {
|
|
2267
|
+
width: calc(100% + 64px);
|
|
2268
|
+
left: -32px;
|
|
2269
|
+
}
|
|
2270
|
+
`;
|
|
2271
|
+
const StyledSpecialtyItem = styled__default["default"].li `
|
|
2272
|
+
position: relative;
|
|
2273
|
+
cursor: pointer;
|
|
2274
|
+
padding: 12px 18px;
|
|
2275
|
+
display: flex;
|
|
2276
|
+
align-items: center;
|
|
2277
|
+
gap: 14px;
|
|
2278
|
+
overflow: hidden;
|
|
2279
|
+
|
|
2280
|
+
.image-item {
|
|
2281
|
+
display: flex;
|
|
2282
|
+
align-items: center;
|
|
2283
|
+
width: 40px;
|
|
2284
|
+
height: 40px;
|
|
2285
|
+
|
|
2286
|
+
img {
|
|
2287
|
+
width: 100%;
|
|
2288
|
+
object-fit: cover;
|
|
2289
|
+
}
|
|
2290
|
+
|
|
2291
|
+
svg {
|
|
2292
|
+
width: 40px;
|
|
2293
|
+
}
|
|
2294
|
+
}
|
|
2295
|
+
|
|
2296
|
+
${({ isSelected }) => isSelected &&
|
|
2297
|
+
`
|
|
2298
|
+
&::after {
|
|
2299
|
+
content: ${checkMarkIconUrl};
|
|
2300
|
+
top: 50%;
|
|
2301
|
+
right: 18px;
|
|
2302
|
+
position: absolute;
|
|
2303
|
+
transform: translateY(-50%);
|
|
2304
|
+
}
|
|
2305
|
+
`}
|
|
2306
|
+
|
|
2307
|
+
& + li::before {
|
|
2308
|
+
content: '';
|
|
2309
|
+
position: absolute;
|
|
2310
|
+
left: 18px;
|
|
2311
|
+
right: 18px;
|
|
2312
|
+
top: 0;
|
|
2313
|
+
height: 1px;
|
|
2314
|
+
background-color: ${theme.theme.colors.neutral100};
|
|
2315
|
+
}
|
|
2316
|
+
|
|
2317
|
+
&:not([data-is-denied='true']):hover {
|
|
2318
|
+
background-color: ${theme.theme.colors.neutral50};
|
|
2319
|
+
}
|
|
2320
|
+
|
|
2321
|
+
&:last-child:hover {
|
|
2322
|
+
border-bottom-right-radius: 6px;
|
|
2323
|
+
border-bottom-left-radius: 6px;
|
|
2324
|
+
}
|
|
2325
|
+
|
|
2326
|
+
&:first-child:hover {
|
|
2327
|
+
border-top-right-radius: 6px;
|
|
2328
|
+
border-top-left-radius: 6px;
|
|
2329
|
+
}
|
|
2330
|
+
|
|
2331
|
+
&[data-is-denied='true'] {
|
|
2332
|
+
cursor: not-allowed;
|
|
2333
|
+
}
|
|
2334
|
+
`;
|
|
2335
|
+
|
|
2336
|
+
const DoctorIcon = () => (React__default["default"].createElement("svg", { width: "16", height: "16", viewBox: "0 0 16 16", fill: "none" },
|
|
2337
|
+
React__default["default"].createElement("path", { d: "M8.98307 14.3333C7.87196 14.3333 6.92752 13.9445 6.14974 13.1667C5.37196 12.3889 4.98307 11.4445 4.98307 10.3333V9.96668C4.08307 9.85557 3.33041 9.45557 2.72507 8.76668C2.1193 8.07779 1.81641 7.26668 1.81641 6.33334V3.10001C1.81641 2.93334 1.87463 2.79157 1.99107 2.67468C2.10796 2.55823 2.24974 2.50001 2.41641 2.50001H3.81641V2.33334C3.81641 2.1889 3.86374 2.06934 3.95841 1.97468C4.05263 1.88045 4.17196 1.83334 4.31641 1.83334C4.46085 1.83334 4.58041 1.88045 4.67507 1.97468C4.7693 2.06934 4.81641 2.1889 4.81641 2.33334V3.66668C4.81641 3.81112 4.7693 3.93045 4.67507 4.02468C4.58041 4.11934 4.46085 4.16668 4.31641 4.16668C4.17196 4.16668 4.05263 4.11934 3.95841 4.02468C3.86374 3.93045 3.81641 3.81112 3.81641 3.66668V3.50001H2.81641V6.33334C2.81641 7.06668 3.07752 7.69445 3.59974 8.21668C4.12196 8.7389 4.74974 9.00001 5.48307 9.00001C6.21641 9.00001 6.84418 8.7389 7.36641 8.21668C7.88863 7.69445 8.14974 7.06668 8.14974 6.33334V3.50001H7.14974V3.66668C7.14974 3.81112 7.10263 3.93045 7.00841 4.02468C6.91374 4.11934 6.79418 4.16668 6.64974 4.16668C6.5053 4.16668 6.38596 4.11934 6.29174 4.02468C6.19707 3.93045 6.14974 3.81112 6.14974 3.66668V2.33334C6.14974 2.1889 6.19707 2.06934 6.29174 1.97468C6.38596 1.88045 6.5053 1.83334 6.64974 1.83334C6.79418 1.83334 6.91374 1.88045 7.00841 1.97468C7.10263 2.06934 7.14974 2.1889 7.14974 2.33334V2.50001H8.54974C8.71641 2.50001 8.85818 2.55823 8.97507 2.67468C9.09152 2.79157 9.14974 2.93334 9.14974 3.10001V6.33334C9.14974 7.26668 8.84707 8.07779 8.24174 8.76668C7.63596 9.45557 6.88307 9.85557 5.98307 9.96668V10.3333C5.98307 11.1667 6.27485 11.8751 6.85841 12.4587C7.44152 13.0418 8.14974 13.3333 8.98307 13.3333C9.81641 13.3333 10.5249 13.0418 11.1084 12.4587C11.6915 11.8751 11.9831 11.1667 11.9831 10.3333V9.25001C11.6386 9.1389 11.3526 8.93601 11.1251 8.64134C10.8971 8.34712 10.7831 8.01112 10.7831 7.63334C10.7831 7.15557 10.9497 6.75001 11.2831 6.41668C11.6164 6.08334 12.0164 5.91668 12.4831 5.91668C12.9609 5.91668 13.3664 6.08334 13.6997 6.41668C14.0331 6.75001 14.1997 7.15557 14.1997 7.63334C14.1997 8.01112 14.086 8.34712 13.8584 8.64134C13.6304 8.93601 13.3386 9.1389 12.9831 9.25001V10.3333C12.9831 11.4445 12.5942 12.3889 11.8164 13.1667C11.0386 13.9445 10.0942 14.3333 8.98307 14.3333ZM12.4831 8.33334C12.6831 8.33334 12.8526 8.26401 12.9917 8.12534C13.1304 7.98623 13.1997 7.82223 13.1997 7.63334C13.1997 7.43334 13.1304 7.26401 12.9917 7.12534C12.8526 6.98623 12.6831 6.91668 12.4831 6.91668C12.2831 6.91668 12.1164 6.98623 11.9831 7.12534C11.8497 7.26401 11.7831 7.43334 11.7831 7.63334C11.7831 7.82223 11.8497 7.98623 11.9831 8.12534C12.1164 8.26401 12.2831 8.33334 12.4831 8.33334Z", fill: "#595959" })));
|
|
2338
|
+
const ServiceIcon = () => (React__default["default"].createElement("svg", { width: "16", height: "16", viewBox: "0 0 16 16", fill: "none" },
|
|
2339
|
+
React__default["default"].createElement("path", { d: "M6.86836 9.26489V10.2386C6.86836 10.509 6.96294 10.7389 7.15209 10.9283C7.34124 11.1176 7.57093 11.2122 7.84114 11.2122C8.11135 11.2122 8.34133 11.1176 8.53106 10.9283C8.7208 10.7389 8.81567 10.509 8.81567 10.2386V9.26489H9.78936C10.0598 9.26489 10.2897 9.17031 10.479 8.98116C10.6684 8.79201 10.763 8.56233 10.763 8.29211C10.763 8.0219 10.6684 7.79192 10.479 7.60219C10.2897 7.41245 10.0598 7.31758 9.78936 7.31758H8.81567V6.34389C8.81567 6.07343 8.72109 5.84354 8.53194 5.65422C8.34279 5.4649 8.11311 5.37024 7.84289 5.37024C7.57268 5.37024 7.3427 5.4649 7.15297 5.65422C6.96323 5.84354 6.86836 6.07343 6.86836 6.34389V7.31758H5.89467C5.62421 7.31758 5.39432 7.41216 5.205 7.60131C5.01568 7.79046 4.92102 8.02014 4.92102 8.29036C4.92102 8.56057 5.01568 8.79055 5.205 8.98028C5.39432 9.17002 5.62421 9.26489 5.89467 9.26489H6.86836ZM3.40809 14.1333C3.02086 14.1333 2.68938 13.9954 2.41364 13.7196C2.13788 13.4439 2 13.1124 2 12.7252V6.07426C2 5.85132 2.04987 5.64011 2.14961 5.44063C2.24936 5.24116 2.38723 5.07689 2.56323 4.94782L6.99718 1.61486C7.24323 1.42712 7.52444 1.33325 7.84081 1.33325C8.15718 1.33325 8.43919 1.42712 8.68685 1.61486L13.1208 4.94782C13.2968 5.07689 13.4347 5.24116 13.5344 5.44063C13.6342 5.64011 13.684 5.85132 13.684 6.07426V12.7252C13.684 13.1124 13.5462 13.4439 13.2704 13.7196C12.9947 13.9954 12.6632 14.1333 12.2759 14.1333H3.40809ZM3.40809 12.9649H12.2759C12.3459 12.9649 12.4033 12.9424 12.4482 12.8974C12.4932 12.8525 12.5156 12.7951 12.5156 12.7252V6.07426C12.5156 6.03431 12.5069 5.99811 12.4894 5.96566C12.4719 5.9332 12.4482 5.90449 12.4183 5.87953L7.98433 2.55406C7.94438 2.51911 7.89694 2.50164 7.84202 2.50164C7.78709 2.50164 7.73965 2.51911 7.69971 2.55406L3.26576 5.87953C3.2358 5.90449 3.21209 5.9332 3.1946 5.96566C3.17712 5.99811 3.16839 6.03431 3.16839 6.07426V12.7252C3.16839 12.7951 3.19086 12.8525 3.2358 12.8974C3.28075 12.9424 3.33818 12.9649 3.40809 12.9649Z", fill: "#595959" })));
|
|
2340
|
+
const HospitalIcon = () => (React__default["default"].createElement("svg", { width: "16", height: "16", viewBox: "0 0 16 16", fill: "none" },
|
|
2341
|
+
React__default["default"].createElement("path", { d: "M7.99984 8.00004C8.3665 8.00004 8.68039 7.86949 8.9415 7.60837C9.20261 7.34726 9.33317 7.03337 9.33317 6.66671C9.33317 6.30004 9.20261 5.98615 8.9415 5.72504C8.68039 5.46393 8.3665 5.33337 7.99984 5.33337C7.63317 5.33337 7.31928 5.46393 7.05817 5.72504C6.79706 5.98615 6.6665 6.30004 6.6665 6.66671C6.6665 7.03337 6.79706 7.34726 7.05817 7.60837C7.31928 7.86949 7.63317 8.00004 7.99984 8.00004ZM7.99984 12.9C9.35539 11.6556 10.3609 10.525 11.0165 9.50837C11.6721 8.49171 11.9998 7.58893 11.9998 6.80004C11.9998 5.58893 11.6137 4.59726 10.8415 3.82504C10.0693 3.05282 9.12206 2.66671 7.99984 2.66671C6.87761 2.66671 5.93039 3.05282 5.15817 3.82504C4.38595 4.59726 3.99984 5.58893 3.99984 6.80004C3.99984 7.58893 4.32761 8.49171 4.98317 9.50837C5.63873 10.525 6.64428 11.6556 7.99984 12.9ZM7.99984 14.4167C7.91095 14.4167 7.82206 14.4 7.73317 14.3667C7.64428 14.3334 7.5665 14.2889 7.49984 14.2334C5.87761 12.8 4.6665 11.4695 3.8665 10.2417C3.0665 9.01393 2.6665 7.86671 2.6665 6.80004C2.6665 5.13337 3.20261 3.8056 4.27484 2.81671C5.34706 1.82782 6.58873 1.33337 7.99984 1.33337C9.41095 1.33337 10.6526 1.82782 11.7248 2.81671C12.7971 3.8056 13.3332 5.13337 13.3332 6.80004C13.3332 7.86671 12.9332 9.01393 12.1332 10.2417C11.3332 11.4695 10.1221 12.8 8.49984 14.2334C8.43317 14.2889 8.35539 14.3334 8.2665 14.3667C8.17761 14.4 8.08873 14.4167 7.99984 14.4167Z", fill: "#8C8C8C" })));
|
|
2342
|
+
const SpecialtyIcon = () => (React__default["default"].createElement("svg", { width: "16", height: "16", viewBox: "0 0 16 16" },
|
|
2343
|
+
React__default["default"].createElement("path", { d: "M3.83333 0.5C2.94928 0.5 2.10143 0.851189 1.47631 1.47631C0.851189 2.10143 0.5 2.94928 0.5 3.83333C0.5 4.71739 0.851189 5.56523 1.47631 6.19036C2.10143 6.81548 2.94928 7.16667 3.83333 7.16667C4.71739 7.16667 5.56523 6.81548 6.19036 6.19036C6.81548 5.56523 7.16667 4.71739 7.16667 3.83333C7.16667 2.94928 6.81548 2.10143 6.19036 1.47631C5.56523 0.851189 4.71739 0.5 3.83333 0.5V0.5ZM10.5 0.5C9.57917 0.5 8.83333 1.24583 8.83333 2.16667V5.5C8.83333 6.42083 9.57917 7.16667 10.5 7.16667H13.8333C14.7542 7.16667 15.5 6.42083 15.5 5.5V2.16667C15.5 1.24583 14.7542 0.5 13.8333 0.5H10.5ZM3.83333 8.83333C2.94928 8.83333 2.10143 9.18452 1.47631 9.80964C0.851189 10.4348 0.5 11.2826 0.5 12.1667C0.5 13.0507 0.851189 13.8986 1.47631 14.5237C2.10143 15.1488 2.94928 15.5 3.83333 15.5C4.71739 15.5 5.56523 15.1488 6.19036 14.5237C6.81548 13.8986 7.16667 13.0507 7.16667 12.1667C7.16667 11.2826 6.81548 10.4348 6.19036 9.80964C5.56523 9.18452 4.71739 8.83333 3.83333 8.83333V8.83333ZM12.1667 8.83333C11.2826 8.83333 10.4348 9.18452 9.80964 9.80964C9.18452 10.4348 8.83333 11.2826 8.83333 12.1667C8.83333 13.0507 9.18452 13.8986 9.80964 14.5237C10.4348 15.1488 11.2826 15.5 12.1667 15.5C13.0507 15.5 13.8986 15.1488 14.5237 14.5237C15.1488 13.8986 15.5 13.0507 15.5 12.1667C15.5 11.2826 15.1488 10.4348 14.5237 9.80964C13.8986 9.18452 13.0507 8.83333 12.1667 8.83333V8.83333Z", fill: "#9AA2AC" })));
|
|
2344
|
+
|
|
2345
|
+
const SearchSpecialty = ({ state, isMobile, debouncedFetchSearchResults, selectedLocation, onSpecialtyClick, dispatch, }) => {
|
|
2346
|
+
var _a;
|
|
2347
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
2348
|
+
const inputSpecialtyWrapperRef = React.useRef(null);
|
|
2349
|
+
const slugs = React.useMemo(() => constants.LOCALIZED_SLUGS[locale], [locale]);
|
|
2350
|
+
const styleSpecialties = React.useMemo(() => {
|
|
2351
|
+
return {
|
|
2352
|
+
wrapper: {
|
|
2353
|
+
'&:after': {
|
|
2354
|
+
content: '""',
|
|
2355
|
+
width: '1px',
|
|
2356
|
+
height: '20px',
|
|
2357
|
+
backgroundColor: '#E4E8EC',
|
|
2358
|
+
position: 'absolute',
|
|
2359
|
+
right: 0,
|
|
2360
|
+
top: '13px',
|
|
2361
|
+
},
|
|
2362
|
+
},
|
|
2363
|
+
input: {
|
|
2364
|
+
border: isMobile ? 'border: 1px solid #d9d9d9' : 'none',
|
|
2365
|
+
height: isMobile ? '40px' : '46px !important',
|
|
2366
|
+
paddingRight: '30px',
|
|
2367
|
+
'&:focus': {
|
|
2368
|
+
boxShadow: isMobile ? 'box-shadow: 0px 0px 0px 2px #91caff' : 'none',
|
|
2369
|
+
},
|
|
2370
|
+
},
|
|
2371
|
+
rightSection: {
|
|
2372
|
+
width: '30px',
|
|
2373
|
+
svg: {
|
|
2374
|
+
fontSize: '20px',
|
|
2375
|
+
},
|
|
2376
|
+
},
|
|
2377
|
+
};
|
|
2378
|
+
}, [isMobile]);
|
|
2379
|
+
const handleSearchSpecialtyInputChange = React.useCallback(function handleSearchSpecialtyInputChange(value) {
|
|
2380
|
+
// dispatch({ type: ActionTypes.ChangeInputLocation, payload: value })
|
|
2381
|
+
// if (value.trim().length > SEARCH_KEYWORD_MIN_LENGTH[state.locale]) {
|
|
2382
|
+
// debouncedFetchSearchResults(value.trim())
|
|
2383
|
+
// } else {
|
|
2384
|
+
// debouncedFetchSearchResults.cancel()
|
|
2385
|
+
// dispatch({ type: ActionTypes.DisplayInitialCities })
|
|
2386
|
+
// }
|
|
2387
|
+
console.log(value);
|
|
2388
|
+
}, [debouncedFetchSearchResults, dispatch]);
|
|
2389
|
+
useOutsideClick.useOutsideClick(inputSpecialtyWrapperRef, () => {
|
|
2390
|
+
dispatch({ type: ActionTypes.ClickOutsideInputSpecialty });
|
|
2391
|
+
});
|
|
2392
|
+
return (React__default["default"].createElement(StyleSearchSpecialtyWrapper, { ref: inputSpecialtyWrapperRef },
|
|
2393
|
+
React__default["default"].createElement(core.Input.Wrapper, null,
|
|
2394
|
+
React__default["default"].createElement(core.Input, { size: isMobile ? 'md' : 'lg', placeholder: t('booking.searchPopup.specialties'), value: ((_a = state === null || state === void 0 ? void 0 : state.selectedSpecialty) === null || _a === void 0 ? void 0 : _a.name) || '', rightSection: React__default["default"].createElement(ChevronDown.ChevronDown, null), styles: styleSpecialties, onFocus: () => dispatch({ type: ActionTypes.FocusInputSpecialty }), onChange: (event) => {
|
|
2395
|
+
handleSearchSpecialtyInputChange(event.target.value);
|
|
2396
|
+
} })),
|
|
2397
|
+
state.focused === 'specialty' && (React__default["default"].createElement(StyleResultWrapper$1, null,
|
|
2398
|
+
React__default["default"].createElement(StyledSpecialtyItem, { key: "all-location", role: "button", tabIndex: 0, onClick: () => {
|
|
2399
|
+
if (onSpecialtyClick) {
|
|
2400
|
+
onSpecialtyClick({
|
|
2401
|
+
name: t('booking.searchBar.allSpecialties'),
|
|
2402
|
+
id: -1,
|
|
2403
|
+
thumbnail: '',
|
|
2404
|
+
total_doctor: 0,
|
|
2405
|
+
slug: slugs.SPECIALTIES,
|
|
2406
|
+
});
|
|
2407
|
+
}
|
|
2408
|
+
} },
|
|
2409
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2410
|
+
React__default["default"].createElement(SpecialtyIcon, null)),
|
|
2411
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, t('booking.searchBar.allSpecialties'))),
|
|
2412
|
+
state.allSpecialties.map((specialty) => (React__default["default"].createElement(StyledSpecialtyItem, { key: specialty.id, onClick: (evt) => {
|
|
2413
|
+
evt.nativeEvent.stopImmediatePropagation();
|
|
2414
|
+
if (onSpecialtyClick) {
|
|
2415
|
+
onSpecialtyClick(Object.assign(Object.assign({}, specialty), { total_doctor: 0 }));
|
|
2416
|
+
}
|
|
2417
|
+
}, role: "button", tabIndex: 0, "aria-label": `Select ${specialty.name} as location`, isSelected: (selectedLocation === null || selectedLocation === void 0 ? void 0 : selectedLocation.id) === specialty.id },
|
|
2418
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2419
|
+
React__default["default"].createElement("img", { src: specialty.thumbnail, alt: specialty.name })),
|
|
2420
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, specialty.name))))))));
|
|
2421
|
+
};
|
|
2422
|
+
|
|
2423
|
+
const SearchInputs = ({ state, type, isMobile, isLoading, initalSearchValue, typeInformation, debouncedFetchSearchResults, trackingAttributes, hideSpecialtySelection = false, clientSlug = '', focusSearchInput, onSearch, onEnterSearch, dispatch, }) => {
|
|
2424
|
+
var _a;
|
|
2425
|
+
const { t } = useTranslations.useTranslations();
|
|
2426
|
+
const inputSearchWrapperRef = React.useRef(null);
|
|
2427
|
+
const gaAttributes = React.useMemo(() => {
|
|
2428
|
+
if (trackingAttributes) {
|
|
2429
|
+
return {
|
|
2430
|
+
'data-event-category': trackingAttributes.dataEventCategory,
|
|
2431
|
+
'data-event-action': trackingAttributes.dataEventAction,
|
|
2432
|
+
'data-event-label': trackingAttributes.dataEventLabel,
|
|
2433
|
+
};
|
|
2434
|
+
}
|
|
2435
|
+
else {
|
|
2436
|
+
return {};
|
|
2437
|
+
}
|
|
2438
|
+
}, [trackingAttributes]);
|
|
2439
|
+
const placeholderSearch = React.useMemo(() => {
|
|
2440
|
+
if (type === 'doctor') {
|
|
2441
|
+
return t('booking.searchBar.placeholder.doctor');
|
|
2442
|
+
}
|
|
2443
|
+
if (type === 'service') {
|
|
2444
|
+
return t('booking.searchBar.placeholder.service');
|
|
2445
|
+
}
|
|
2446
|
+
if (type === 'hospital') {
|
|
2447
|
+
return t('booking.searchBar.placeholder.hospital');
|
|
2448
|
+
}
|
|
2449
|
+
if (type === 'specialty') {
|
|
2450
|
+
return t('booking.searchBar.placeholder.specialty');
|
|
2451
|
+
}
|
|
2452
|
+
return '';
|
|
2453
|
+
}, [type]);
|
|
2454
|
+
const styleInputWrapper = React.useMemo(() => {
|
|
2455
|
+
return {
|
|
2456
|
+
root: {
|
|
2457
|
+
flex: 1,
|
|
2458
|
+
'&.hide-specialty-selection': {
|
|
2459
|
+
'.mantine-Input-rightSection': {
|
|
2460
|
+
display: 'none',
|
|
2461
|
+
},
|
|
2462
|
+
input: {
|
|
2463
|
+
paddingLeft: '48px',
|
|
2464
|
+
},
|
|
2465
|
+
'.mantine-Input-icon': {
|
|
2466
|
+
left: '0',
|
|
2467
|
+
},
|
|
2468
|
+
},
|
|
2469
|
+
},
|
|
2470
|
+
};
|
|
2471
|
+
}, []);
|
|
2472
|
+
const styleInput = React.useMemo(() => {
|
|
2473
|
+
return {
|
|
2474
|
+
icon: {
|
|
2475
|
+
left: '165px',
|
|
2476
|
+
},
|
|
2477
|
+
input: {
|
|
2478
|
+
color: '#262626',
|
|
2479
|
+
'&[data-with-icon="true"]': {
|
|
2480
|
+
paddingLeft: '205px',
|
|
2481
|
+
paddingRight: '16px',
|
|
2482
|
+
},
|
|
2483
|
+
},
|
|
2484
|
+
rightSection: {
|
|
2485
|
+
left: 0,
|
|
2486
|
+
width: '165px',
|
|
2487
|
+
padding: '1px',
|
|
2488
|
+
},
|
|
2489
|
+
};
|
|
2490
|
+
}, []);
|
|
2491
|
+
const styleInputSpecialties = React.useMemo(() => {
|
|
2492
|
+
return {
|
|
2493
|
+
input: {
|
|
2494
|
+
color: '#262626',
|
|
2495
|
+
},
|
|
2496
|
+
};
|
|
2497
|
+
}, []);
|
|
2498
|
+
useOutsideClick.useOutsideClick(inputSearchWrapperRef, () => {
|
|
2499
|
+
dispatch({ type: ActionTypes.ClickOutsideInputSearch });
|
|
2500
|
+
});
|
|
2501
|
+
const handleSearchInputChange = React.useCallback(function handleSearchInputChange(value) {
|
|
2502
|
+
dispatch({ type: ActionTypes.ChangeInputSearch, payload: value });
|
|
2503
|
+
if (typeof onSearch === 'function') {
|
|
2504
|
+
return;
|
|
2505
|
+
}
|
|
2506
|
+
if (value.trim().length > SEARCH_KEYWORD_MIN_LENGTH[state.locale] ||
|
|
2507
|
+
initalSearchValue ||
|
|
2508
|
+
value.trim().length === 0) {
|
|
2509
|
+
debouncedFetchSearchResults(value.trim(), state, type, clientSlug);
|
|
2510
|
+
}
|
|
2511
|
+
else {
|
|
2512
|
+
debouncedFetchSearchResults.cancel();
|
|
2513
|
+
dispatch({ type: ActionTypes.DisplayInitialSearchResults });
|
|
2514
|
+
}
|
|
2515
|
+
}, [dispatch, state, type]);
|
|
2516
|
+
const handleSpecialtyClick = React.useCallback(function handleSpecialtyClick(specialty) {
|
|
2517
|
+
dispatch({ type: ActionTypes.SelectSpecialty, payload: specialty });
|
|
2518
|
+
focusSearchInput();
|
|
2519
|
+
}, [dispatch]);
|
|
2520
|
+
const inputOnKeyDown = React.useCallback((e) => {
|
|
2521
|
+
if (e.keyCode === 13) {
|
|
2522
|
+
e.stopPropagation();
|
|
2523
|
+
e.preventDefault();
|
|
2524
|
+
onEnterSearch && onEnterSearch();
|
|
2525
|
+
}
|
|
2526
|
+
}, [onEnterSearch]);
|
|
2527
|
+
return (React__default["default"].createElement(StyleSearchInputsWrapper, { ref: inputSearchWrapperRef }, type === 'specialty' ? (React__default["default"].createElement(core.Input.Wrapper, { styles: styleInputWrapper },
|
|
2528
|
+
React__default["default"].createElement(core.Input, { icon: React__default["default"].createElement(core$1.Search, null), size: isMobile ? 'md' : 'lg', placeholder: placeholderSearch, styles: styleInputSpecialties, value: state.searchKeywords, onFocus: () => dispatch({ type: ActionTypes.FocusInputSearchSpecialty }), onChange: (event) => {
|
|
2529
|
+
handleSearchInputChange(event.target.value);
|
|
2530
|
+
}, onKeyDown: inputOnKeyDown }))) : (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
2531
|
+
type === 'service' ? (React__default["default"].createElement(core.Input.Wrapper, { styles: styleInputWrapper },
|
|
2532
|
+
React__default["default"].createElement(core.Input, { icon: React__default["default"].createElement(core$1.Search, null), size: isMobile ? 'md' : 'lg', name: "search-results", placeholder: placeholderSearch, onFocus: () => dispatch({ type: ActionTypes.FocusInputSearch }), value: state.searchKeywords, onChange: (event) => {
|
|
2533
|
+
handleSearchInputChange(event.target.value);
|
|
2534
|
+
}, onKeyDown: inputOnKeyDown }))) : (React__default["default"].createElement(React__default["default"].Fragment, null, isMobile && !hideSpecialtySelection ? (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
2535
|
+
React__default["default"].createElement(SearchSpecialty, { state: state, isMobile: isMobile, dispatch: dispatch, debouncedFetchSearchResults: debouncedFetchSearchResults, onSpecialtyClick: handleSpecialtyClick }),
|
|
2536
|
+
React__default["default"].createElement(core.Input.Wrapper, { styles: styleInputWrapper },
|
|
2537
|
+
React__default["default"].createElement(core.Input, { icon: React__default["default"].createElement(core$1.Search, null), size: "md", placeholder: placeholderSearch, value: state.searchKeywords, name: "search-results", onFocus: () => dispatch({ type: ActionTypes.FocusInputSearch }), onChange: (event) => {
|
|
2538
|
+
handleSearchInputChange(event.target.value);
|
|
2539
|
+
}, onKeyDown: inputOnKeyDown })))) : (React__default["default"].createElement(core.Input.Wrapper, { styles: styleInputWrapper, className: hideSpecialtySelection ? 'hide-specialty-selection' : '' },
|
|
2540
|
+
React__default["default"].createElement(core.Input, Object.assign({ icon: React__default["default"].createElement(core$1.Search, null), size: "lg", placeholder: placeholderSearch, styles: styleInput, name: "search-results", autoComplete: "off", value: state.searchKeywords, onChange: (event) => {
|
|
2541
|
+
handleSearchInputChange(event.target.value);
|
|
2542
|
+
}, onFocus: () => dispatch({ type: ActionTypes.FocusInputSearch }), onKeyDown: inputOnKeyDown }, gaAttributes, { rightSection: hideSpecialtySelection ? (React__default["default"].createElement(React__default["default"].Fragment, null)) : (React__default["default"].createElement(SearchSpecialty, { state: state, isMobile: isMobile, dispatch: dispatch, debouncedFetchSearchResults: debouncedFetchSearchResults, onSpecialtyClick: handleSpecialtyClick })) })))))),
|
|
2543
|
+
state.focused === 'search' && (React__default["default"].createElement(StyleResultWrapper$2, null,
|
|
2544
|
+
React__default["default"].createElement(SearchResult, { type: type, state: state, results: ((_a = state.searchResults) === null || _a === void 0 ? void 0 : _a[type]) || [], location: state.selectedLocation.name, dispatch: dispatch, isLoading: isLoading, typeInformation: typeInformation, clientSlug: clientSlug })))))));
|
|
2545
|
+
};
|
|
2546
|
+
|
|
2547
|
+
const StyleSearchLocationWrapper = styled__default["default"].div `
|
|
2548
|
+
position: relative;
|
|
2549
|
+
|
|
2550
|
+
${utils.MediaQueries.mbDown} {
|
|
2551
|
+
width: 100%;
|
|
2552
|
+
display: flex;
|
|
2553
|
+
flex-direction: column;
|
|
2554
|
+
gap: 12px;
|
|
2555
|
+
}
|
|
2556
|
+
`;
|
|
2557
|
+
const StyleResultWrapper = styled__default["default"].div `
|
|
2558
|
+
position: absolute;
|
|
2559
|
+
top: calc(100% + 2px);
|
|
2560
|
+
width: 100%;
|
|
2561
|
+
border-radius: 4px;
|
|
2562
|
+
background: ${theme.theme.colors.white};
|
|
2563
|
+
box-shadow: 0px 8px 40px 0px rgba(0, 0, 0, 0.1);
|
|
2564
|
+
z-index: 10;
|
|
2565
|
+
|
|
2566
|
+
${utils.MediaQueries.mbDown} {
|
|
2567
|
+
width: calc(100% + 64px);
|
|
2568
|
+
left: -32px;
|
|
2569
|
+
}
|
|
2570
|
+
`;
|
|
2571
|
+
const StyledLocationItem = styled__default["default"].li `
|
|
2572
|
+
position: relative;
|
|
2573
|
+
cursor: pointer;
|
|
2574
|
+
padding: 12px 18px;
|
|
2575
|
+
display: flex;
|
|
2576
|
+
align-items: center;
|
|
2577
|
+
gap: 14px;
|
|
2578
|
+
overflow: hidden;
|
|
2579
|
+
|
|
2580
|
+
${({ isSelected }) => isSelected &&
|
|
2581
|
+
`
|
|
2582
|
+
&::after {
|
|
2583
|
+
content: ${checkMarkIconUrl};
|
|
2584
|
+
top: 50%;
|
|
2585
|
+
right: 18px;
|
|
2586
|
+
position: absolute;
|
|
2587
|
+
transform: translateY(-50%);
|
|
2588
|
+
}
|
|
2589
|
+
`}
|
|
2590
|
+
|
|
2591
|
+
& + li::before {
|
|
2592
|
+
content: '';
|
|
2593
|
+
position: absolute;
|
|
2594
|
+
left: 18px;
|
|
2595
|
+
right: 18px;
|
|
2596
|
+
top: 0;
|
|
2597
|
+
height: 1px;
|
|
2598
|
+
background-color: ${theme.theme.colors.neutral100};
|
|
2599
|
+
}
|
|
2600
|
+
|
|
2601
|
+
&:not([data-is-denied='true']):hover {
|
|
2602
|
+
background-color: ${theme.theme.colors.neutral50};
|
|
2603
|
+
}
|
|
2604
|
+
|
|
2605
|
+
&:last-child:hover {
|
|
2606
|
+
border-bottom-right-radius: 6px;
|
|
2607
|
+
border-bottom-left-radius: 6px;
|
|
2608
|
+
}
|
|
2609
|
+
|
|
2610
|
+
&:first-child:hover {
|
|
2611
|
+
border-top-right-radius: 6px;
|
|
2612
|
+
border-top-left-radius: 6px;
|
|
2613
|
+
}
|
|
2614
|
+
|
|
2615
|
+
&[data-is-denied='true'] {
|
|
2616
|
+
cursor: not-allowed;
|
|
2617
|
+
}
|
|
2618
|
+
`;
|
|
2619
|
+
const StyledPinIcon = styled__default["default"](PinIcon) `
|
|
2620
|
+
width: 12px;
|
|
2621
|
+
height: 18px;
|
|
2622
|
+
flex: 0 0 12px;
|
|
2623
|
+
`;
|
|
2624
|
+
|
|
2625
|
+
const SearchLocation = ({ state, isMobile, debouncedFetchCitiesByKeyword, selectedLocation, trackingAttributes, onLocationClick, dispatch, }) => {
|
|
2626
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
2627
|
+
const inputLocationWrapperRef = React.useRef(null);
|
|
2628
|
+
const gaAttributes = React.useMemo(() => {
|
|
2629
|
+
if (trackingAttributes) {
|
|
2630
|
+
return {
|
|
2631
|
+
'data-event-category': trackingAttributes.dataEventCategory,
|
|
2632
|
+
'data-event-action': trackingAttributes.dataEventAction,
|
|
2633
|
+
'data-event-label': trackingAttributes.dataEventLabel,
|
|
2634
|
+
};
|
|
2635
|
+
}
|
|
2636
|
+
else {
|
|
2637
|
+
return {};
|
|
2638
|
+
}
|
|
2639
|
+
}, [trackingAttributes]);
|
|
2640
|
+
const handleSearchLocationInputChange = React.useCallback(function handleSearchLocationInputChange(value) {
|
|
2641
|
+
dispatch({ type: ActionTypes.ChangeInputLocation, payload: value });
|
|
2642
|
+
if (value.trim().length > SEARCH_KEYWORD_MIN_LENGTH[state.locale]) {
|
|
2643
|
+
debouncedFetchCitiesByKeyword(value.trim());
|
|
2644
|
+
}
|
|
2645
|
+
else {
|
|
2646
|
+
debouncedFetchCitiesByKeyword.cancel();
|
|
2647
|
+
dispatch({ type: ActionTypes.DisplayInitialCities });
|
|
2648
|
+
}
|
|
2649
|
+
}, [debouncedFetchCitiesByKeyword, dispatch]);
|
|
2650
|
+
useOutsideClick.useOutsideClick(inputLocationWrapperRef, () => {
|
|
2651
|
+
dispatch({ type: ActionTypes.ClickOutsideInputLocation });
|
|
2652
|
+
});
|
|
2653
|
+
return (React__default["default"].createElement(StyleSearchLocationWrapper, { ref: inputLocationWrapperRef },
|
|
2654
|
+
React__default["default"].createElement(core.Input.Wrapper, null,
|
|
2655
|
+
React__default["default"].createElement(core.Input, Object.assign({ size: isMobile ? 'md' : 'lg', placeholder: "Search location", value: state.searchLocationKeywords, onFocus: () => dispatch({ type: ActionTypes.FocusInputLocation }), onChange: (event) => {
|
|
2656
|
+
handleSearchLocationInputChange(event.target.value);
|
|
2657
|
+
} }, gaAttributes))),
|
|
2658
|
+
state.focused === 'location' && (React__default["default"].createElement(StyleResultWrapper, null,
|
|
2659
|
+
React__default["default"].createElement(StyledLocationItem, { key: "all-location", role: "button", tabIndex: 0, onClick: () => {
|
|
2660
|
+
var _a;
|
|
2661
|
+
if (onLocationClick) {
|
|
2662
|
+
onLocationClick({
|
|
2663
|
+
name: t('booking.searchBar.allLocations'),
|
|
2664
|
+
id: constants.ID_OPTION_ALL_LOCATION,
|
|
2665
|
+
slug: (_a = constants.LOCALIZED_SLUGS[locale]) === null || _a === void 0 ? void 0 : _a.ALL,
|
|
2666
|
+
});
|
|
2667
|
+
}
|
|
2668
|
+
} },
|
|
2669
|
+
React__default["default"].createElement(StyledPinIcon, { color: theme.theme.colors.neutral400 }),
|
|
2670
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, t('booking.searchBar.allLocations'))),
|
|
2671
|
+
state.cities.map((city) => (React__default["default"].createElement(StyledLocationItem, { key: city.id, onClick: (evt) => {
|
|
2672
|
+
evt.nativeEvent.stopImmediatePropagation();
|
|
2673
|
+
if (onLocationClick) {
|
|
2674
|
+
onLocationClick(city);
|
|
2675
|
+
}
|
|
2676
|
+
}, role: "button", tabIndex: 0, "aria-label": `Select ${city.name} as location`, isSelected: (selectedLocation === null || selectedLocation === void 0 ? void 0 : selectedLocation.id) === city.id },
|
|
2677
|
+
React__default["default"].createElement(StyledPinIcon, { color: theme.theme.colors.neutral400 }),
|
|
2678
|
+
React__default["default"].createElement(index$2.Text, { size: "md" }, city.name))))))));
|
|
2679
|
+
};
|
|
2680
|
+
|
|
2681
|
+
const StyleSpecialtiesWrapper = styled__default["default"].div `
|
|
2682
|
+
display: flex;
|
|
2683
|
+
flex-wrap: wrap;
|
|
2684
|
+
row-gap: 8px;
|
|
2685
|
+
column-gap: 20px;
|
|
2686
|
+
${utils.MediaQueries.mbDown} {
|
|
2687
|
+
margin-top: 12px;
|
|
2688
|
+
}
|
|
2689
|
+
`;
|
|
2690
|
+
const StyleSpecialtyItem = styled__default["default"].div `
|
|
2691
|
+
display: flex;
|
|
2692
|
+
align-items: center;
|
|
2693
|
+
border-radius: 8px;
|
|
2694
|
+
border: 1px solid ${theme.theme.colors.neutral100};
|
|
2695
|
+
background: ${theme.theme.colors.white};
|
|
2696
|
+
padding: 8px 12px 8px 8px;
|
|
2697
|
+
flex: 0 0 calc(33.3% - 13px);
|
|
2698
|
+
gap: 12px;
|
|
2699
|
+
cursor: pointer;
|
|
2700
|
+
|
|
2701
|
+
&:hover {
|
|
2702
|
+
background: ${theme.theme.colors.blue50};
|
|
2703
|
+
}
|
|
2704
|
+
|
|
2705
|
+
${utils.MediaQueries.tdDown} {
|
|
2706
|
+
flex: 0 0 calc(50% - 10px);
|
|
2707
|
+
}
|
|
2708
|
+
|
|
2709
|
+
${utils.MediaQueries.mbDown} {
|
|
2710
|
+
flex: 0 0 100%;
|
|
2711
|
+
border: none;
|
|
2712
|
+
}
|
|
2713
|
+
|
|
2714
|
+
.image-item {
|
|
2715
|
+
display: flex;
|
|
2716
|
+
align-items: center;
|
|
2717
|
+
width: 40px;
|
|
2718
|
+
height: 40px;
|
|
2719
|
+
|
|
2720
|
+
img {
|
|
2721
|
+
width: 100%;
|
|
2722
|
+
object-fit: cover;
|
|
2723
|
+
}
|
|
2724
|
+
}
|
|
2725
|
+
|
|
2726
|
+
.infor {
|
|
2727
|
+
flex: 1;
|
|
2728
|
+
.title {
|
|
2729
|
+
color: ${theme.theme.colors.gray800};
|
|
2730
|
+
font-size: 14px;
|
|
2731
|
+
font-style: normal;
|
|
2732
|
+
font-weight: 400;
|
|
2733
|
+
line-height: 22px;
|
|
2734
|
+
}
|
|
2735
|
+
|
|
2736
|
+
.description {
|
|
2737
|
+
color: ${theme.theme.colors.gray600};
|
|
2738
|
+
font-size: 12px;
|
|
2739
|
+
font-weight: 400;
|
|
2740
|
+
line-height: 18px;
|
|
2741
|
+
}
|
|
2742
|
+
}
|
|
2743
|
+
`;
|
|
2744
|
+
const StyleDivider = styled__default["default"](core.Divider) `
|
|
2745
|
+
margin: 24px 0 !important;
|
|
2746
|
+
`;
|
|
2747
|
+
const StyleShowMore = styled__default["default"].div `
|
|
2748
|
+
display: flex;
|
|
2749
|
+
justify-content: center;
|
|
2750
|
+
margin-top: 24px;
|
|
2751
|
+
.show-more {
|
|
2752
|
+
border-radius: 4px;
|
|
2753
|
+
border: 1px solid ${theme.theme.colors.neutral200};
|
|
2754
|
+
padding: 12px 16px;
|
|
2755
|
+
cursor: pointer;
|
|
2756
|
+
display: inline-block;
|
|
2757
|
+
color: ${theme.theme.colors.gray800};
|
|
2758
|
+
font-size: 16px;
|
|
2759
|
+
font-weight: 600;
|
|
2760
|
+
line-height: 24px;
|
|
2761
|
+
|
|
2762
|
+
${utils.MediaQueries.mbDown} {
|
|
2763
|
+
width: 100%;
|
|
2764
|
+
text-align: center;
|
|
2765
|
+
}
|
|
2766
|
+
}
|
|
2767
|
+
`;
|
|
2768
|
+
|
|
2769
|
+
const SearchResultSpecialties = ({ state, isMobile, specialties, isLoading, dispatch, }) => {
|
|
2770
|
+
const { t, locale } = useTranslations.useTranslations();
|
|
2771
|
+
const { selectedLocation } = state;
|
|
2772
|
+
const slugs = React.useMemo(() => constants.LOCALIZED_SLUGS[locale], [locale]);
|
|
2773
|
+
const handleOnClick = (specialtySlug) => {
|
|
2774
|
+
let url = '';
|
|
2775
|
+
if (specialtySlug === constants.SLUG_VACIN_ID) {
|
|
2776
|
+
url = `/${selectedLocation.slug}/${slugs.HOSPITAL}/${constants.CLIENT_KEY.GSK}/`;
|
|
2777
|
+
dispatch({ type: ActionTypes.ClickOutsideInputSearchSpecialty });
|
|
2778
|
+
}
|
|
2779
|
+
else {
|
|
2780
|
+
url = `/${selectedLocation.slug}/${slugs.DOCTOR}/${specialtySlug}`;
|
|
2781
|
+
}
|
|
2782
|
+
dispatch({ type: ActionTypes.NavigateTo, payload: url });
|
|
2783
|
+
};
|
|
2784
|
+
const handleShowMore = () => {
|
|
2785
|
+
const url = `/${slugs.SPECIALTIES}`;
|
|
2786
|
+
dispatch({ type: ActionTypes.NavigateTo, payload: url });
|
|
2787
|
+
};
|
|
2788
|
+
const showSeeMore = React.useMemo(() => {
|
|
2789
|
+
return (specialties.length >= 9 ||
|
|
2790
|
+
state.searchKeywords.trim().length <=
|
|
2791
|
+
SEARCH_KEYWORD_MIN_LENGTH[state.locale]);
|
|
2792
|
+
}, [state.searchKeywords, specialties]);
|
|
2793
|
+
return (React__default["default"].createElement(React__default["default"].Fragment, null,
|
|
2794
|
+
!isMobile && React__default["default"].createElement(StyleDivider, { color: "#E4E8EC" }),
|
|
2795
|
+
React__default["default"].createElement(StyleSpecialtiesWrapper, null,
|
|
2796
|
+
specialties.length > 0 && !isLoading && (React__default["default"].createElement(React__default["default"].Fragment, null, specialties.map((specialty, index) => {
|
|
2797
|
+
if (index >= 9) {
|
|
2798
|
+
return React__default["default"].createElement(React__default["default"].Fragment, null);
|
|
2799
|
+
}
|
|
2800
|
+
return (React__default["default"].createElement(StyleSpecialtyItem, { key: specialty.id, onClick: () => handleOnClick(specialty.slug) },
|
|
2801
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2802
|
+
React__default["default"].createElement("img", { src: specialty.thumbnail, alt: specialty.name })),
|
|
2803
|
+
React__default["default"].createElement("div", { className: "infor" },
|
|
2804
|
+
React__default["default"].createElement("div", { className: "title" }, specialty.name))));
|
|
2805
|
+
}))),
|
|
2806
|
+
specialties.length === 0 && !isLoading && (React__default["default"].createElement(index$2.Text, { size: "sm", color: theme.theme.colors.gray400 }, t('booking.searchBar.noResults'))),
|
|
2807
|
+
isLoading &&
|
|
2808
|
+
Array(6)
|
|
2809
|
+
.fill(undefined)
|
|
2810
|
+
.map((_, i) => (React__default["default"].createElement(StyleSpecialtyItem, { key: 'loading' + i },
|
|
2811
|
+
React__default["default"].createElement("div", { className: "image-item" },
|
|
2812
|
+
React__default["default"].createElement(core.Skeleton, { height: 40, animate: true })),
|
|
2813
|
+
React__default["default"].createElement("div", { className: "infor" },
|
|
2814
|
+
React__default["default"].createElement("div", { className: "title" },
|
|
2815
|
+
React__default["default"].createElement(core.Skeleton, { height: 20, radius: "sm", animate: true }))))))),
|
|
2816
|
+
showSeeMore && (React__default["default"].createElement(StyleShowMore, null,
|
|
2817
|
+
React__default["default"].createElement("div", { className: "show-more", onClick: handleShowMore }, t('home.seeAll'))))));
|
|
2818
|
+
};
|
|
2819
|
+
|
|
2820
|
+
const StyleSearchTagWrapper = styled__default["default"].div `
|
|
2821
|
+
display: flex;
|
|
2822
|
+
gap: 5px;
|
|
2823
|
+
margin-top: 16px;
|
|
2824
|
+
flex-wrap: wrap;
|
|
2825
|
+
`;
|
|
2826
|
+
const StyleTagItem = styled__default["default"].div `
|
|
2827
|
+
color: ${theme.theme.colors.gray600};
|
|
2828
|
+
font-size: 14px;
|
|
2829
|
+
font-weight: 600;
|
|
2830
|
+
line-height: 22px;
|
|
2831
|
+
padding: 4px 12px;
|
|
2832
|
+
background: ${theme.theme.colors.white};
|
|
2833
|
+
border-radius: 32px;
|
|
2834
|
+
cursor: pointer;
|
|
2835
|
+
border: 1px solid ${theme.theme.colors.white};
|
|
2836
|
+
margin-bottom: 5px;
|
|
2837
|
+
border-color: ${theme.theme.colors.neutral100};
|
|
2838
|
+
background: #f7f9fc;
|
|
2839
|
+
|
|
2840
|
+
&.view-all {
|
|
2841
|
+
border-radius: 32px;
|
|
2842
|
+
border-color: ${theme.theme.colors.blue50};
|
|
2843
|
+
background: ${theme.theme.colors.blue50};
|
|
2844
|
+
color: ${theme.theme.colors.blue600};
|
|
2845
|
+
|
|
2846
|
+
&:hover {
|
|
2847
|
+
border-color: ${theme.theme.colors.blue50};
|
|
2848
|
+
background: ${theme.theme.colors.blue50};
|
|
2849
|
+
color: ${theme.theme.colors.blue600};
|
|
2850
|
+
}
|
|
2851
|
+
}
|
|
2852
|
+
|
|
2853
|
+
&:hover {
|
|
2854
|
+
border-color: ${theme.theme.colors.neutral100};
|
|
2855
|
+
background: #f7f9fc;
|
|
2856
|
+
}
|
|
2857
|
+
`;
|
|
2858
|
+
const StyleTagLabel = styled__default["default"].div `
|
|
2859
|
+
color: ${theme.theme.colors.gray600};
|
|
2860
|
+
font-size: 14px;
|
|
2861
|
+
font-weight: 600;
|
|
2862
|
+
line-height: 22px;
|
|
2863
|
+
padding: 4px 0;
|
|
2864
|
+
background: ${theme.theme.colors.white};
|
|
2865
|
+
border-radius: 32px;
|
|
2866
|
+
border: 1px solid ${theme.theme.colors.white};
|
|
2867
|
+
margin-bottom: 5px;
|
|
2868
|
+
margin-right: 7px;
|
|
2869
|
+
`;
|
|
2870
|
+
|
|
2871
|
+
const SearchTag = ({ state, type, typeInformation, dispatch }) => {
|
|
2872
|
+
const { t } = useTranslations.useTranslations();
|
|
2873
|
+
const { selectedLocation } = state;
|
|
2874
|
+
const typeSlug = React.useMemo(() => typeInformation[type].slug, [typeInformation, type]);
|
|
2875
|
+
const handleViewAll = () => {
|
|
2876
|
+
const url = `/${selectedLocation.slug}/${typeSlug}`;
|
|
2877
|
+
if (url) {
|
|
2878
|
+
dispatch({ type: ActionTypes.NavigateTo, payload: url });
|
|
2879
|
+
}
|
|
2880
|
+
};
|
|
2881
|
+
const handleClickKeyword = (keyword) => {
|
|
2882
|
+
if (keyword.url) {
|
|
2883
|
+
window.location.href = keyword.url;
|
|
2884
|
+
}
|
|
2885
|
+
};
|
|
2886
|
+
return (React__default["default"].createElement(StyleSearchTagWrapper, null,
|
|
2887
|
+
React__default["default"].createElement(StyleTagLabel, null, t('booking.searchBar.popularKey')),
|
|
2888
|
+
state.popularKeys.map((item) => {
|
|
2889
|
+
return (React__default["default"].createElement(StyleTagItem, { key: item.id, onClick: () => handleClickKeyword(item) }, item.keyword));
|
|
2890
|
+
}),
|
|
2891
|
+
React__default["default"].createElement(StyleTagItem, { className: "view-all", onClick: handleViewAll }, t('booking.searchBar.viewAll'))));
|
|
2892
|
+
};
|
|
2893
|
+
|
|
2894
|
+
const StyledTabWrapper = styled__default["default"].div `
|
|
2895
|
+
background: rgba(255, 255, 255, 0.64);
|
|
2896
|
+
backdrop-filter: blur(12px);
|
|
2897
|
+
border-bottom: 1px solid ${theme.theme.colors.neutral100};
|
|
2898
|
+
`;
|
|
2899
|
+
const StyleTabContainer = styled__default["default"](index$3.Container) `
|
|
2900
|
+
padding: 0 16px;
|
|
2901
|
+
`;
|
|
2902
|
+
|
|
2903
|
+
const itemTabs = () => {
|
|
2904
|
+
const { t } = useTranslations.useTranslations();
|
|
2905
|
+
return [
|
|
2906
|
+
{
|
|
2907
|
+
value: 'hospital',
|
|
2908
|
+
label: t('booking.searchPopup.hospitals'),
|
|
2909
|
+
},
|
|
2910
|
+
{
|
|
2911
|
+
value: 'doctor',
|
|
2912
|
+
label: t('booking.searchPopup.doctors'),
|
|
2913
|
+
},
|
|
2914
|
+
{
|
|
2915
|
+
value: 'service',
|
|
2916
|
+
label: t('booking.searchPopup.services'),
|
|
2917
|
+
},
|
|
2918
|
+
{
|
|
2919
|
+
value: 'specialty',
|
|
2920
|
+
label: t('booking.searchPopup.specialties'),
|
|
2921
|
+
},
|
|
2922
|
+
];
|
|
2923
|
+
};
|
|
2924
|
+
const TabSearch = ({ currentTab, hideTabBookingSearch = [], isMobile, setCurrentTab, }) => {
|
|
2925
|
+
const stylesTabs = React.useMemo(() => {
|
|
2926
|
+
return {
|
|
2927
|
+
root: {
|
|
2928
|
+
overflowY: isMobile ? 'hidden' : 'initial',
|
|
2929
|
+
overflowX: isMobile ? 'auto' : 'initial',
|
|
2930
|
+
},
|
|
2931
|
+
tabsList: {
|
|
2932
|
+
background: 'rgba(255, 255, 255, 0)',
|
|
2933
|
+
borderBottom: 'none',
|
|
2934
|
+
flexWrap: 'nowrap',
|
|
2935
|
+
'.mantine-Tabs-tab': {
|
|
2936
|
+
'&:last-child': {
|
|
2937
|
+
'&:after': {
|
|
2938
|
+
display: 'none',
|
|
2939
|
+
},
|
|
2940
|
+
},
|
|
2941
|
+
},
|
|
2942
|
+
},
|
|
2943
|
+
tab: {
|
|
2944
|
+
padding: isMobile ? '12px 16px 12px 16px' : '15px 40px 15px 40px',
|
|
2945
|
+
borderTop: '2px solid transparent',
|
|
2946
|
+
borderBottom: 'none',
|
|
2947
|
+
margin: 0,
|
|
2948
|
+
borderRadius: 0,
|
|
2949
|
+
position: 'relative',
|
|
2950
|
+
width: 'auto',
|
|
2951
|
+
'&[data-active="true"]': {
|
|
2952
|
+
borderColor: '#2d87f3',
|
|
2953
|
+
backgroundColor: '#ffffff',
|
|
2954
|
+
'&:after': {
|
|
2955
|
+
display: 'none',
|
|
2956
|
+
},
|
|
2957
|
+
'&:before': {
|
|
2958
|
+
content: '""',
|
|
2959
|
+
width: '100%',
|
|
2960
|
+
height: '1px',
|
|
2961
|
+
position: 'absolute',
|
|
2962
|
+
backgroundColor: '#ffffff',
|
|
2963
|
+
bottom: '-1px',
|
|
2964
|
+
},
|
|
2965
|
+
},
|
|
2966
|
+
'&:hover': {
|
|
2967
|
+
borderColor: '#2d87f3',
|
|
2968
|
+
backgroundColor: '#ffffff',
|
|
2969
|
+
'&:before': {
|
|
2970
|
+
content: '""',
|
|
2971
|
+
width: '100%',
|
|
2972
|
+
height: '1px',
|
|
2973
|
+
position: 'absolute',
|
|
2974
|
+
backgroundColor: '#ffffff',
|
|
2975
|
+
bottom: '-1px',
|
|
2976
|
+
},
|
|
2977
|
+
},
|
|
2978
|
+
'&:after': {
|
|
2979
|
+
content: '""',
|
|
2980
|
+
width: '1px',
|
|
2981
|
+
height: '24px',
|
|
2982
|
+
backgroundColor: '#E4E8EC',
|
|
2983
|
+
position: 'absolute',
|
|
2984
|
+
right: '-1px',
|
|
2985
|
+
},
|
|
2986
|
+
},
|
|
2987
|
+
tabLabel: {
|
|
2988
|
+
color: '#595959',
|
|
2989
|
+
fontSize: isMobile ? '14px' : '16px',
|
|
2990
|
+
fontWeight: 600,
|
|
2991
|
+
lineHeight: isMobile ? '22px' : '24px',
|
|
2992
|
+
},
|
|
2993
|
+
};
|
|
2994
|
+
}, [isMobile]);
|
|
2995
|
+
const tabConfig = itemTabs();
|
|
2996
|
+
const activeTabs = React.useMemo(() => {
|
|
2997
|
+
return (tabConfig.filter((item) => !hideTabBookingSearch.includes(item.value)) ||
|
|
2998
|
+
[]);
|
|
2999
|
+
}, [hideTabBookingSearch, tabConfig]);
|
|
3000
|
+
return (React__default["default"].createElement(StyledTabWrapper, { className: "booking-search-tab" },
|
|
3001
|
+
React__default["default"].createElement(StyleTabContainer, null,
|
|
3002
|
+
React__default["default"].createElement(core.Tabs, { value: currentTab, onTabChange: (tab) => {
|
|
3003
|
+
setCurrentTab(tab);
|
|
3004
|
+
}, styles: stylesTabs },
|
|
3005
|
+
React__default["default"].createElement(core.Tabs.List, null, activeTabs.map((tab) => {
|
|
3006
|
+
return (React__default["default"].createElement(core.Tabs.Tab, { value: tab.value, key: tab.value }, tab.label));
|
|
3007
|
+
}))))));
|
|
3008
|
+
};
|
|
3009
|
+
|
|
3010
|
+
var TypePopularKeySearch;
|
|
3011
|
+
(function (TypePopularKeySearch) {
|
|
3012
|
+
TypePopularKeySearch["doctor"] = "doctor";
|
|
3013
|
+
TypePopularKeySearch["service"] = "hospital_service";
|
|
3014
|
+
TypePopularKeySearch["hospital"] = "hospital_branch";
|
|
3015
|
+
})(TypePopularKeySearch || (TypePopularKeySearch = {}));
|
|
3016
|
+
|
|
3017
|
+
function useSearchBarApi({ dispatch, careApiDomain, locale = 'vi-VN', client = '', }) {
|
|
3018
|
+
const fetchCitiesApi = React.useCallback(function fetchCitiesApi(path, params = {}) {
|
|
3019
|
+
const url = `${careApiDomain}${path}`;
|
|
3020
|
+
dispatch({ type: ActionTypes.FetchCitiesStart });
|
|
3021
|
+
return fetch(getApiPath(url, params, locale), { method: 'GET' })
|
|
3022
|
+
.then((res) => res.json())
|
|
3023
|
+
.then((data) => {
|
|
3024
|
+
if (data._status !== 1 || !data._data) {
|
|
3025
|
+
console.log('error loading cities', data);
|
|
3026
|
+
return Promise.reject(data);
|
|
3027
|
+
}
|
|
3028
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
3029
|
+
})
|
|
3030
|
+
.finally(() => dispatch({ type: ActionTypes.FetchCitiesFinish }));
|
|
3031
|
+
}, [locale]);
|
|
3032
|
+
const fetchCitiesByLocation = React.useCallback(function fetchCitiesByLocation({ coordinates }) {
|
|
3033
|
+
let params = {};
|
|
3034
|
+
const moreParams = {};
|
|
3035
|
+
if (coordinates) {
|
|
3036
|
+
params = {
|
|
3037
|
+
lat: coordinates.lat,
|
|
3038
|
+
lng: coordinates.lng,
|
|
3039
|
+
};
|
|
3040
|
+
}
|
|
3041
|
+
if (locale === 'ms-MY') {
|
|
3042
|
+
moreParams.noPaging = 1;
|
|
3043
|
+
}
|
|
3044
|
+
const requests = [
|
|
3045
|
+
fetchCitiesApi(paths.PATHS.GET_CITY_BY_IP, Object.assign(Object.assign(Object.assign({}, params), moreParams), { client: constants.CLIENT_KEY.MSD === client ? '' : client })),
|
|
3046
|
+
];
|
|
3047
|
+
if (locale === 'zh-TW') {
|
|
3048
|
+
requests.push(fetchCitiesApi(paths.PATHS.GET_CITIES_LIST, {
|
|
3049
|
+
noPaging: 1,
|
|
3050
|
+
client: constants.CLIENT_KEY.MSD === client ? '' : client,
|
|
3051
|
+
}));
|
|
3052
|
+
}
|
|
3053
|
+
return Promise.all(requests)
|
|
3054
|
+
.then(([data1, data2]) => {
|
|
3055
|
+
const data = Object.assign({}, data1);
|
|
3056
|
+
if (data2) {
|
|
3057
|
+
const citiesIds = data.cities.map((c) => c.id);
|
|
3058
|
+
data.cities = data.cities.concat(data2.cities.filter((c) => !citiesIds.includes(c.id)));
|
|
3059
|
+
}
|
|
3060
|
+
dispatch({
|
|
3061
|
+
type: ActionTypes.FetchCitiesByGeoIpComplete,
|
|
3062
|
+
payload: data,
|
|
3063
|
+
});
|
|
3064
|
+
})
|
|
3065
|
+
.catch((err) => console.error('error loading cities by location', err));
|
|
3066
|
+
}, [locale, careApiDomain, dispatch]);
|
|
3067
|
+
const fetchCitiesByKeyword = React.useCallback(function fetchCitiesByKeyword(keyword) {
|
|
3068
|
+
return fetchCitiesApi(paths.PATHS.GET_CITIES_LIST, {
|
|
3069
|
+
keyword,
|
|
3070
|
+
client,
|
|
3071
|
+
})
|
|
3072
|
+
.then((data) => {
|
|
3073
|
+
dispatch({
|
|
3074
|
+
type: ActionTypes.FetchCitiesByKeywordComplete,
|
|
3075
|
+
payload: data.cities,
|
|
3076
|
+
});
|
|
3077
|
+
})
|
|
3078
|
+
.catch((err) => console.error('error loading cities by keyword', err));
|
|
3079
|
+
}, [locale, careApiDomain, dispatch]);
|
|
3080
|
+
const fetchSearchResults = React.useCallback(function fetchSearchResults(searchKeywords, state, searchType, clientSlug, cacheResult) {
|
|
3081
|
+
const url = searchType === 'specialty'
|
|
3082
|
+
? `${careApiDomain}${paths.PATHS.GET_SEARCH_SPECIALTY}`
|
|
3083
|
+
: `${careApiDomain}${paths.PATHS.GET_SEARCH_V2}`;
|
|
3084
|
+
dispatch({ type: ActionTypes.FetchSearchResultsStart });
|
|
3085
|
+
const { selectedLocation, geoLocationCoordinates, selectedSpecialty } = state;
|
|
3086
|
+
let cityId = '';
|
|
3087
|
+
if (!selectedLocation) {
|
|
3088
|
+
dispatch({ type: ActionTypes.FetchSearchResultsFinish });
|
|
3089
|
+
return;
|
|
3090
|
+
}
|
|
3091
|
+
if (selectedLocation.id === constants.ID_OPTION_ALL_LOCATION) {
|
|
3092
|
+
cityId = '';
|
|
3093
|
+
}
|
|
3094
|
+
else {
|
|
3095
|
+
cityId = selectedLocation.id;
|
|
3096
|
+
}
|
|
3097
|
+
const lat = (geoLocationCoordinates === null || geoLocationCoordinates === void 0 ? void 0 : geoLocationCoordinates.lat) || '';
|
|
3098
|
+
const lng = (geoLocationCoordinates === null || geoLocationCoordinates === void 0 ? void 0 : geoLocationCoordinates.lng) || '';
|
|
3099
|
+
const specialty_id = (selectedSpecialty === null || selectedSpecialty === void 0 ? void 0 : selectedSpecialty.id) > 0 ? selectedSpecialty === null || selectedSpecialty === void 0 ? void 0 : selectedSpecialty.id : '';
|
|
3100
|
+
const keyword = searchKeywords.trim().length > SEARCH_KEYWORD_MIN_LENGTH[locale]
|
|
3101
|
+
? searchKeywords.trim()
|
|
3102
|
+
: '';
|
|
3103
|
+
return fetch(getApiPath(url, {
|
|
3104
|
+
domain: careApiDomain,
|
|
3105
|
+
searchType: searchType || 'global',
|
|
3106
|
+
keyword: keyword,
|
|
3107
|
+
city: cityId === constants.ID_OPTION_CURRENT_LOCATION ? '' : cityId,
|
|
3108
|
+
lat,
|
|
3109
|
+
lng,
|
|
3110
|
+
specialty_id,
|
|
3111
|
+
client_slug: constants.CLIENT_KEY.MSD === clientSlug ? '' : clientSlug,
|
|
3112
|
+
msd: constants.CLIENT_KEY.MSD === client ? 1 : '',
|
|
3113
|
+
}, locale), {
|
|
3114
|
+
method: 'GET',
|
|
3115
|
+
headers: {
|
|
3116
|
+
accept: 'version=2.0.0.0',
|
|
3117
|
+
},
|
|
3118
|
+
})
|
|
3119
|
+
.then((res) => res.json())
|
|
3120
|
+
.then((data) => {
|
|
3121
|
+
if (data._status !== 1 || !data._data) {
|
|
3122
|
+
return Promise.reject(data);
|
|
3123
|
+
}
|
|
3124
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
3125
|
+
})
|
|
3126
|
+
.then((results) => {
|
|
3127
|
+
let searchesResult = [];
|
|
3128
|
+
if (searchType !== 'specialty') {
|
|
3129
|
+
searchesResult = results.searches;
|
|
3130
|
+
}
|
|
3131
|
+
if (searchType === 'specialty') {
|
|
3132
|
+
if (keyword) {
|
|
3133
|
+
searchesResult = results.specialties;
|
|
3134
|
+
}
|
|
3135
|
+
else {
|
|
3136
|
+
searchesResult = results.default;
|
|
3137
|
+
}
|
|
3138
|
+
}
|
|
3139
|
+
dispatch({
|
|
3140
|
+
type: ActionTypes.FetchSearchResultsComplete,
|
|
3141
|
+
payload: {
|
|
3142
|
+
key: searchType,
|
|
3143
|
+
searches: searchesResult || [],
|
|
3144
|
+
},
|
|
3145
|
+
});
|
|
3146
|
+
if (cacheResult) {
|
|
3147
|
+
dispatch({
|
|
3148
|
+
type: ActionTypes.UpdateInitialSearchResults,
|
|
3149
|
+
payload: {
|
|
3150
|
+
key: searchType,
|
|
3151
|
+
searches: searchesResult || [],
|
|
3152
|
+
},
|
|
3153
|
+
});
|
|
3154
|
+
}
|
|
3155
|
+
})
|
|
3156
|
+
.catch((error) => {
|
|
3157
|
+
console.log('error loading search results', { url, error });
|
|
3158
|
+
})
|
|
3159
|
+
.finally(() => dispatch({ type: ActionTypes.FetchSearchResultsFinish }));
|
|
3160
|
+
}, [locale, careApiDomain, dispatch]);
|
|
3161
|
+
const fetchAllSpecialties = React.useCallback(function fetchSearchSpecialties() {
|
|
3162
|
+
const url = `${careApiDomain}${paths.PATHS.GET_SEARCH_SPECIALTY}`;
|
|
3163
|
+
return fetch(getApiPath(url, {
|
|
3164
|
+
domain: careApiDomain,
|
|
3165
|
+
searchType: '',
|
|
3166
|
+
msd: constants.CLIENT_KEY.MSD === client ? 1 : '',
|
|
3167
|
+
}, locale), {
|
|
3168
|
+
method: 'GET',
|
|
3169
|
+
headers: {
|
|
3170
|
+
accept: 'version=2.0.0.0',
|
|
3171
|
+
},
|
|
3172
|
+
})
|
|
3173
|
+
.then((res) => res.json())
|
|
3174
|
+
.then((data) => {
|
|
3175
|
+
if (data._status !== 1 || !data._data) {
|
|
3176
|
+
return Promise.reject(data);
|
|
3177
|
+
}
|
|
3178
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
3179
|
+
})
|
|
3180
|
+
.then((results) => {
|
|
3181
|
+
dispatch({
|
|
3182
|
+
type: ActionTypes.FetchAllSpecialties,
|
|
3183
|
+
payload: results.specialties || [],
|
|
3184
|
+
});
|
|
3185
|
+
})
|
|
3186
|
+
.catch((error) => {
|
|
3187
|
+
console.log('error loading search results', { url, error });
|
|
3188
|
+
});
|
|
3189
|
+
}, [locale, careApiDomain, dispatch]);
|
|
3190
|
+
const fetchPopularKeys = React.useCallback(function fetchPopularKeys(searchType) {
|
|
3191
|
+
const url = `${careApiDomain}${paths.PATHS.GET_SEARCH_POPULAR_KEY}`;
|
|
3192
|
+
return fetch(getApiPath(url, {
|
|
3193
|
+
domain: careApiDomain,
|
|
3194
|
+
searchType: TypePopularKeySearch[searchType],
|
|
3195
|
+
sort_by: 'display_order',
|
|
3196
|
+
sort_order: 'asc',
|
|
3197
|
+
}, locale))
|
|
3198
|
+
.then((res) => res.json())
|
|
3199
|
+
.then((data) => {
|
|
3200
|
+
if (data._status !== 1 || !data._data) {
|
|
3201
|
+
return Promise.reject(data);
|
|
3202
|
+
}
|
|
3203
|
+
return data === null || data === void 0 ? void 0 : data._data;
|
|
3204
|
+
})
|
|
3205
|
+
.then((results) => {
|
|
3206
|
+
dispatch({
|
|
3207
|
+
type: ActionTypes.FetchPopularKeys,
|
|
3208
|
+
payload: results.popular_searches || [],
|
|
3209
|
+
});
|
|
3210
|
+
})
|
|
3211
|
+
.catch((error) => {
|
|
3212
|
+
console.log('error loading search results', { url, error });
|
|
3213
|
+
});
|
|
3214
|
+
}, [locale, careApiDomain, dispatch]);
|
|
3215
|
+
return {
|
|
3216
|
+
fetchCitiesByLocation,
|
|
3217
|
+
fetchCitiesByKeyword,
|
|
3218
|
+
fetchSearchResults,
|
|
3219
|
+
fetchAllSpecialties,
|
|
3220
|
+
fetchPopularKeys,
|
|
3221
|
+
};
|
|
3222
|
+
}
|
|
3223
|
+
|
|
3224
|
+
const BookingSearchBarV2 = ({ isMobile, careApiDomain, geoLocationPermission: geoLocationPermissionFromProps, geoLocationCoordinates: geoLocationCoordinatesFromProps, initialSelectedCity: initialSelectedCityFromProps, initialSearchValue = '', initTypeSearch = 'hospital', initSpecialty, careFrontDomain = '/care', isDebug = false,
|
|
3225
|
+
// askForGeolocationPermission = false,
|
|
3226
|
+
gaTrackingSearchBar, gaTrackingLocationSearch, autoCompleteDisabled = false, inputSearchPlaceholder = '', hideTabBookingSearch = [], hideSpecialtySelection = false, hidePopularSearchKeys = false, clientSlug = '',
|
|
3227
|
+
// isOptionAllLocation = false,
|
|
3228
|
+
// hideResults = [],
|
|
3229
|
+
// isNavResultItem = true,
|
|
3230
|
+
routerPush, onGeoLocationPermissionChange,
|
|
3231
|
+
// onSearch,
|
|
3232
|
+
onChangeLocation, }) => {
|
|
3233
|
+
const { locale, t } = useTranslations.useTranslations();
|
|
3234
|
+
const wrapperRef = React.useRef(null);
|
|
3235
|
+
const inputSearchSpecialtyWrapperRef = React.useRef(null);
|
|
3236
|
+
const [currentTab, setCurrentTab] = React.useState(initTypeSearch);
|
|
3237
|
+
const { geoLocationPermission: geoLocationPermissionFromHook, geoLocationCoordinates: geoLocationCoordinatesFromHook, } = useGeolocation();
|
|
3238
|
+
const [state, dispatch] = React.useReducer(reducer, initialState, (s) => (Object.assign(Object.assign({}, s), { isDebug,
|
|
3239
|
+
isMobile, geoLocationPermission: geoLocationPermissionFromProps ||
|
|
3240
|
+
geoLocationPermissionFromHook ||
|
|
3241
|
+
'unset', geoLocationCoordinates: geoLocationCoordinatesFromProps ||
|
|
3242
|
+
geoLocationCoordinatesFromHook ||
|
|
3243
|
+
null, searchKeywords: initialSearchValue, initialSelectedCity: initialSelectedCityFromProps || null, selectedLocation: initialSelectedCityFromProps || s.selectedLocation || null, searchLocationKeywords: (initialSelectedCityFromProps === null || initialSelectedCityFromProps === void 0 ? void 0 : initialSelectedCityFromProps.name) || s.searchLocationKeywords, autoCompleteDisabled,
|
|
3244
|
+
inputSearchPlaceholder,
|
|
3245
|
+
locale })));
|
|
3246
|
+
const { navigateTo, focusedSpecialty,
|
|
3247
|
+
// isLoadingCities,
|
|
3248
|
+
// cities,
|
|
3249
|
+
searchKeywords, geoLocationPermission, selectedLocation, selectedSpecialty, initialSelectedCity,
|
|
3250
|
+
// defaultCity,
|
|
3251
|
+
searchResults, isLoadingSearchResults,
|
|
3252
|
+
// isMobileModalOpened,
|
|
3253
|
+
// inputSearchPlaceholder,
|
|
3254
|
+
// allSpecialties,
|
|
3255
|
+
} = state;
|
|
3256
|
+
const { fetchCitiesByLocation, fetchCitiesByKeyword, fetchSearchResults, fetchAllSpecialties, fetchPopularKeys, } = useSearchBarApi({
|
|
3257
|
+
dispatch,
|
|
3258
|
+
locale,
|
|
3259
|
+
careApiDomain,
|
|
3260
|
+
client: clientSlug,
|
|
3261
|
+
});
|
|
3262
|
+
const slugs = React.useMemo(() => constants.LOCALIZED_SLUGS[locale], [locale]);
|
|
3263
|
+
const typeInformation = React.useMemo(() => {
|
|
3264
|
+
return {
|
|
3265
|
+
doctor: {
|
|
3266
|
+
name: t('booking.searchPopup.doctors'),
|
|
3267
|
+
icon: React__default["default"].createElement(DoctorIcon, null),
|
|
3268
|
+
slug: slugs.DOCTOR,
|
|
3269
|
+
},
|
|
3270
|
+
service: {
|
|
3271
|
+
name: t('booking.searchPopup.services'),
|
|
3272
|
+
icon: React__default["default"].createElement(ServiceIcon, null),
|
|
3273
|
+
slug: slugs.SERVICE,
|
|
3274
|
+
},
|
|
3275
|
+
hospital: {
|
|
3276
|
+
name: t('booking.searchPopup.hospitals'),
|
|
3277
|
+
icon: React__default["default"].createElement(HospitalIcon, null),
|
|
3278
|
+
slug: slugs.HOSPITAL,
|
|
3279
|
+
},
|
|
3280
|
+
specialty: {
|
|
3281
|
+
name: t('booking.searchPopup.specialties'),
|
|
3282
|
+
icon: React__default["default"].createElement(SpecialtyIcon, null),
|
|
3283
|
+
slug: slugs.SPECIALTIES,
|
|
3284
|
+
},
|
|
3285
|
+
};
|
|
3286
|
+
}, [currentTab]);
|
|
3287
|
+
const debouncedFetchCitiesByKeyword = React.useMemo(() => debounce__default["default"](fetchCitiesByKeyword, 400), [fetchCitiesByKeyword]);
|
|
3288
|
+
const debouncedFetchSearchResults = React.useMemo(() => debounce__default["default"](fetchSearchResults, 400), [fetchSearchResults]);
|
|
3289
|
+
const handleLocationClick = React.useCallback(function handleLocationClick(city) {
|
|
3290
|
+
dispatch({ type: ActionTypes.SelectLocation, payload: city });
|
|
3291
|
+
focusSearchInput();
|
|
3292
|
+
if (onChangeLocation) {
|
|
3293
|
+
onChangeLocation(city);
|
|
3294
|
+
}
|
|
3295
|
+
}, [t, dispatch]);
|
|
3296
|
+
function focusSearchInput() {
|
|
3297
|
+
var _a;
|
|
3298
|
+
if (wrapperRef.current) {
|
|
3299
|
+
(_a = wrapperRef.current
|
|
3300
|
+
.querySelector('input[name="search-results"]')) === null || _a === void 0 ? void 0 : _a.focus();
|
|
3301
|
+
}
|
|
3302
|
+
}
|
|
3303
|
+
function onClickSearchByKeyword() {
|
|
3304
|
+
let url = '';
|
|
3305
|
+
const { slug: typeSlug } = typeInformation[currentTab];
|
|
3306
|
+
let moreParams = '';
|
|
3307
|
+
const slugClientUrl = constants.MAPPING_CLIENT_WITH_SLUG[locale][clientSlug];
|
|
3308
|
+
if ((currentTab === 'doctor' || currentTab === 'hospital') &&
|
|
3309
|
+
state.selectedSpecialty.id > 0) {
|
|
3310
|
+
moreParams = `&specialtyId=${state.selectedSpecialty.id}`;
|
|
3311
|
+
}
|
|
3312
|
+
if (currentTab === 'specialty') {
|
|
3313
|
+
url = `/${typeSlug}`;
|
|
3314
|
+
}
|
|
3315
|
+
else {
|
|
3316
|
+
url = `/${selectedLocation.slug}/${typeSlug}`;
|
|
3317
|
+
}
|
|
3318
|
+
if (slugClientUrl) {
|
|
3319
|
+
url += `/${slugClientUrl}`;
|
|
3320
|
+
}
|
|
3321
|
+
url += `?q=${searchKeywords}${moreParams}`;
|
|
3322
|
+
if (url) {
|
|
3323
|
+
dispatch({ type: ActionTypes.NavigateTo, payload: url });
|
|
3324
|
+
}
|
|
3325
|
+
}
|
|
3326
|
+
useOutsideClick.useOutsideClick(inputSearchSpecialtyWrapperRef, () => {
|
|
3327
|
+
dispatch({ type: ActionTypes.ClickOutsideInputSearchSpecialty });
|
|
3328
|
+
});
|
|
3329
|
+
React.useEffect(() => {
|
|
3330
|
+
var _a;
|
|
3331
|
+
if (geoLocationPermission !== 'denied' && !initialSelectedCity) {
|
|
3332
|
+
dispatch({
|
|
3333
|
+
type: ActionTypes.SelectLocation,
|
|
3334
|
+
payload: {
|
|
3335
|
+
name: t('booking.searchBar.allLocations'),
|
|
3336
|
+
id: constants.ID_OPTION_ALL_LOCATION,
|
|
3337
|
+
slug: (_a = constants.LOCALIZED_SLUGS[locale]) === null || _a === void 0 ? void 0 : _a.ALL,
|
|
3338
|
+
},
|
|
3339
|
+
});
|
|
3340
|
+
}
|
|
3341
|
+
if (onGeoLocationPermissionChange) {
|
|
3342
|
+
onGeoLocationPermissionChange(geoLocationPermission, state.geoLocationCoordinates);
|
|
3343
|
+
}
|
|
3344
|
+
if (isMobile && geoLocationPermission === 'granted' && selectedLocation) {
|
|
3345
|
+
dispatch({ type: ActionTypes.FocusInputSearch });
|
|
3346
|
+
}
|
|
3347
|
+
fetchCitiesByLocation({ coordinates: state.geoLocationCoordinates });
|
|
3348
|
+
}, [geoLocationPermission]);
|
|
3349
|
+
React.useEffect(() => {
|
|
3350
|
+
const defaultSpecialty = initSpecialty
|
|
3351
|
+
? initSpecialty
|
|
3352
|
+
: {
|
|
3353
|
+
name: t('booking.searchBar.allSpecialties'),
|
|
3354
|
+
id: -1,
|
|
3355
|
+
thumbnail: '',
|
|
3356
|
+
total_doctor: 0,
|
|
3357
|
+
slug: slugs.SPECIALTIES,
|
|
3358
|
+
};
|
|
3359
|
+
if (!state.selectedSpecialty) {
|
|
3360
|
+
dispatch({
|
|
3361
|
+
type: ActionTypes.SelectSpecialty,
|
|
3362
|
+
payload: defaultSpecialty,
|
|
3363
|
+
});
|
|
3364
|
+
}
|
|
3365
|
+
}, [initSpecialty, state.selectedSpecialty]);
|
|
3366
|
+
React.useEffect(() => {
|
|
3367
|
+
fetchAllSpecialties();
|
|
3368
|
+
}, []);
|
|
3369
|
+
React.useEffect(() => {
|
|
3370
|
+
fetchPopularKeys(currentTab);
|
|
3371
|
+
}, [currentTab]);
|
|
3372
|
+
React.useEffect(() => {
|
|
3373
|
+
if (navigateTo) {
|
|
3374
|
+
if (routerPush) {
|
|
3375
|
+
routerPush(navigateTo);
|
|
3376
|
+
}
|
|
3377
|
+
else {
|
|
3378
|
+
window.location.href = `${careFrontDomain}${navigateTo}`;
|
|
3379
|
+
}
|
|
3380
|
+
}
|
|
3381
|
+
}, [navigateTo]);
|
|
3382
|
+
React.useEffect(() => {
|
|
3383
|
+
fetchSearchResults(state.searchKeywords, state, currentTab, clientSlug, true);
|
|
3384
|
+
}, [selectedLocation, selectedSpecialty, currentTab]);
|
|
3385
|
+
return (React__default["default"].createElement(StyledSearchBarWrapper, { ref: wrapperRef },
|
|
3386
|
+
React__default["default"].createElement(TabSearch, { currentTab: currentTab, setCurrentTab: setCurrentTab, isMobile: isMobile, hideTabBookingSearch: hideTabBookingSearch }),
|
|
3387
|
+
React__default["default"].createElement(StyleWrapperContainer, { className: "booking-search-container" },
|
|
3388
|
+
React__default["default"].createElement(StyleSearchInputContainer, null,
|
|
3389
|
+
React__default["default"].createElement(StyleSearchContent, null,
|
|
3390
|
+
React__default["default"].createElement("div", { ref: inputSearchSpecialtyWrapperRef },
|
|
3391
|
+
React__default["default"].createElement(core.Flex, { gap: "12px", justify: "space-between", align: "center", direction: isMobile ? 'column' : 'row', className: "flex-search-input" },
|
|
3392
|
+
currentTab !== 'specialty' && (React__default["default"].createElement(SearchLocation, { state: state, isMobile: isMobile, dispatch: dispatch, debouncedFetchCitiesByKeyword: debouncedFetchCitiesByKeyword, selectedLocation: selectedLocation, onLocationClick: handleLocationClick, trackingAttributes: gaTrackingLocationSearch })),
|
|
3393
|
+
React__default["default"].createElement(SearchInputs, { type: currentTab, isMobile: isMobile, state: state, dispatch: dispatch, debouncedFetchSearchResults: debouncedFetchSearchResults, initalSearchValue: initialSearchValue, focusSearchInput: focusSearchInput, onEnterSearch: onClickSearchByKeyword, typeInformation: typeInformation, trackingAttributes: gaTrackingSearchBar, isLoading: isLoadingSearchResults, hideSpecialtySelection: hideSpecialtySelection, clientSlug: clientSlug }),
|
|
3394
|
+
React__default["default"].createElement(core.Button, { size: isMobile ? 'md' : 'lg', color: "#2D87F3", fullWidth: isMobile, variant: "filled", onClick: onClickSearchByKeyword, styles: {
|
|
3395
|
+
root: {
|
|
3396
|
+
height: isMobile ? '40px' : '48px',
|
|
3397
|
+
},
|
|
3398
|
+
} }, t('booking.searchBar.searchButton'))),
|
|
3399
|
+
!hidePopularSearchKeys &&
|
|
3400
|
+
currentTab !== 'specialty' &&
|
|
3401
|
+
state.popularKeys.length > 0 && (React__default["default"].createElement(SearchTag, { type: currentTab, state: state, typeInformation: typeInformation, dispatch: dispatch })),
|
|
3402
|
+
currentTab === 'specialty' && focusedSpecialty === 'search' && (React__default["default"].createElement(SearchResultSpecialties, { state: state, isMobile: isMobile, dispatch: dispatch, specialties: (searchResults === null || searchResults === void 0 ? void 0 : searchResults.specialty) || [], isLoading: isLoadingSearchResults }))))))));
|
|
3403
|
+
};
|
|
3404
|
+
|
|
3405
|
+
const StyledTextDivider = styled__default["default"].div `
|
|
3406
|
+
background-color: var(--neutral50);
|
|
3407
|
+
padding: 12px 0;
|
|
3408
|
+
box-shadow: inset 0px 1px 0px #e4e8ec;
|
|
3409
|
+
|
|
3410
|
+
> * {
|
|
3411
|
+
display: grid;
|
|
3412
|
+
grid-template-columns: 32px 1fr;
|
|
3413
|
+
align-content: center;
|
|
3414
|
+
|
|
3415
|
+
p {
|
|
3416
|
+
font-weight: 600;
|
|
3417
|
+
}
|
|
3418
|
+
}
|
|
3419
|
+
|
|
3420
|
+
.icon-wrapper {
|
|
3421
|
+
display: flex;
|
|
3422
|
+
align-items: center;
|
|
3423
|
+
}
|
|
3424
|
+
`;
|
|
3425
|
+
const TextDivider = ({ children, icon, className, style }) => (React__default["default"].createElement(StyledTextDivider, { style: style, className: className },
|
|
3426
|
+
React__default["default"].createElement(index$3.Container, null,
|
|
3427
|
+
React__default["default"].createElement("div", { className: "icon-wrapper" }, icon),
|
|
3428
|
+
React__default["default"].createElement(index$2.Text, { size: "c1", color: "var(--neutral800)" }, children))));
|
|
3429
|
+
|
|
3430
|
+
var RedirectType;
|
|
3431
|
+
(function (RedirectType) {
|
|
3432
|
+
RedirectType[RedirectType["SPECIALTY"] = 1] = "SPECIALTY";
|
|
3433
|
+
RedirectType[RedirectType["DOCTOR"] = 2] = "DOCTOR";
|
|
3434
|
+
RedirectType[RedirectType["CLINIC"] = 3] = "CLINIC";
|
|
3435
|
+
RedirectType[RedirectType["SERVICE"] = 4] = "SERVICE";
|
|
3436
|
+
})(RedirectType || (RedirectType = {}));
|
|
3437
|
+
|
|
3438
|
+
var types = /*#__PURE__*/Object.freeze({
|
|
3439
|
+
__proto__: null,
|
|
3440
|
+
get RedirectType () { return RedirectType; }
|
|
3441
|
+
});
|
|
3442
|
+
|
|
3443
|
+
exports.BookingSearchBar = BookingSearchBar;
|
|
3444
|
+
exports.BookingSearchBarV2 = BookingSearchBarV2;
|
|
3445
|
+
exports.TextDivider = TextDivider;
|
|
3446
|
+
exports.types = types;
|