@salla.sa/twilight-theme-engine 1.0.85 → 1.0.86

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (372) hide show
  1. package/dist/{AddToCartForm-B5C2M4OZ.js → AddToCartForm-5X2WZDWR.js} +3 -3
  2. package/dist/{AddToCartForm-B5C2M4OZ.js.map → AddToCartForm-5X2WZDWR.js.map} +1 -1
  3. package/dist/{BlogAuthorPage-GTF4UGSS.js → BlogAuthorPage-LO7FSSJR.js} +12 -10
  4. package/dist/BlogAuthorPage-LO7FSSJR.js.map +1 -0
  5. package/dist/{BlogCategoryPage-TN7Y4NBP.js → BlogCategoryPage-KKFQ3PGR.js} +12 -10
  6. package/dist/BlogCategoryPage-KKFQ3PGR.js.map +1 -0
  7. package/dist/{BlogPage-TDB3M3PI.js → BlogPage-VLF3NSGE.js} +11 -9
  8. package/dist/BlogPage-VLF3NSGE.js.map +1 -0
  9. package/dist/{BlogSinglePage-4A52Q5QW.js → BlogSinglePage-AVK535IW.js} +11 -9
  10. package/dist/BlogSinglePage-AVK535IW.js.map +1 -0
  11. package/dist/{BlogTagPage-TOVPBETA.js → BlogTagPage-F3T4D7RH.js} +12 -10
  12. package/dist/BlogTagPage-F3T4D7RH.js.map +1 -0
  13. package/dist/{BrandsPage-VUDGYSQI.js → BrandsPage-LVSBZSVC.js} +11 -9
  14. package/dist/BrandsPage-LVSBZSVC.js.map +1 -0
  15. package/dist/{Breadcrumb-CI3SN5YR.js → Breadcrumb-VLFTXRFC.js} +11 -9
  16. package/dist/Breadcrumb-VLFTXRFC.js.map +1 -0
  17. package/dist/{CartItem-BHLEURAB.js → CartItem-G3H34GW6.js} +11 -9
  18. package/dist/CartItem-G3H34GW6.js.map +1 -0
  19. package/dist/{CartSummary-QERVESYN.js → CartSummary-VH37RPUI.js} +11 -9
  20. package/dist/CartSummary-VH37RPUI.js.map +1 -0
  21. package/dist/{Copyright-RL6ALKRC.js → Copyright-HE5ZWINZ.js} +3 -3
  22. package/dist/{Copyright-RL6ALKRC.js.map → Copyright-HE5ZWINZ.js.map} +1 -1
  23. package/dist/{CustomerLayout-VRZUWGQK.js → CustomerLayout-LKBLOAVW.js} +11 -9
  24. package/dist/CustomerLayout-LKBLOAVW.js.map +1 -0
  25. package/dist/{Footer-ZWBZCMDL.js → Footer-HHXAST72.js} +5 -5
  26. package/dist/{Footer-ZWBZCMDL.js.map → Footer-HHXAST72.js.map} +1 -1
  27. package/dist/{Header-WNK4O66B.js → Header-GEVZM2YG.js} +8 -6
  28. package/dist/{Header-WNK4O66B.js.map → Header-GEVZM2YG.js.map} +1 -1
  29. package/dist/{LoyaltyPage-CGTHWJ76.js → LoyaltyPage-M5CT3CFD.js} +11 -9
  30. package/dist/LoyaltyPage-M5CT3CFD.js.map +1 -0
  31. package/dist/{LoyaltyPointsPage-QSU6K3PW.js → LoyaltyPointsPage-SDJB52U6.js} +10 -3
  32. package/dist/LoyaltyPointsPage-SDJB52U6.js.map +1 -0
  33. package/dist/{MainMenu-V3T7F32R.js → MainMenu-I7EYS752.js} +3 -3
  34. package/dist/{MainMenu-V3T7F32R.js.map → MainMenu-I7EYS752.js.map} +1 -1
  35. package/dist/{MasterLayout-XQF644LD.js → MasterLayout-QDK4T3NE.js} +11 -9
  36. package/dist/{MasterLayout-XQF644LD.js.map → MasterLayout-QDK4T3NE.js.map} +1 -1
  37. package/dist/{MobileMenu-U4BVQYKH.js → MobileMenu-7VTCWAVJ.js} +11 -9
  38. package/dist/MobileMenu-7VTCWAVJ.js.map +1 -0
  39. package/dist/{NotificationsPage-ZRRQY7TF.js → NotificationsPage-QCABE6QD.js} +11 -9
  40. package/dist/NotificationsPage-QCABE6QD.js.map +1 -0
  41. package/dist/{OrderSinglePage-O3XYVMG5.js → OrderSinglePage-2HVBKBG4.js} +11 -9
  42. package/dist/OrderSinglePage-2HVBKBG4.js.map +1 -0
  43. package/dist/{OrdersPage-CMXZF5MI.js → OrdersPage-5MNCPCM3.js} +11 -9
  44. package/dist/OrdersPage-5MNCPCM3.js.map +1 -0
  45. package/dist/{PageSingle-IIG2US43.js → PageSingle-EN5XIM2B.js} +3 -3
  46. package/dist/{PageSingle-IIG2US43.js.map → PageSingle-EN5XIM2B.js.map} +1 -1
  47. package/dist/{ProductDetails-65GDABI7.js → ProductDetails-UEWQPPDZ.js} +13 -6
  48. package/dist/ProductDetails-UEWQPPDZ.js.map +1 -0
  49. package/dist/{ProfilePage-SNJ4WXU4.js → ProfilePage-TZSU3GHZ.js} +11 -9
  50. package/dist/ProfilePage-TZSU3GHZ.js.map +1 -0
  51. package/dist/{ReviewsPage-UT7UT55J.js → ReviewsPage-WYZ6CHF2.js} +3 -3
  52. package/dist/{ReviewsPage-UT7UT55J.js.map → ReviewsPage-WYZ6CHF2.js.map} +1 -1
  53. package/dist/{SeoCartWidget-DBJAXJKT.js → SeoCartWidget-5JR5RXQM.js} +11 -9
  54. package/dist/SeoCartWidget-5JR5RXQM.js.map +1 -0
  55. package/dist/{SettingsPage-FLTIOPU5.js → SettingsPage-DIDRQXMM.js} +11 -9
  56. package/dist/SettingsPage-DIDRQXMM.js.map +1 -0
  57. package/dist/{StoreClosedNotification-ZT3QKDKS.js → StoreClosedNotification-C2G32E34.js} +12 -10
  58. package/dist/{StoreClosedNotification-ZT3QKDKS.js.map → StoreClosedNotification-C2G32E34.js.map} +1 -1
  59. package/dist/{TestimonialsPage-CU7HKU4O.js → TestimonialsPage-XPHFRBZ7.js} +3 -3
  60. package/dist/{TestimonialsPage-CU7HKU4O.js.map → TestimonialsPage-XPHFRBZ7.js.map} +1 -1
  61. package/dist/{ThankYouPage-5X6B4X3T.js → ThankYouPage-UA6YYFB2.js} +11 -9
  62. package/dist/ThankYouPage-UA6YYFB2.js.map +1 -0
  63. package/dist/{WalletPage-H2BKIDPA.js → WalletPage-AJVV7LVL.js} +11 -9
  64. package/dist/WalletPage-AJVV7LVL.js.map +1 -0
  65. package/dist/{WishlistPage-RS5UCIQ3.js → WishlistPage-UW6LJLSW.js} +11 -9
  66. package/dist/WishlistPage-UW6LJLSW.js.map +1 -0
  67. package/dist/api/advertisement.d.ts +33 -0
  68. package/dist/api/advertisement.d.ts.map +1 -0
  69. package/dist/api/advertisement.js +8 -0
  70. package/dist/api/advertisement.js.map +1 -0
  71. package/dist/boot/critical-style.d.ts +3 -0
  72. package/dist/boot/critical-style.d.ts.map +1 -0
  73. package/dist/boot/index.d.ts +15 -0
  74. package/dist/boot/index.d.ts.map +1 -0
  75. package/dist/boot.d.ts +1 -0
  76. package/dist/boot.js +69 -0
  77. package/dist/boot.js.map +1 -0
  78. package/dist/{chunk-SE5JYWOK.js → chunk-2HCCIHU7.js} +4 -4
  79. package/dist/{chunk-SE5JYWOK.js.map → chunk-2HCCIHU7.js.map} +1 -1
  80. package/dist/chunk-4FJGZQD3.js +6 -0
  81. package/dist/chunk-4FJGZQD3.js.map +1 -0
  82. package/dist/{chunk-SDFDS4Q3.js → chunk-4WVJJ7SN.js} +20 -4
  83. package/dist/chunk-4WVJJ7SN.js.map +1 -0
  84. package/dist/{chunk-NXQJA7D3.js → chunk-BAYGWTNM.js} +3 -3
  85. package/dist/{chunk-NXQJA7D3.js.map → chunk-BAYGWTNM.js.map} +1 -1
  86. package/dist/{chunk-OWX2CPNQ.js → chunk-CLBFF2CY.js} +3 -3
  87. package/dist/{chunk-OWX2CPNQ.js.map → chunk-CLBFF2CY.js.map} +1 -1
  88. package/dist/chunk-DBW7XXNE.js +103 -0
  89. package/dist/chunk-DBW7XXNE.js.map +1 -0
  90. package/dist/{chunk-KHBSGD2D.js → chunk-DBXH3EMJ.js} +3 -3
  91. package/dist/{chunk-KHBSGD2D.js.map → chunk-DBXH3EMJ.js.map} +1 -1
  92. package/dist/{chunk-JRNH3FUF.js → chunk-E26YG3AO.js} +4 -4
  93. package/dist/{chunk-JRNH3FUF.js.map → chunk-E26YG3AO.js.map} +1 -1
  94. package/dist/{chunk-22SH7OVF.js → chunk-E7WWO3V3.js} +3 -3
  95. package/dist/{chunk-22SH7OVF.js.map → chunk-E7WWO3V3.js.map} +1 -1
  96. package/dist/{chunk-UJKFBZFJ.js → chunk-HQ7WA37L.js} +7 -7
  97. package/dist/{chunk-UJKFBZFJ.js.map → chunk-HQ7WA37L.js.map} +1 -1
  98. package/dist/chunk-IVBOLREE.js +29 -0
  99. package/dist/chunk-IVBOLREE.js.map +1 -0
  100. package/dist/{chunk-6SWDSRIL.js → chunk-KP3VYG4F.js} +6 -6
  101. package/dist/{chunk-6SWDSRIL.js.map → chunk-KP3VYG4F.js.map} +1 -1
  102. package/dist/{chunk-4CZRUAZB.js → chunk-PWTXR4RR.js} +10 -10
  103. package/dist/{chunk-4CZRUAZB.js.map → chunk-PWTXR4RR.js.map} +1 -1
  104. package/dist/chunk-QJYUTRAQ.js +14 -0
  105. package/dist/{chunk-7WAXN2PP.js.map → chunk-QJYUTRAQ.js.map} +1 -1
  106. package/dist/{chunk-JO7JWV34.js → chunk-U55ZJC2X.js} +4 -4
  107. package/dist/{chunk-JO7JWV34.js.map → chunk-U55ZJC2X.js.map} +1 -1
  108. package/dist/{chunk-SX5MF2YA.js → chunk-WSDG4ZRI.js} +4 -4
  109. package/dist/{chunk-SX5MF2YA.js.map → chunk-WSDG4ZRI.js.map} +1 -1
  110. package/dist/{chunk-NZVR4OF7.js → chunk-X54QP332.js} +8 -8
  111. package/dist/chunk-X54QP332.js.map +1 -0
  112. package/dist/components/cart/index.js +1 -1
  113. package/dist/components/common/index.js +1 -1
  114. package/dist/components/drawer/index.js +9 -7
  115. package/dist/components/home/index.js +11 -9
  116. package/dist/components/layout/PageAdvertisements.d.ts +7 -0
  117. package/dist/components/layout/PageAdvertisements.d.ts.map +1 -0
  118. package/dist/components/layout/index.d.ts +1 -0
  119. package/dist/components/layout/index.d.ts.map +1 -1
  120. package/dist/components/layout/index.js +8 -1
  121. package/dist/components/product/index.js +10 -8
  122. package/dist/components/store/index.js +11 -9
  123. package/dist/components/store/index.js.map +1 -1
  124. package/dist/{document-class-67HTP45G.js → document-class-7AXAAWGZ.js} +6 -5
  125. package/dist/{document-class-67HTP45G.js.map → document-class-7AXAAWGZ.js.map} +1 -1
  126. package/dist/hooks/index.js +9 -7
  127. package/dist/hooks/useGtm.js +9 -7
  128. package/dist/hooks/useMoney.js +9 -7
  129. package/dist/hooks/useStore.js +9 -7
  130. package/dist/index.js +9 -7
  131. package/dist/index.js.map +1 -1
  132. package/dist/{not-found-QTHBFPNT.js → not-found-3EEMQZMU.js} +11 -9
  133. package/dist/not-found-3EEMQZMU.js.map +1 -0
  134. package/dist/providers/index.js +9 -7
  135. package/dist/routes/account/orders.js +1 -1
  136. package/dist/routes/account.js +6 -6
  137. package/dist/routes/blog.js +5 -5
  138. package/dist/routes/brands.js +1 -1
  139. package/dist/routes/cart.js +13 -11
  140. package/dist/routes/cart.js.map +1 -1
  141. package/dist/routes/home.js +12 -10
  142. package/dist/routes/loyalty.js +2 -2
  143. package/dist/routes/page.js +1 -1
  144. package/dist/routes/product-listing.js +11 -9
  145. package/dist/routes/product-listing.js.map +1 -1
  146. package/dist/routes/product.js +11 -9
  147. package/dist/routes/product.js.map +1 -1
  148. package/dist/routes/root/beforeLoad.d.ts +2 -2
  149. package/dist/routes/root/beforeLoad.d.ts.map +1 -1
  150. package/dist/routes/root/head.d.ts.map +1 -1
  151. package/dist/routes/testimonials.js +2 -2
  152. package/dist/routes/thank-you.js +1 -1
  153. package/dist/skeleton.js +12 -10
  154. package/dist/tanstack/document-class.d.ts.map +1 -1
  155. package/dist/tanstack/index.d.ts +1 -0
  156. package/dist/tanstack/index.d.ts.map +1 -1
  157. package/dist/tanstack/stylesheet.d.ts +15 -0
  158. package/dist/tanstack/stylesheet.d.ts.map +1 -0
  159. package/dist/tanstack.js +34 -5
  160. package/dist/tanstack.js.map +1 -1
  161. package/dist/utils/index.js +1 -1
  162. package/dist/vite/index.js +1 -1
  163. package/package.json +12 -3
  164. package/tailwind/components/Component.tsx.txt +21 -0
  165. package/tailwind/components/ComponentRegistry.ts.txt +66 -0
  166. package/tailwind/components/cart/CartItem.tsx.txt +211 -0
  167. package/tailwind/components/cart/CartSummary.tsx.txt +269 -0
  168. package/tailwind/components/cart/PreOrderNotification.tsx.txt +16 -0
  169. package/tailwind/components/cart/PriceQuoteButton.tsx.txt +21 -0
  170. package/tailwind/components/cart/SeoCartWidget.tsx.txt +99 -0
  171. package/tailwind/components/cart/index.ts.txt +11 -0
  172. package/tailwind/components/cart/lazy.ts.txt +15 -0
  173. package/tailwind/components/collapse/Collapse.tsx.txt +95 -0
  174. package/tailwind/components/collapse/index.ts.txt +41 -0
  175. package/tailwind/components/common/Breadcrumb.tsx.txt +27 -0
  176. package/tailwind/components/common/BreadcrumbJsonLd.tsx.txt +40 -0
  177. package/tailwind/components/common/BreadcrumbTrail.tsx.txt +97 -0
  178. package/tailwind/components/common/CurrencySymbol.tsx.txt +8 -0
  179. package/tailwind/components/common/DeferredData.tsx.txt +122 -0
  180. package/tailwind/components/common/ErrorPage.tsx.txt +69 -0
  181. package/tailwind/components/common/Image.tsx.txt +119 -0
  182. package/tailwind/components/common/Link.tsx.txt +36 -0
  183. package/tailwind/components/common/Link.types.ts.txt +85 -0
  184. package/tailwind/components/common/NoContent.tsx.txt +27 -0
  185. package/tailwind/components/common/RenderWhenVisible.tsx.txt +92 -0
  186. package/tailwind/components/common/index.ts.txt +42 -0
  187. package/tailwind/components/common/lazy.ts.txt +28 -0
  188. package/tailwind/components/defineComponent.ts.txt +32 -0
  189. package/tailwind/components/drawer/Drawer.tsx.txt +219 -0
  190. package/tailwind/components/drawer/index.ts.txt +38 -0
  191. package/tailwind/components/dropdown/Dropdown.tsx.txt +166 -0
  192. package/tailwind/components/dropdown/index.ts.txt +40 -0
  193. package/tailwind/components/home/BundleComponent.tsx.txt +35 -0
  194. package/tailwind/components/home/ComponentErrorBoundary.tsx.txt +98 -0
  195. package/tailwind/components/home/FeaturedProductsStyle1.tsx.txt +125 -0
  196. package/tailwind/components/home/FeaturedProductsStyle2.tsx.txt +127 -0
  197. package/tailwind/components/home/FeaturedProductsStyle3.tsx.txt +71 -0
  198. package/tailwind/components/home/FixedBanner.tsx.txt +68 -0
  199. package/tailwind/components/home/FixedProducts.tsx.txt +72 -0
  200. package/tailwind/components/home/HomePageRenderer.tsx.txt +284 -0
  201. package/tailwind/components/home/PageBlocks.tsx.txt +24 -0
  202. package/tailwind/components/home/ParallaxBackground.tsx.txt +50 -0
  203. package/tailwind/components/home/PhotosSlider.tsx.txt +61 -0
  204. package/tailwind/components/home/ProductsSlider.tsx.txt +87 -0
  205. package/tailwind/components/home/ReorderProducts.tsx.txt +38 -0
  206. package/tailwind/components/home/SquarePhotos.tsx.txt +68 -0
  207. package/tailwind/components/home/StoreFeatures.tsx.txt +34 -0
  208. package/tailwind/components/home/Testimonials.tsx.txt +36 -0
  209. package/tailwind/components/home/Youtube.tsx.txt +48 -0
  210. package/tailwind/components/home/index.ts.txt +50 -0
  211. package/tailwind/components/home/lazy.ts.txt +17 -0
  212. package/tailwind/components/home/register.ts.txt +44 -0
  213. package/tailwind/components/home/reorder-hooks.ts.txt +52 -0
  214. package/tailwind/components/home/types.ts.txt +4 -0
  215. package/tailwind/components/layout/Copyright.tsx.txt +23 -0
  216. package/tailwind/components/layout/CustomerLayout.tsx.txt +91 -0
  217. package/tailwind/components/layout/Footer.tsx.txt +343 -0
  218. package/tailwind/components/layout/Header.tsx.txt +154 -0
  219. package/tailwind/components/layout/MasterLayout.tsx.txt +63 -0
  220. package/tailwind/components/layout/PageAdvertisements.tsx.txt +131 -0
  221. package/tailwind/components/layout/WidgetHead.tsx.txt +53 -0
  222. package/tailwind/components/layout/index.ts.txt +27 -0
  223. package/tailwind/components/layout/lazy.ts.txt +25 -0
  224. package/tailwind/components/layout/types.ts.txt +11 -0
  225. package/tailwind/components/modal/ImageModal.tsx.txt +70 -0
  226. package/tailwind/components/modal/Modal.tsx.txt +245 -0
  227. package/tailwind/components/modal/index.ts.txt +39 -0
  228. package/tailwind/components/modal/lazy.ts.txt +10 -0
  229. package/tailwind/components/navigation/MainMenu.tsx.txt +94 -0
  230. package/tailwind/components/navigation/MobileMenu.tsx.txt +160 -0
  231. package/tailwind/components/navigation/index.ts.txt +4 -0
  232. package/tailwind/components/navigation/lazy.ts.txt +11 -0
  233. package/tailwind/components/product/AddToCartForm.tsx.txt +365 -0
  234. package/tailwind/components/product/ProductCard.tsx.txt +305 -0
  235. package/tailwind/components/product/ProductDetails.tsx.txt +267 -0
  236. package/tailwind/components/product/ProductGallery.tsx.txt +234 -0
  237. package/tailwind/components/product/index.ts.txt +15 -0
  238. package/tailwind/components/product/lazy.ts.txt +9 -0
  239. package/tailwind/components/snippets/AppsSnippets.tsx.txt +225 -0
  240. package/tailwind/components/snippets/SallaSdkScripts.tsx.txt +14 -0
  241. package/tailwind/components/snippets/index.ts.txt +4 -0
  242. package/tailwind/components/store/StoreClosedNotification.tsx.txt +73 -0
  243. package/tailwind/components/store/index.ts.txt +8 -0
  244. package/tailwind/components/store/lazy.ts.txt +8 -0
  245. package/tailwind/components/toast/Toaster.tsx.txt +177 -0
  246. package/tailwind/components/toast/index.ts.txt +10 -0
  247. package/tailwind/components/toast/types.ts.txt +38 -0
  248. package/tailwind/components/toast/useToast.ts.txt +61 -0
  249. package/tailwind/components/tracking/GoogleTag.tsx.txt +77 -0
  250. package/tailwind/components/tracking/SiftSnippet.tsx.txt +49 -0
  251. package/tailwind/components/tracking/TwilightBundles.tsx.txt +67 -0
  252. package/tailwind/components/tracking/index.ts.txt +11 -0
  253. package/tailwind/components/tracking/lazy.ts.txt +11 -0
  254. package/tailwind/components/useComponent.ts.txt +12 -0
  255. package/tailwind/routes/account/index.tsx.txt +16 -0
  256. package/tailwind/routes/account/notifications/NotificationsPage.tsx.txt +54 -0
  257. package/tailwind/routes/account/notifications/index.tsx.txt +39 -0
  258. package/tailwind/routes/account/notifications/loader.ts.txt +22 -0
  259. package/tailwind/routes/account/notifications/types.ts.txt +18 -0
  260. package/tailwind/routes/account/orders/OrderSinglePage.tsx.txt +181 -0
  261. package/tailwind/routes/account/orders/OrdersPage.tsx.txt +28 -0
  262. package/tailwind/routes/account/orders/index.tsx.txt +86 -0
  263. package/tailwind/routes/account/orders/loader.ts.txt +66 -0
  264. package/tailwind/routes/account/orders/single/OrderActions.tsx.txt +197 -0
  265. package/tailwind/routes/account/orders/single/OrderHeader.tsx.txt +143 -0
  266. package/tailwind/routes/account/orders/single/OrderItemRow.tsx.txt +209 -0
  267. package/tailwind/routes/account/orders/single/OrderSections.tsx.txt +215 -0
  268. package/tailwind/routes/account/orders/single/types.ts.txt +38 -0
  269. package/tailwind/routes/account/orders/types.ts.txt +29 -0
  270. package/tailwind/routes/account/profile/ProfilePage.tsx.txt +30 -0
  271. package/tailwind/routes/account/profile/index.tsx.txt +39 -0
  272. package/tailwind/routes/account/profile/loader.ts.txt +16 -0
  273. package/tailwind/routes/account/profile/types.ts.txt +5 -0
  274. package/tailwind/routes/account/settings/SettingsPage.tsx.txt +13 -0
  275. package/tailwind/routes/account/settings/index.tsx.txt +39 -0
  276. package/tailwind/routes/account/settings/loader.ts.txt +13 -0
  277. package/tailwind/routes/account/settings/types.ts.txt +5 -0
  278. package/tailwind/routes/account/types.ts.txt +320 -0
  279. package/tailwind/routes/account/wallet/WalletPage.tsx.txt +195 -0
  280. package/tailwind/routes/account/wallet/index.tsx.txt +38 -0
  281. package/tailwind/routes/account/wallet/loader.ts.txt +27 -0
  282. package/tailwind/routes/account/wallet/types.ts.txt +11 -0
  283. package/tailwind/routes/account/wishlist/WishlistPage.tsx.txt +314 -0
  284. package/tailwind/routes/account/wishlist/WishlistShare.tsx.txt +248 -0
  285. package/tailwind/routes/account/wishlist/index.tsx.txt +40 -0
  286. package/tailwind/routes/account/wishlist/loader.ts.txt +26 -0
  287. package/tailwind/routes/account/wishlist/types.ts.txt +9 -0
  288. package/tailwind/routes/blog/BlogAuthorPage.tsx.txt +82 -0
  289. package/tailwind/routes/blog/BlogCategoryPage.tsx.txt +84 -0
  290. package/tailwind/routes/blog/BlogPage.tsx.txt +191 -0
  291. package/tailwind/routes/blog/BlogSinglePage.tsx.txt +168 -0
  292. package/tailwind/routes/blog/BlogTagPage.tsx.txt +84 -0
  293. package/tailwind/routes/blog/BlogTags.tsx.txt +54 -0
  294. package/tailwind/routes/blog/components.tsx.txt +87 -0
  295. package/tailwind/routes/blog/index.tsx.txt +238 -0
  296. package/tailwind/routes/blog/loader.ts.txt +173 -0
  297. package/tailwind/routes/blog/types.ts.txt +106 -0
  298. package/tailwind/routes/brands/BrandsPage.tsx.txt +179 -0
  299. package/tailwind/routes/brands/index.tsx.txt +47 -0
  300. package/tailwind/routes/brands/loader.ts.txt +14 -0
  301. package/tailwind/routes/brands/types.ts.txt +53 -0
  302. package/tailwind/routes/cart/CartPage.tsx.txt +112 -0
  303. package/tailwind/routes/cart/index.tsx.txt +39 -0
  304. package/tailwind/routes/cart/loader.ts.txt +15 -0
  305. package/tailwind/routes/cart/types.ts.txt +6 -0
  306. package/tailwind/routes/home/HomePage.tsx.txt +53 -0
  307. package/tailwind/routes/home/index.tsx.txt +56 -0
  308. package/tailwind/routes/home/loader.ts.txt +24 -0
  309. package/tailwind/routes/home/types.ts.txt +11 -0
  310. package/tailwind/routes/index.ts.txt +94 -0
  311. package/tailwind/routes/lazy.ts.txt +105 -0
  312. package/tailwind/routes/loyalty/LoyaltyPage.tsx.txt +17 -0
  313. package/tailwind/routes/loyalty/LoyaltyPointsPage.tsx.txt +11 -0
  314. package/tailwind/routes/loyalty/index.tsx.txt +81 -0
  315. package/tailwind/routes/loyalty/loader.ts.txt +53 -0
  316. package/tailwind/routes/loyalty/types.ts.txt +109 -0
  317. package/tailwind/routes/not-found.tsx.txt +50 -0
  318. package/tailwind/routes/page/PageSingle.tsx.txt +34 -0
  319. package/tailwind/routes/page/index.tsx.txt +60 -0
  320. package/tailwind/routes/page/loader.ts.txt +19 -0
  321. package/tailwind/routes/page/types.ts.txt +34 -0
  322. package/tailwind/routes/product/ProductPage.tsx.txt +77 -0
  323. package/tailwind/routes/product/index.tsx.txt +157 -0
  324. package/tailwind/routes/product/loader.ts.txt +35 -0
  325. package/tailwind/routes/product/types.ts.txt +6 -0
  326. package/tailwind/routes/product-listing/ProductListPage.tsx.txt +321 -0
  327. package/tailwind/routes/product-listing/index.tsx.txt +95 -0
  328. package/tailwind/routes/product-listing/loader.ts.txt +323 -0
  329. package/tailwind/routes/product-listing/types.ts.txt +96 -0
  330. package/tailwind/routes/product-listing/useAppliedFilters.ts.txt +130 -0
  331. package/tailwind/routes/product-short-link.ts.txt +104 -0
  332. package/tailwind/routes/root/beforeLoad.ts.txt +354 -0
  333. package/tailwind/routes/root/head.ts.txt +424 -0
  334. package/tailwind/routes/root/index.ts.txt +2 -0
  335. package/tailwind/routes/seo-redirects.ts.txt +82 -0
  336. package/tailwind/routes/testimonials/ReviewsPage.tsx.txt +12 -0
  337. package/tailwind/routes/testimonials/TestimonialsPage.tsx.txt +80 -0
  338. package/tailwind/routes/testimonials/index.tsx.txt +80 -0
  339. package/tailwind/routes/testimonials/loader.ts.txt +29 -0
  340. package/tailwind/routes/testimonials/types.ts.txt +9 -0
  341. package/tailwind/routes/thank-you/ThankYouPage.tsx.txt +241 -0
  342. package/tailwind/routes/thank-you/index.tsx.txt +49 -0
  343. package/tailwind/routes/thank-you/loader.ts.txt +40 -0
  344. package/tailwind/routes/thank-you/types.ts.txt +16 -0
  345. package/tailwind/routes/types.ts.txt +41 -0
  346. package/dist/BlogAuthorPage-GTF4UGSS.js.map +0 -1
  347. package/dist/BlogCategoryPage-TN7Y4NBP.js.map +0 -1
  348. package/dist/BlogPage-TDB3M3PI.js.map +0 -1
  349. package/dist/BlogSinglePage-4A52Q5QW.js.map +0 -1
  350. package/dist/BlogTagPage-TOVPBETA.js.map +0 -1
  351. package/dist/BrandsPage-VUDGYSQI.js.map +0 -1
  352. package/dist/Breadcrumb-CI3SN5YR.js.map +0 -1
  353. package/dist/CartItem-BHLEURAB.js.map +0 -1
  354. package/dist/CartSummary-QERVESYN.js.map +0 -1
  355. package/dist/CustomerLayout-VRZUWGQK.js.map +0 -1
  356. package/dist/LoyaltyPage-CGTHWJ76.js.map +0 -1
  357. package/dist/LoyaltyPointsPage-QSU6K3PW.js.map +0 -1
  358. package/dist/MobileMenu-U4BVQYKH.js.map +0 -1
  359. package/dist/NotificationsPage-ZRRQY7TF.js.map +0 -1
  360. package/dist/OrderSinglePage-O3XYVMG5.js.map +0 -1
  361. package/dist/OrdersPage-CMXZF5MI.js.map +0 -1
  362. package/dist/ProductDetails-65GDABI7.js.map +0 -1
  363. package/dist/ProfilePage-SNJ4WXU4.js.map +0 -1
  364. package/dist/SeoCartWidget-DBJAXJKT.js.map +0 -1
  365. package/dist/SettingsPage-FLTIOPU5.js.map +0 -1
  366. package/dist/ThankYouPage-5X6B4X3T.js.map +0 -1
  367. package/dist/WalletPage-H2BKIDPA.js.map +0 -1
  368. package/dist/WishlistPage-RS5UCIQ3.js.map +0 -1
  369. package/dist/chunk-7WAXN2PP.js +0 -14
  370. package/dist/chunk-NZVR4OF7.js.map +0 -1
  371. package/dist/chunk-SDFDS4Q3.js.map +0 -1
  372. package/dist/not-found-QTHBFPNT.js.map +0 -1
@@ -0,0 +1,245 @@
1
+ /**
2
+ * Modal Component
3
+ *
4
+ * A controlled modal dialog with backdrop, close button, and keyboard support.
5
+ *
6
+ * @example
7
+ * ```tsx
8
+ * function MyComponent() {
9
+ * const [isOpen, setIsOpen] = useState(false);
10
+ *
11
+ * return (
12
+ * <>
13
+ * <button onClick={() => setIsOpen(true)}>Open Modal</button>
14
+ * <Modal isOpen={isOpen} onClose={() => setIsOpen(false)}>
15
+ * <Modal.Header>Modal Title</Modal.Header>
16
+ * <Modal.Body>Modal content here</Modal.Body>
17
+ * <Modal.Footer>
18
+ * <Button onClick={() => setIsOpen(false)}>Close</Button>
19
+ * </Modal.Footer>
20
+ * </Modal>
21
+ * </>
22
+ * );
23
+ * }
24
+ * ```
25
+ */
26
+
27
+ import React, { useEffect, useCallback, useRef, type ReactNode, type HTMLAttributes } from 'react';
28
+ import { createPortal } from 'react-dom';
29
+
30
+ export interface ModalProps {
31
+ isOpen: boolean;
32
+ onClose: () => void;
33
+ children: ReactNode;
34
+ /**
35
+ * Close modal when clicking backdrop
36
+ * @default true
37
+ */
38
+ closeOnBackdropClick?: boolean;
39
+ /**
40
+ * Close modal on Escape key
41
+ * @default true
42
+ */
43
+ closeOnEscape?: boolean;
44
+ /**
45
+ * Prevent body scroll when modal is open
46
+ * @default true
47
+ */
48
+ preventBodyScroll?: boolean;
49
+ /**
50
+ * Size of the modal
51
+ * @default 'md'
52
+ */
53
+ size?: 'sm' | 'md' | 'lg' | 'xl' | 'full';
54
+ /**
55
+ * Position of the modal
56
+ * @default 'center'
57
+ */
58
+ position?: 'center' | 'top';
59
+ /**
60
+ * Additional className for the modal content
61
+ */
62
+ className?: string;
63
+ }
64
+
65
+ const sizeClasses = {
66
+ sm: 'max-w-sm',
67
+ md: 'max-w-md',
68
+ lg: 'max-w-lg',
69
+ xl: 'max-w-xl',
70
+ full: 'max-w-full mx-4',
71
+ };
72
+
73
+ const positionClasses = {
74
+ center: 'items-center',
75
+ top: 'items-start pt-10',
76
+ };
77
+
78
+ export function Modal({
79
+ isOpen,
80
+ onClose,
81
+ children,
82
+ closeOnBackdropClick = true,
83
+ closeOnEscape = true,
84
+ preventBodyScroll = true,
85
+ size = 'md',
86
+ position = 'center',
87
+ className,
88
+ }: ModalProps) {
89
+ const modalRef = useRef<HTMLDivElement>(null);
90
+ const previousActiveElement = useRef<HTMLElement | null>(null);
91
+
92
+ // Handle Escape key
93
+ const handleKeyDown = useCallback(
94
+ (event: KeyboardEvent) => {
95
+ if (event.key === 'Escape' && closeOnEscape) {
96
+ onClose();
97
+ }
98
+ },
99
+ [closeOnEscape, onClose]
100
+ );
101
+
102
+ // Bound to the backdrop, which covers the wrapper and is a sibling of the panel
103
+ const handleBackdropClick = useCallback(
104
+ (event: React.MouseEvent) => {
105
+ if (closeOnBackdropClick && event.target === event.currentTarget) {
106
+ onClose();
107
+ }
108
+ },
109
+ [closeOnBackdropClick, onClose]
110
+ );
111
+
112
+ // Focus management and body scroll
113
+ useEffect(() => {
114
+ if (isOpen) {
115
+ // Store the previously focused element
116
+ previousActiveElement.current = document.activeElement as HTMLElement;
117
+
118
+ // Focus the modal
119
+ modalRef.current?.focus();
120
+
121
+ // Prevent body scroll
122
+ if (preventBodyScroll) {
123
+ document.body.classList.add('menu-opened');
124
+ }
125
+
126
+ // Add keyboard listener
127
+ document.addEventListener('keydown', handleKeyDown);
128
+ }
129
+
130
+ return () => {
131
+ document.removeEventListener('keydown', handleKeyDown);
132
+
133
+ // Restore body scroll
134
+ if (preventBodyScroll) {
135
+ document.body.classList.remove('menu-opened');
136
+ }
137
+
138
+ // Restore focus
139
+ previousActiveElement.current?.focus();
140
+ };
141
+ }, [isOpen, handleKeyDown, preventBodyScroll]);
142
+
143
+ if (!isOpen || typeof document === 'undefined') {
144
+ return null;
145
+ }
146
+
147
+ return createPortal(
148
+ <div
149
+ className={`fixed inset-0 z-50 flex justify-center ${positionClasses[position]}`}
150
+ aria-modal="true"
151
+ role="dialog"
152
+ >
153
+ {/* Backdrop */}
154
+ <div
155
+ className="absolute inset-0 bg-black/50 transition-opacity"
156
+ role="presentation"
157
+ onClick={handleBackdropClick}
158
+ onKeyDown={(e) => {
159
+ if ((e.key === 'Enter' || e.key === ' ') && closeOnBackdropClick) {
160
+ e.preventDefault();
161
+ onClose();
162
+ }
163
+ }}
164
+ />
165
+
166
+ {/* Modal Content */}
167
+ <div
168
+ ref={modalRef}
169
+ tabIndex={-1}
170
+ className={`relative z-10 w-full rounded-lg bg-white shadow-xl transform transition-all duration-200 ease-out ${sizeClasses[size]} ${isOpen ? 'scale-100 opacity-100' : 'scale-95 opacity-0'} ${className || ''}`}
171
+ >
172
+ {children}
173
+ </div>
174
+ </div>,
175
+ document.body
176
+ );
177
+ }
178
+
179
+ // Modal Sub-components
180
+ export interface ModalHeaderProps extends HTMLAttributes<HTMLDivElement> {
181
+ children: ReactNode;
182
+ showCloseButton?: boolean;
183
+ onClose?: () => void;
184
+ }
185
+
186
+ Modal.Header = function ModalHeader({
187
+ children,
188
+ showCloseButton = true,
189
+ onClose,
190
+ className,
191
+ ...props
192
+ }: ModalHeaderProps) {
193
+ return (
194
+ <div
195
+ className={`flex items-center justify-between border-b border-gray-200 px-6 py-4 ${className || ''}`}
196
+ {...props}
197
+ >
198
+ <h2 className="text-lg font-semibold text-gray-900">{children}</h2>
199
+ {showCloseButton && onClose && (
200
+ <button
201
+ type="button"
202
+ onClick={onClose}
203
+ className="rounded-md text-gray-400 hover:text-gray-500 focus:outline-none focus:ring-2 focus:ring-gray-500"
204
+ >
205
+ <span className="sr-only">Close</span>
206
+ <svg className="h-6 w-6" fill="none" viewBox="0 0 24 24" stroke="currentColor">
207
+ <path
208
+ strokeLinecap="round"
209
+ strokeLinejoin="round"
210
+ strokeWidth={2}
211
+ d="M6 18L18 6M6 6l12 12"
212
+ />
213
+ </svg>
214
+ </button>
215
+ )}
216
+ </div>
217
+ );
218
+ };
219
+
220
+ export interface ModalBodyProps extends HTMLAttributes<HTMLDivElement> {
221
+ children: ReactNode;
222
+ }
223
+
224
+ Modal.Body = function ModalBody({ children, className, ...props }: ModalBodyProps) {
225
+ return (
226
+ <div className={`px-6 py-4 ${className || ''}`} {...props}>
227
+ {children}
228
+ </div>
229
+ );
230
+ };
231
+
232
+ export interface ModalFooterProps extends HTMLAttributes<HTMLDivElement> {
233
+ children: ReactNode;
234
+ }
235
+
236
+ Modal.Footer = function ModalFooter({ children, className, ...props }: ModalFooterProps) {
237
+ return (
238
+ <div
239
+ className={`flex items-center justify-end gap-3 border-t border-gray-200 px-6 py-4 ${className || ''}`}
240
+ {...props}
241
+ >
242
+ {children}
243
+ </div>
244
+ );
245
+ };
@@ -0,0 +1,39 @@
1
+ /**
2
+ * Modal Component System
3
+ *
4
+ * Controlled modal dialog with composable parts.
5
+ * Eager-loaded because Modal uses compound component pattern (Modal.Header, Modal.Body).
6
+ * ImageModal is lazy-loaded since it's a standalone component.
7
+ *
8
+ * @example
9
+ * ```tsx
10
+ * import { Modal } from '@salla.sa/twilight-theme-engine/components/modal';
11
+ *
12
+ * function ConfirmDialog({ isOpen, onClose, onConfirm }) {
13
+ * return (
14
+ * <Modal isOpen={isOpen} onClose={onClose} size="sm">
15
+ * <Modal.Header onClose={onClose}>Confirm Action</Modal.Header>
16
+ * <Modal.Body>Are you sure you want to proceed?</Modal.Body>
17
+ * <Modal.Footer>
18
+ * <Button variant="outline" onClick={onClose}>Cancel</Button>
19
+ * <Button onClick={onConfirm}>Confirm</Button>
20
+ * </Modal.Footer>
21
+ * </Modal>
22
+ * );
23
+ * }
24
+ * ```
25
+ */
26
+
27
+ // Modal is eager (compound component pattern)
28
+ export {
29
+ Modal,
30
+ type ModalProps,
31
+ type ModalHeaderProps,
32
+ type ModalBodyProps,
33
+ type ModalFooterProps,
34
+ } from './Modal';
35
+
36
+ // ImageModal is lazy (standalone component)
37
+ import { LazyImageModal } from './lazy';
38
+ export { LazyImageModal as ImageModal };
39
+ export type { ImageModalProps } from './ImageModal';
@@ -0,0 +1,10 @@
1
+ import { lazy } from 'react';
2
+
3
+ /**
4
+ * Lazy-loaded modal components
5
+ * ImageModal is lazy-loaded since it's a standalone component.
6
+ * Modal is kept eager because it uses compound component pattern.
7
+ */
8
+ export const LazyImageModal = lazy(() =>
9
+ import('./ImageModal').then((m) => ({ default: m.ImageModal }))
10
+ );
@@ -0,0 +1,94 @@
1
+ import { useMemo, memo } from 'react';
2
+ import { useQuery } from '@tanstack/react-query';
3
+ import { useTwilight } from '../../providers/twilight-context';
4
+ import { useTranslation } from '../../providers/I18nProvider';
5
+ import { Link } from '../common';
6
+ import { menu } from '../../api/menu';
7
+ import type { MenuItem } from '../../types';
8
+
9
+ const SKELETON_ITEMS = [
10
+ { id: 'first', width: 'w-16' },
11
+ { id: 'second', width: 'w-20' },
12
+ { id: 'third', width: 'w-24' },
13
+ { id: 'fourth', width: 'w-16' },
14
+ { id: 'fifth', width: 'w-20' },
15
+ ];
16
+
17
+ const MainMenuSkeleton = memo(function MainMenuSkeleton() {
18
+ return (
19
+ <nav>
20
+ <ul className="main-menu">
21
+ {SKELETON_ITEMS.map(({ id, width }) => (
22
+ <li key={id} className="!hidden lg:!block root-level">
23
+ <Link to="#">
24
+ <span className={`inline-block animate-pulse rounded bg-gray-200 h-4 ${width}`} />
25
+ </Link>
26
+ </li>
27
+ ))}
28
+ </ul>
29
+ </nav>
30
+ );
31
+ });
32
+
33
+ export function MainMenu() {
34
+ const { theme } = useTwilight();
35
+ const { data: menus = [], isLoading } = useQuery(menu.queries.header());
36
+ const { t } = useTranslation();
37
+
38
+ const { visibleMenus, hiddenMenus } = useMemo(() => {
39
+ const enableMore = theme?.settings?.is_more_button_enabled;
40
+ const visibleCount = 7;
41
+
42
+ if (enableMore && menus.length > visibleCount) {
43
+ return {
44
+ visibleMenus: menus.slice(0, visibleCount),
45
+ hiddenMenus: menus.slice(visibleCount),
46
+ };
47
+ }
48
+
49
+ return { visibleMenus: menus, hiddenMenus: [] };
50
+ }, [menus, theme?.settings?.enable_more_menu, theme?.settings?.is_more_button_enabled]);
51
+
52
+ if (isLoading) {
53
+ return <MainMenuSkeleton />;
54
+ }
55
+
56
+ const renderItem = (item: MenuItem, isChild = false, inMoreMenu = false) => {
57
+ const hasChildren = item.has_children && item.children && item.children.length > 0;
58
+ const showDropdown = hasChildren && !inMoreMenu;
59
+
60
+ return (
61
+ <li
62
+ key={item.id}
63
+ className={`${isChild ? 'relative' : '!hidden lg:!block root-level'} ${hasChildren ? 'has-children' : ''}`}
64
+ >
65
+ <Link to={item.url}>
66
+ <span>{item.title}</span>
67
+ </Link>
68
+ {showDropdown && (
69
+ <div className="sub-menu w-56">
70
+ <ul>{item?.children?.map((child: MenuItem) => renderItem(child, true))}</ul>
71
+ </div>
72
+ )}
73
+ </li>
74
+ );
75
+ };
76
+
77
+ return (
78
+ <nav>
79
+ <ul className="main-menu">
80
+ {visibleMenus.map((item) => renderItem(item))}
81
+ {hiddenMenus.length > 0 && (
82
+ <li id="more-menu-dropdown" className="!hidden lg:!block root-level has-children">
83
+ <Link to="#">
84
+ <span>{t('common.titles.more', 'More')}</span>
85
+ </Link>
86
+ <div className="sub-menu w-56">
87
+ <ul>{hiddenMenus.map((item) => renderItem(item, true, true))}</ul>
88
+ </div>
89
+ </li>
90
+ )}
91
+ </ul>
92
+ </nav>
93
+ );
94
+ }
@@ -0,0 +1,160 @@
1
+ import { useState, useCallback, useEffect, memo } from 'react';
2
+ import { useQuery } from '@tanstack/react-query';
3
+ import { useTwilight } from '../../providers/twilight-context';
4
+ import { useTranslation } from '../../providers/I18nProvider';
5
+ import { Drawer } from '../../components/drawer';
6
+ import { Link } from '../common';
7
+ import { menu } from '../../api/menu';
8
+ import type { MenuItem } from '../../types';
9
+
10
+ export interface MobileMenuProps {
11
+ isOpen: boolean;
12
+ onClose: () => void;
13
+ }
14
+
15
+ const MOBILE_SKELETON_ITEMS = 5;
16
+ const SKELETON_WIDTHS = ['w-32', 'w-28', 'w-36', 'w-24', 'w-30'];
17
+
18
+ const MobileMenuSkeleton = memo(function MobileMenuSkeleton() {
19
+ return (
20
+ <ul className="divide-y divide-gray-100">
21
+ {Array.from({ length: MOBILE_SKELETON_ITEMS }, (_, i) => (
22
+ <li key={i} className="py-4">
23
+ <span
24
+ className={`inline-block animate-pulse rounded bg-gray-200 h-5 ${SKELETON_WIDTHS[i]}`}
25
+ />
26
+ </li>
27
+ ))}
28
+ </ul>
29
+ );
30
+ });
31
+
32
+ export function MobileMenu(props: MobileMenuProps) {
33
+ if (!props.isOpen) return null;
34
+ return <MobileMenuContent {...props} />;
35
+ }
36
+
37
+ function MobileMenuContent({ onClose }: MobileMenuProps) {
38
+ const { theme } = useTwilight();
39
+ const { data: menus = [], isLoading } = useQuery(menu.queries.header());
40
+ const { t } = useTranslation();
41
+
42
+ const [menuStack, setMenuStack] = useState<{ title: string; items: MenuItem[] }[]>([]);
43
+ const [isAnimating, setIsAnimating] = useState(false);
44
+
45
+ const currentLevel = menuStack[menuStack.length - 1] ?? { title: '', items: menus };
46
+ const isRootLevel = menuStack.length === 0;
47
+
48
+ const openSubmenu = useCallback((item: MenuItem) => {
49
+ if (item.children && item.children.length > 0) {
50
+ setIsAnimating(true);
51
+ setMenuStack((prev) => [...prev, { title: item.title, items: item.children! }]);
52
+ requestAnimationFrame(() => {
53
+ setIsAnimating(false);
54
+ });
55
+ }
56
+ }, []);
57
+
58
+ const goBack = useCallback(() => {
59
+ setIsAnimating(true);
60
+ setMenuStack((prev) => prev.slice(0, -1));
61
+ requestAnimationFrame(() => {
62
+ setIsAnimating(false);
63
+ });
64
+ }, []);
65
+
66
+ useEffect(() => {
67
+ document.body.classList.add('menu-opened');
68
+ return () => document.body.classList.remove('menu-opened');
69
+ }, []);
70
+
71
+ const getListAnimationClass = () => {
72
+ if (isAnimating) {
73
+ return theme.is_rtl ? 'translate-x-4 opacity-0' : '-translate-x-4 opacity-0';
74
+ }
75
+ return 'translate-x-0 opacity-100';
76
+ };
77
+
78
+ return (
79
+ <>
80
+ <Drawer
81
+ isOpen
82
+ onClose={onClose}
83
+ size="md"
84
+ closeOnBackdropClick={true}
85
+ preventBodyScroll={false}
86
+ className="overflow-visible"
87
+ >
88
+ <button
89
+ type="button"
90
+ onClick={onClose}
91
+ aria-label={t('common.buttons.close', 'Close')}
92
+ className="absolute top-0 w-12 h-12 flex items-center justify-center bg-[#d35a51] text-white hover:bg-red-600 transition-colors z-50 ltr:-right-12 rtl:-left-12"
93
+ >
94
+ <i className="sicon-cancel text-xl leading-none"></i>
95
+ </button>
96
+
97
+ <Drawer.Header showCloseButton={false} onClose={onClose}>
98
+ <div className="flex items-center gap-2 w-full">
99
+ {!isRootLevel && (
100
+ <button
101
+ type="button"
102
+ className="text-gray-500 hover:text-gray-800 transition-colors flex-shrink-0"
103
+ onClick={goBack}
104
+ aria-label={t('common.buttons.back', 'Back')}
105
+ >
106
+ <i className="sicon-keyboard_arrow_left text-xl flex items-center justify-center"></i>
107
+ </button>
108
+ )}
109
+ <span className="font-bold text-lg truncate flex-1 text-center pr-6 rtl:pl-6 rtl:pr-0">
110
+ {isRootLevel ? t('blocks.header.main_menu', 'Menu') : currentLevel.title}
111
+ </span>
112
+ </div>
113
+ </Drawer.Header>
114
+ <Drawer.Body className="p-0 overflow-hidden">
115
+ <nav className="mobile-menu h-full overflow-y-auto">
116
+ {isLoading ? (
117
+ <MobileMenuSkeleton />
118
+ ) : (
119
+ <ul
120
+ className={`divide-y divide-gray-100 transition-all duration-200 ease-out ${getListAnimationClass()}`}
121
+ >
122
+ {currentLevel.items.map((item) => {
123
+ const hasChildren =
124
+ item.has_children && item.children && item.children.length > 0;
125
+
126
+ return (
127
+ <li key={item.id} className="mobile-menu-item">
128
+ {hasChildren ? (
129
+ <button
130
+ type="button"
131
+ className="flex items-center justify-between w-full py-4 hover:text-primary transition-colors text-start group"
132
+ onClick={() => openSubmenu(item)}
133
+ >
134
+ <span className="text-gray-800 group-hover:text-primary font-medium text-base">
135
+ {item.title}
136
+ </span>
137
+ <i className="sicon-keyboard_arrow_right rtl:rotate-180 text-gray-500 group-hover:text-primary text-lg flex items-center justify-center h-full"></i>
138
+ </button>
139
+ ) : (
140
+ <Link
141
+ to={item.url}
142
+ className="block w-full py-4 hover:text-primary transition-colors text-gray-800 font-medium text-base group"
143
+ onClick={onClose}
144
+ >
145
+ <span className="group-hover:translate-x-1 rtl:group-hover:-translate-x-1 inline-block transition-transform">
146
+ {item.title}
147
+ </span>
148
+ </Link>
149
+ )}
150
+ </li>
151
+ );
152
+ })}
153
+ </ul>
154
+ )}
155
+ </nav>
156
+ </Drawer.Body>
157
+ </Drawer>
158
+ </>
159
+ );
160
+ }
@@ -0,0 +1,4 @@
1
+ import { LazyMainMenu, LazyMobileMenu } from './lazy';
2
+
3
+ // Lazy-loaded navigation components (code-split)
4
+ export { LazyMainMenu as MainMenu, LazyMobileMenu as MobileMenu };
@@ -0,0 +1,11 @@
1
+ import { lazy } from 'react';
2
+
3
+ /**
4
+ * Lazy-loaded navigation components
5
+ * Use these for code-splitting navigation sections
6
+ */
7
+ export const LazyMainMenu = lazy(() => import('./MainMenu').then((m) => ({ default: m.MainMenu })));
8
+
9
+ export const LazyMobileMenu = lazy(() =>
10
+ import('./MobileMenu').then((m) => ({ default: m.MobileMenu }))
11
+ );