@pretty-chitty/core 1.1.2 → 1.2.1

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 (351) hide show
  1. package/dist/components/BottomBarButton.d.ts +2 -1
  2. package/dist/components/BottomBarButton.d.ts.map +1 -1
  3. package/dist/components/BottomBarButton.js +2 -1
  4. package/dist/components/BottomBarButton.js.map +1 -1
  5. package/dist/components/ClientTrustMatchViewer.d.ts +4 -1
  6. package/dist/components/ClientTrustMatchViewer.d.ts.map +1 -1
  7. package/dist/components/ClientTrustMatchViewer.js +11 -4
  8. package/dist/components/ClientTrustMatchViewer.js.map +1 -1
  9. package/dist/components/ContextGalleryDisplay.js +1 -1
  10. package/dist/components/ContextGalleryDisplay.js.map +1 -1
  11. package/dist/components/DemoWrapper.d.ts +9 -0
  12. package/dist/components/DemoWrapper.d.ts.map +1 -0
  13. package/dist/components/DemoWrapper.js +76 -0
  14. package/dist/components/DemoWrapper.js.map +1 -0
  15. package/dist/components/FullScreenGalleryDisplay.d.ts +2 -0
  16. package/dist/components/FullScreenGalleryDisplay.d.ts.map +1 -0
  17. package/dist/components/FullScreenGalleryDisplay.js +56 -0
  18. package/dist/components/FullScreenGalleryDisplay.js.map +1 -0
  19. package/dist/components/Gallery/AnimationController.d.ts +19 -0
  20. package/dist/components/Gallery/AnimationController.d.ts.map +1 -0
  21. package/dist/components/Gallery/AnimationController.js +82 -0
  22. package/dist/components/Gallery/AnimationController.js.map +1 -0
  23. package/dist/components/Gallery/BuiltItem.d.ts +58 -0
  24. package/dist/components/Gallery/BuiltItem.d.ts.map +1 -0
  25. package/dist/components/Gallery/BuiltItem.js +313 -0
  26. package/dist/components/Gallery/BuiltItem.js.map +1 -0
  27. package/dist/components/Gallery/CameraManager.d.ts +14 -0
  28. package/dist/components/Gallery/CameraManager.d.ts.map +1 -0
  29. package/dist/components/Gallery/CameraManager.js +43 -0
  30. package/dist/components/Gallery/CameraManager.js.map +1 -0
  31. package/dist/components/Gallery/GalleryController.d.ts +30 -0
  32. package/dist/components/Gallery/GalleryController.d.ts.map +1 -0
  33. package/dist/components/Gallery/GalleryController.js +137 -0
  34. package/dist/components/Gallery/GalleryController.js.map +1 -0
  35. package/dist/components/Gallery/GalleryViewer.d.ts +18 -0
  36. package/dist/components/Gallery/GalleryViewer.d.ts.map +1 -0
  37. package/dist/components/Gallery/GalleryViewer.js +141 -0
  38. package/dist/components/Gallery/GalleryViewer.js.map +1 -0
  39. package/dist/components/Gallery/LayoutManager.d.ts +49 -0
  40. package/dist/components/Gallery/LayoutManager.d.ts.map +1 -0
  41. package/dist/components/Gallery/LayoutManager.js +132 -0
  42. package/dist/components/Gallery/LayoutManager.js.map +1 -0
  43. package/dist/components/Gallery/constants.d.ts +13 -0
  44. package/dist/components/Gallery/constants.d.ts.map +1 -0
  45. package/dist/components/Gallery/constants.js +13 -0
  46. package/dist/components/Gallery/constants.js.map +1 -0
  47. package/dist/components/Gallery/index.d.ts +3 -0
  48. package/dist/components/Gallery/index.d.ts.map +1 -0
  49. package/dist/components/Gallery/index.js +2 -0
  50. package/dist/components/Gallery/index.js.map +1 -0
  51. package/dist/components/Gallery/types.d.ts +45 -0
  52. package/dist/components/Gallery/types.d.ts.map +1 -0
  53. package/dist/components/Gallery/types.js +2 -0
  54. package/dist/components/Gallery/types.js.map +1 -0
  55. package/dist/components/GalleryPlayground.js +1 -1
  56. package/dist/components/GalleryPlayground.js.map +1 -1
  57. package/dist/components/GalleryViewer.d.ts +2 -47
  58. package/dist/components/GalleryViewer.d.ts.map +1 -1
  59. package/dist/components/GalleryViewer.js +3 -569
  60. package/dist/components/GalleryViewer.js.map +1 -1
  61. package/dist/components/GameDesigner.d.ts.map +1 -1
  62. package/dist/components/GameDesigner.js +13 -2
  63. package/dist/components/GameDesigner.js.map +1 -1
  64. package/dist/components/InlineGalleryDisplay.d.ts +2 -0
  65. package/dist/components/InlineGalleryDisplay.d.ts.map +1 -0
  66. package/dist/components/InlineGalleryDisplay.js +69 -0
  67. package/dist/components/InlineGalleryDisplay.js.map +1 -0
  68. package/dist/components/LiveButton.d.ts.map +1 -1
  69. package/dist/components/LiveButton.js +1 -1
  70. package/dist/components/LiveButton.js.map +1 -1
  71. package/dist/components/MatchViewer.d.ts +0 -1
  72. package/dist/components/MatchViewer.d.ts.map +1 -1
  73. package/dist/components/MatchViewer.js +20 -10
  74. package/dist/components/MatchViewer.js.map +1 -1
  75. package/dist/components/Panel/MultiPanel.d.ts.map +1 -1
  76. package/dist/components/Panel/MultiPanel.js +14 -7
  77. package/dist/components/Panel/MultiPanel.js.map +1 -1
  78. package/dist/components/Panel/PanelContents.d.ts +2 -1
  79. package/dist/components/Panel/PanelContents.d.ts.map +1 -1
  80. package/dist/components/Panel/PanelContents.js +16 -11
  81. package/dist/components/Panel/PanelContents.js.map +1 -1
  82. package/dist/components/Panel/SinglePanel.d.ts.map +1 -1
  83. package/dist/components/Panel/SinglePanel.js +4 -3
  84. package/dist/components/Panel/SinglePanel.js.map +1 -1
  85. package/dist/components/Panel/ViewerWrapper.d.ts +1 -3
  86. package/dist/components/Panel/ViewerWrapper.d.ts.map +1 -1
  87. package/dist/components/Panel/ViewerWrapper.js +2 -3
  88. package/dist/components/Panel/ViewerWrapper.js.map +1 -1
  89. package/dist/components/Playground.d.ts.map +1 -1
  90. package/dist/components/Playground.js +353 -50
  91. package/dist/components/Playground.js.map +1 -1
  92. package/dist/components/PromptControls.d.ts.map +1 -1
  93. package/dist/components/PromptControls.js +39 -6
  94. package/dist/components/PromptControls.js.map +1 -1
  95. package/dist/components/ServerTrustMatchViewer.d.ts +11 -0
  96. package/dist/components/ServerTrustMatchViewer.d.ts.map +1 -0
  97. package/dist/components/ServerTrustMatchViewer.js +26 -0
  98. package/dist/components/ServerTrustMatchViewer.js.map +1 -0
  99. package/dist/components/Viewer.d.ts.map +1 -1
  100. package/dist/components/Viewer.js +54 -14
  101. package/dist/components/Viewer.js.map +1 -1
  102. package/dist/game/Chit.d.ts +6 -2
  103. package/dist/game/Chit.d.ts.map +1 -1
  104. package/dist/game/Chit.js +50 -6
  105. package/dist/game/Chit.js.map +1 -1
  106. package/dist/game/ClientTimeState.d.ts +1 -0
  107. package/dist/game/ClientTimeState.d.ts.map +1 -1
  108. package/dist/game/ClientTimeState.js +4 -1
  109. package/dist/game/ClientTimeState.js.map +1 -1
  110. package/dist/game/GalleryItemChitChildrenSource.d.ts +1 -0
  111. package/dist/game/GalleryItemChitChildrenSource.d.ts.map +1 -1
  112. package/dist/game/GalleryItemChitChildrenSource.js +1 -0
  113. package/dist/game/GalleryItemChitChildrenSource.js.map +1 -1
  114. package/dist/game/GalleryItemRawSource.d.ts +1 -0
  115. package/dist/game/GalleryItemRawSource.d.ts.map +1 -1
  116. package/dist/game/GalleryItemRawSource.js +1 -0
  117. package/dist/game/GalleryItemRawSource.js.map +1 -1
  118. package/dist/game/Game.d.ts +2 -1
  119. package/dist/game/Game.d.ts.map +1 -1
  120. package/dist/game/GameButton.d.ts +1 -0
  121. package/dist/game/GameButton.d.ts.map +1 -1
  122. package/dist/game/GameButton.js +2 -0
  123. package/dist/game/GameButton.js.map +1 -1
  124. package/dist/game/GameDeckChit.d.ts +6 -0
  125. package/dist/game/GameDeckChit.d.ts.map +1 -1
  126. package/dist/game/GameDeckChit.js +32 -5
  127. package/dist/game/GameDeckChit.js.map +1 -1
  128. package/dist/game/GameMetaData.d.ts +18 -0
  129. package/dist/game/GameMetaData.d.ts.map +1 -0
  130. package/dist/game/GameMetaData.js +2 -0
  131. package/dist/game/GameMetaData.js.map +1 -0
  132. package/dist/game/GameTheme.d.ts +11 -0
  133. package/dist/game/GameTheme.d.ts.map +1 -1
  134. package/dist/game/GameTheme.js +19 -4
  135. package/dist/game/GameTheme.js.map +1 -1
  136. package/dist/game/Match.d.ts +2 -1
  137. package/dist/game/Match.d.ts.map +1 -1
  138. package/dist/game/Match.js +4 -3
  139. package/dist/game/Match.js.map +1 -1
  140. package/dist/game/MatchStorage.d.ts +10 -0
  141. package/dist/game/MatchStorage.d.ts.map +1 -1
  142. package/dist/game/MatchStorage.js +29 -0
  143. package/dist/game/MatchStorage.js.map +1 -1
  144. package/dist/game/ModalState.d.ts +1 -0
  145. package/dist/game/ModalState.d.ts.map +1 -1
  146. package/dist/game/ModalState.js +1 -0
  147. package/dist/game/ModalState.js.map +1 -1
  148. package/dist/game/OrderedOutlet.d.ts.map +1 -1
  149. package/dist/game/OrderedOutlet.js +6 -6
  150. package/dist/game/OrderedOutlet.js.map +1 -1
  151. package/dist/game/Pick.d.ts +11 -1
  152. package/dist/game/Pick.d.ts.map +1 -1
  153. package/dist/game/Pick.js +83 -1
  154. package/dist/game/Pick.js.map +1 -1
  155. package/dist/game/PlayerChit.d.ts +2 -1
  156. package/dist/game/PlayerChit.d.ts.map +1 -1
  157. package/dist/game/PlayerChit.js +13 -1
  158. package/dist/game/PlayerChit.js.map +1 -1
  159. package/dist/game/PlayerInfo.d.ts +2 -1
  160. package/dist/game/PlayerInfo.d.ts.map +1 -1
  161. package/dist/game/PlayerInfo.js +20 -3
  162. package/dist/game/PlayerInfo.js.map +1 -1
  163. package/dist/game/Prompt.d.ts +1 -11
  164. package/dist/game/Prompt.d.ts.map +1 -1
  165. package/dist/game/Prompt.js +0 -32
  166. package/dist/game/Prompt.js.map +1 -1
  167. package/dist/game/RootChit.d.ts +4 -0
  168. package/dist/game/RootChit.d.ts.map +1 -1
  169. package/dist/game/RootChit.js +36 -1
  170. package/dist/game/RootChit.js.map +1 -1
  171. package/dist/game/Turn.d.ts +9 -8
  172. package/dist/game/Turn.d.ts.map +1 -1
  173. package/dist/game/Turn.js +34 -34
  174. package/dist/game/Turn.js.map +1 -1
  175. package/dist/game/TurnState.d.ts +3 -2
  176. package/dist/game/TurnState.d.ts.map +1 -1
  177. package/dist/game/TurnState.js +22 -2
  178. package/dist/game/TurnState.js.map +1 -1
  179. package/dist/game/badAiTransport/BadAIClientPrompts.d.ts +14 -0
  180. package/dist/game/badAiTransport/BadAIClientPrompts.d.ts.map +1 -0
  181. package/dist/game/badAiTransport/BadAIClientPrompts.js +50 -0
  182. package/dist/game/badAiTransport/BadAIClientPrompts.js.map +1 -0
  183. package/dist/game/clientTransport/ClientTime.js +1 -1
  184. package/dist/game/clientTransport/ClientTime.js.map +1 -1
  185. package/dist/game/serverTransport/ServerTime.d.ts.map +1 -1
  186. package/dist/game/serverTransport/ServerTime.js +1 -1
  187. package/dist/game/serverTransport/ServerTime.js.map +1 -1
  188. package/dist/hooks/useButtonGalleriesOptions.d.ts +4 -0
  189. package/dist/hooks/useButtonGalleriesOptions.d.ts.map +1 -0
  190. package/dist/hooks/useButtonGalleriesOptions.js +7 -0
  191. package/dist/hooks/useButtonGalleriesOptions.js.map +1 -0
  192. package/dist/hooks/useEventChannelState.js +1 -1
  193. package/dist/hooks/useEventChannelState.js.map +1 -1
  194. package/dist/hooks/useLoadingStates.d.ts +17 -0
  195. package/dist/hooks/useLoadingStates.d.ts.map +1 -0
  196. package/dist/hooks/useLoadingStates.js +44 -0
  197. package/dist/hooks/useLoadingStates.js.map +1 -0
  198. package/dist/hooks/useModalState.d.ts +2 -1
  199. package/dist/hooks/useModalState.d.ts.map +1 -1
  200. package/dist/hooks/useModalState.js +2 -2
  201. package/dist/hooks/useModalState.js.map +1 -1
  202. package/dist/hooks/usePanelPositioning.d.ts +0 -1
  203. package/dist/hooks/usePanelPositioning.d.ts.map +1 -1
  204. package/dist/hooks/usePanelPositioning.js.map +1 -1
  205. package/dist/index.d.ts +7 -5
  206. package/dist/index.d.ts.map +1 -1
  207. package/dist/index.js +17 -1
  208. package/dist/index.js.map +1 -1
  209. package/dist/rendering/CameraWrapperPerspective.d.ts.map +1 -1
  210. package/dist/rendering/CameraWrapperPerspective.js +1 -1
  211. package/dist/rendering/CameraWrapperPerspective.js.map +1 -1
  212. package/dist/rendering/ChitGalleryItemInstance.d.ts +2 -0
  213. package/dist/rendering/ChitGalleryItemInstance.d.ts.map +1 -1
  214. package/dist/rendering/ChitGalleryItemInstance.js +2 -0
  215. package/dist/rendering/ChitGalleryItemInstance.js.map +1 -1
  216. package/dist/rendering/ChitRenderInstance.d.ts +13 -2
  217. package/dist/rendering/ChitRenderInstance.d.ts.map +1 -1
  218. package/dist/rendering/ChitRenderInstance.js +95 -47
  219. package/dist/rendering/ChitRenderInstance.js.map +1 -1
  220. package/dist/rendering/ChitRenderSpec.d.ts +3 -0
  221. package/dist/rendering/ChitRenderSpec.d.ts.map +1 -1
  222. package/dist/rendering/ChitRenderSpec.js +3 -0
  223. package/dist/rendering/ChitRenderSpec.js.map +1 -1
  224. package/dist/rendering/RootChitRenderInstance.d.ts +5 -2
  225. package/dist/rendering/RootChitRenderInstance.d.ts.map +1 -1
  226. package/dist/rendering/RootChitRenderInstance.js +76 -13
  227. package/dist/rendering/RootChitRenderInstance.js.map +1 -1
  228. package/dist/rendering/SplayCounter.d.ts.map +1 -1
  229. package/dist/rendering/SplayCounter.js +1 -1
  230. package/dist/rendering/SplayCounter.js.map +1 -1
  231. package/dist/rendering/TextureReferenceCounter.d.ts +1 -1
  232. package/dist/rendering/TextureReferenceCounter.d.ts.map +1 -1
  233. package/dist/rendering/TextureReferenceCounter.js +10 -10
  234. package/dist/rendering/TextureReferenceCounter.js.map +1 -1
  235. package/dist/rendering/outline/passes/DepthOcclusionPass.js +1 -1
  236. package/dist/rendering/outline/passes/DepthOcclusionPass.js.map +1 -1
  237. package/dist/utilities/Annotations.d.ts +59 -0
  238. package/dist/utilities/Annotations.d.ts.map +1 -1
  239. package/dist/utilities/Annotations.js +63 -0
  240. package/dist/utilities/Annotations.js.map +1 -1
  241. package/dist/utilities/CanvasStack/CanvasOperations.d.ts +10 -1
  242. package/dist/utilities/CanvasStack/CanvasOperations.d.ts.map +1 -1
  243. package/dist/utilities/CanvasStack/CanvasOperations.js +8 -0
  244. package/dist/utilities/CanvasStack/CanvasOperations.js.map +1 -1
  245. package/dist/utilities/CanvasStack/ReactCanvas.d.ts +4 -2
  246. package/dist/utilities/CanvasStack/ReactCanvas.d.ts.map +1 -1
  247. package/dist/utilities/CanvasStack/ReactCanvas.js +5 -2
  248. package/dist/utilities/CanvasStack/ReactCanvas.js.map +1 -1
  249. package/dist/utilities/CanvasStack/RichTextRenderer.d.ts.map +1 -1
  250. package/dist/utilities/CanvasStack/RichTextRenderer.js +12 -4
  251. package/dist/utilities/CanvasStack/RichTextRenderer.js.map +1 -1
  252. package/dist/utilities/EventChannel.d.ts.map +1 -1
  253. package/dist/utilities/EventChannel.js +2 -3
  254. package/dist/utilities/EventChannel.js.map +1 -1
  255. package/dist/utilities/GlbLoader.d.ts +15 -0
  256. package/dist/utilities/GlbLoader.d.ts.map +1 -0
  257. package/dist/utilities/GlbLoader.js +212 -0
  258. package/dist/utilities/GlbLoader.js.map +1 -0
  259. package/dist/utilities/LayoutHelper.js +23 -2
  260. package/dist/utilities/LayoutHelper.js.map +1 -1
  261. package/dist/utilities/ObjectWithProps.d.ts.map +1 -1
  262. package/dist/utilities/ObjectWithProps.js +32 -3
  263. package/dist/utilities/ObjectWithProps.js.map +1 -1
  264. package/package.json +6 -5
  265. package/src/library/components/BottomBarButton.tsx +3 -0
  266. package/src/library/components/ClientTrustMatchViewer.tsx +23 -8
  267. package/src/library/components/ContextGalleryDisplay.tsx +2 -2
  268. package/src/library/components/DemoWrapper.tsx +113 -0
  269. package/src/library/components/{GalleryDisplay.tsx → FullScreenGalleryDisplay.tsx} +28 -2
  270. package/src/library/components/Gallery/AnimationController.ts +110 -0
  271. package/src/library/components/Gallery/BuiltItem.ts +385 -0
  272. package/src/library/components/Gallery/CameraManager.ts +54 -0
  273. package/src/library/components/Gallery/GalleryController.ts +193 -0
  274. package/src/library/components/Gallery/GalleryViewer.tsx +211 -0
  275. package/src/library/components/Gallery/LayoutManager.ts +166 -0
  276. package/src/library/components/Gallery/constants.ts +12 -0
  277. package/src/library/components/Gallery/index.ts +2 -0
  278. package/src/library/components/Gallery/types.ts +55 -0
  279. package/src/library/components/GalleryPlayground.tsx +1 -1
  280. package/src/library/components/GalleryViewer.tsx +4 -773
  281. package/src/library/components/GameDesigner.tsx +21 -4
  282. package/src/library/components/InlineGalleryDisplay.tsx +101 -0
  283. package/src/library/components/LiveButton.tsx +2 -1
  284. package/src/library/components/MatchViewer.tsx +32 -14
  285. package/src/library/components/Panel/MultiPanel.tsx +20 -8
  286. package/src/library/components/Panel/PanelContents.tsx +17 -12
  287. package/src/library/components/Panel/SinglePanel.tsx +5 -4
  288. package/src/library/components/Panel/ViewerWrapper.tsx +0 -5
  289. package/src/library/components/Playground.tsx +692 -119
  290. package/src/library/components/PromptControls.tsx +61 -8
  291. package/src/library/components/ServerTrustMatchViewer.tsx +53 -0
  292. package/src/library/components/Viewer.tsx +60 -20
  293. package/src/library/game/Chit.ts +53 -6
  294. package/src/library/game/ClientTimeState.ts +5 -1
  295. package/src/library/game/GalleryItemChitChildrenSource.ts +2 -0
  296. package/src/library/game/GalleryItemRawSource.ts +2 -0
  297. package/src/library/game/Game.ts +3 -1
  298. package/src/library/game/GameButton.ts +3 -0
  299. package/src/library/game/GameDeckChit.ts +36 -5
  300. package/src/library/game/GameMetaData.ts +19 -0
  301. package/src/library/game/GameTheme.ts +23 -5
  302. package/src/library/game/Match.ts +4 -3
  303. package/src/library/game/MatchStorage.ts +37 -0
  304. package/src/library/game/ModalState.ts +1 -0
  305. package/src/library/game/OrderedOutlet.ts +6 -6
  306. package/src/library/game/Pick.ts +98 -2
  307. package/src/library/game/PlayerChit.ts +13 -1
  308. package/src/library/game/PlayerInfo.ts +22 -3
  309. package/src/library/game/Prompt.ts +1 -36
  310. package/src/library/game/RootChit.ts +41 -1
  311. package/src/library/game/Turn.ts +37 -40
  312. package/src/library/game/TurnState.ts +22 -3
  313. package/src/library/game/badAiTransport/BadAIClientPrompts.ts +60 -0
  314. package/src/library/game/clientTransport/ClientTime.ts +1 -1
  315. package/src/library/game/serverTransport/ServerTime.ts +2 -2
  316. package/src/library/hooks/useButtonGalleriesOptions.tsx +9 -0
  317. package/src/library/hooks/useEventChannelState.ts +1 -1
  318. package/src/library/hooks/useLoadingStates.tsx +55 -0
  319. package/src/library/hooks/useModalState.tsx +2 -2
  320. package/src/library/hooks/usePanelPositioning.tsx +0 -1
  321. package/src/library/index.ts +21 -1
  322. package/src/library/rendering/CameraWrapperPerspective.ts +10 -12
  323. package/src/library/rendering/ChitGalleryItemInstance.ts +2 -0
  324. package/src/library/rendering/ChitRenderInstance.ts +119 -61
  325. package/src/library/rendering/ChitRenderSpec.ts +4 -0
  326. package/src/library/rendering/RootChitRenderInstance.ts +87 -13
  327. package/src/library/rendering/SplayCounter.tsx +2 -1
  328. package/src/library/rendering/TextureReferenceCounter.ts +9 -9
  329. package/src/library/rendering/outline/passes/DepthOcclusionPass.ts +1 -1
  330. package/src/library/utilities/Annotations.ts +99 -0
  331. package/src/library/utilities/CanvasStack/CanvasOperations.tsx +19 -1
  332. package/src/library/utilities/CanvasStack/ReactCanvas.tsx +10 -3
  333. package/src/library/utilities/CanvasStack/RichTextRenderer.ts +14 -4
  334. package/src/library/utilities/EventChannel.ts +2 -4
  335. package/src/library/utilities/GlbLoader.ts +292 -0
  336. package/src/library/utilities/LayoutHelper.ts +28 -2
  337. package/src/library/utilities/ObjectWithProps.ts +27 -3
  338. package/dist/components/GalleryDisplay.d.ts +0 -2
  339. package/dist/components/GalleryDisplay.d.ts.map +0 -1
  340. package/dist/components/GalleryDisplay.js +0 -42
  341. package/dist/components/GalleryDisplay.js.map +0 -1
  342. package/dist/utilities/OutlineCanvas.d.ts +0 -12
  343. package/dist/utilities/OutlineCanvas.d.ts.map +0 -1
  344. package/dist/utilities/OutlineCanvas.js +0 -31
  345. package/dist/utilities/OutlineCanvas.js.map +0 -1
  346. package/dist/utilities/OutlineGeometry.d.ts +0 -3
  347. package/dist/utilities/OutlineGeometry.d.ts.map +0 -1
  348. package/dist/utilities/OutlineGeometry.js +0 -57
  349. package/dist/utilities/OutlineGeometry.js.map +0 -1
  350. package/src/library/utilities/OutlineCanvas.tsx +0 -45
  351. package/src/library/utilities/OutlineGeometry.ts +0 -69
@@ -1,773 +1,4 @@
1
- import {
2
- AmbientLight,
3
- Box3,
4
- DirectionalLight,
5
- Fog,
6
- Group,
7
- Mesh,
8
- Object3D,
9
- PerspectiveCamera,
10
- PlaneGeometry,
11
- Raycaster,
12
- Scene,
13
- Vector3,
14
- } from "three";
15
- import { Box } from "@mui/material";
16
- import React, { useEffect, useRef, useState } from "react";
17
- import Hammer from "@egjs/hammerjs";
18
- import { useWebGlRenderer } from "../hooks/useWebGlRenderer";
19
- import { Easing, Tween } from "@tweenjs/tween.js";
20
- import { addWheelListener, removeWheelListener } from "wheel";
21
- import { CanvasStack } from "../utilities/CanvasStack/CanvasStack";
22
- import {
23
- ColorCanvasOperation,
24
- IconMap,
25
- LayeredCanvasOperation,
26
- MarkdownCanvasOperation,
27
- PadCanvasOperation,
28
- } from "../utilities/CanvasStack/CanvasOperations";
29
- import { useGameTheme } from "../hooks/useGameTheme";
30
- import { GameTheme } from "../game/GameTheme";
31
- import { RichTextRenderOptionsParameters } from "../utilities/CanvasStack/RichTextRenderer";
32
- import { SceneWrapper } from "../rendering/outline";
33
- import { requestSharedAnimationFrame } from "../utilities/RequestSharedAnimationFrame";
34
- import { TextureReferenaceCounter, TextureReferenceCounterRootGroup } from "../rendering/TextureReferenceCounter";
35
-
36
- let ID_COUNTER = 1;
37
-
38
- const SCALE_FACTOR = 20;
39
-
40
- type UpdateCallback = () => void;
41
-
42
- export interface GalleryItem {
43
- id: string;
44
- createMesh(sceneWrapper: SceneWrapper): Object3D;
45
- onClick?: () => void;
46
-
47
- maximumWidth?: number;
48
- maximumHeight?: number;
49
-
50
- preferredWidth?: number;
51
- preferredHeight?: number;
52
-
53
- summary?: string;
54
- summaryIconMap?: IconMap;
55
- summaryRenderingOptions?: RichTextRenderOptionsParameters;
56
-
57
- /**
58
- * This takes a callback that gets updated any time the gallery item needs to be refreshed (new texture or mesh or whatnot).
59
- * It returns a callback that can be invoked to unsubscribe this callback
60
- */
61
- registerUpdateHandler(cb: UpdateCallback): UpdateCallback;
62
- }
63
-
64
- export interface GalleryItemSource {
65
- backingObject?: any;
66
- get items(): GalleryItem[];
67
-
68
- /**
69
- * This takes a callback that gets updated any time the gallery item needs to be refreshed (new texture or mesh or whatnot).
70
- * It returns a callback that can be invoked to unsubscribe this callback
71
- */
72
- registerUpdateHandler(cb: UpdateCallback): UpdateCallback;
73
- close(): void;
74
- }
75
-
76
- type BuiltItem = {
77
- index: number;
78
- enteredAmount: number;
79
- targetIndex: number;
80
- item: GalleryItem;
81
- group: Object3D;
82
- mesh: Object3D;
83
- meshToShowOrHideIfCentered?: Object3D;
84
- center: Vector3;
85
- height: number;
86
- depth: number;
87
- summaryHeight: number;
88
- tween?: Tween<{ x: number }>;
89
- enteredTween?: Tween<{ x: number }>;
90
- unsubscribe: UpdateCallback;
91
- };
92
-
93
- class GalleryController implements TextureReferenceCounterRootGroup {
94
- constructor(
95
- public sceneWrapper: SceneWrapper,
96
- private theme: GameTheme,
97
- public offsetAngle: number,
98
- fov: number,
99
- ) {
100
- this.camera = new PerspectiveCamera(fov, 1, 0.1, 10000 / SCALE_FACTOR);
101
- this.camera.position.z = 500 / SCALE_FACTOR;
102
-
103
- this.light = new DirectionalLight(0xffffff, 1);
104
- this.light.position.copy(this.camera.position);
105
- sceneWrapper.scene.add(this.light);
106
- const ambient = new AmbientLight(0xffffff, 1);
107
- sceneWrapper.scene.add(ambient);
108
- }
109
-
110
- getRootGroup(): Object3D {
111
- return this.sceneWrapper.scene;
112
- }
113
- markHasChange(): void {
114
- this.changed = true;
115
- }
116
-
117
- public camera: PerspectiveCamera;
118
- private w = 100 / SCALE_FACTOR;
119
- private h = 100 / SCALE_FACTOR;
120
- private itemWidth = 100 / SCALE_FACTOR;
121
- private itemHeight = 100 / SCALE_FACTOR;
122
-
123
- public tweenDuration = 250;
124
- public showSummary = true;
125
- private changed = false;
126
- private itemSpacing = 100 / SCALE_FACTOR;
127
- private itemsPerPage = 1;
128
- private frontStageWidth = 1;
129
- private offsetX = 0;
130
- private light: DirectionalLight;
131
-
132
- private effectiveItemHeight = 0;
133
- private baseCameraZ = 500 / SCALE_FACTOR;
134
-
135
- private items: BuiltItem[] = [];
136
- private leavingItems: BuiltItem[] = [];
137
- private itemLookup: { [key: string]: BuiltItem } = {};
138
-
139
- private updateEffectiveItemHeightAndCamera() {
140
- // Calculate the tallest actual mesh height (capped at itemHeight)
141
- const tallestMeshHeight = Math.max(...this.items.map((item) => item.height), 0);
142
- const newEffectiveItemHeight = Math.min(tallestMeshHeight, this.itemHeight);
143
-
144
- // Check if effective height changed - if so, need to reposition all summaries
145
- const heightChanged = Math.abs(newEffectiveItemHeight - this.effectiveItemHeight) > 0.001;
146
- this.effectiveItemHeight = newEffectiveItemHeight;
147
-
148
- if (heightChanged) {
149
- this.items.forEach((item) => {
150
- if (item.meshToShowOrHideIfCentered) {
151
- // Reposition summary based on new effective height
152
- const summaryHeight = item.summaryHeight - this.theme.spacing / SCALE_FACTOR;
153
- item.meshToShowOrHideIfCentered.position.y =
154
- -this.effectiveItemHeight * 0.5 - summaryHeight / 2 - this.theme.spacing / SCALE_FACTOR;
155
- }
156
- });
157
- }
158
-
159
- // Calculate tallest summary
160
- const tallestSummaryHeight = Math.max(...this.items.map((item) => item.summaryHeight), 0);
161
-
162
- // Vertical offset is based on effective item height + tallest summary
163
- const verticalOffset = -tallestSummaryHeight / 2;
164
-
165
- // Update camera position using the base Z distance
166
- this.camera.position.z = Math.cos(this.offsetAngle) * this.baseCameraZ;
167
- this.camera.position.y = Math.sin(this.offsetAngle) * this.baseCameraZ + verticalOffset;
168
- this.camera.lookAt(new Vector3(this.camera.position.x, verticalOffset, 0));
169
-
170
- // Update light to match camera
171
- this.light.position.copy(this.camera.position);
172
- this.light.lookAt(0, verticalOffset, 0);
173
-
174
- this.changed = true;
175
- }
176
-
177
- public setSize(w: number, h: number, itemWidth: number, itemHeight: number, itemSpacing: number) {
178
- this.changed = true;
179
- this.w = w / SCALE_FACTOR;
180
- this.h = h / SCALE_FACTOR;
181
- this.itemHeight = Math.min(itemHeight, h - itemSpacing) / SCALE_FACTOR;
182
- this.itemWidth = Math.min(itemWidth, w - itemSpacing) / SCALE_FACTOR;
183
- this.itemSpacing = itemSpacing / SCALE_FACTOR;
184
- this.itemsPerPage = Math.floor((w - itemSpacing * 2) / (this.itemWidth * SCALE_FACTOR + itemSpacing));
185
- this.frontStageWidth =
186
- (this.itemsPerPage * (this.itemWidth * SCALE_FACTOR + itemSpacing)) / SCALE_FACTOR - this.itemSpacing;
187
-
188
- this.camera.aspect = w / h;
189
- this.camera.updateProjectionMatrix();
190
-
191
- // Calculate base camera Z distance from the field of view
192
- const aspect = this.camera.aspect;
193
- const vFov = (this.camera.fov * Math.PI) / 180;
194
- const hFov = 2 * Math.atan(aspect * Math.tan(vFov / 2));
195
- this.baseCameraZ = w / SCALE_FACTOR / (2 * Math.tan(hFov / 2));
196
- this.camera.position.x = 0;
197
-
198
- // Set up fog and camera clipping planes
199
- this.sceneWrapper.scene.fog = new Fog(0x000000, this.baseCameraZ, this.baseCameraZ + (w / SCALE_FACTOR) * 2);
200
- this.camera.near = this.baseCameraZ * 0.5;
201
- this.camera.far = this.baseCameraZ + (w / SCALE_FACTOR) * 3;
202
- this.camera.updateProjectionMatrix();
203
-
204
- // reset the world
205
- this.setItems(this.items.map((item) => item.item));
206
- this.pan(0, true);
207
- }
208
-
209
- getItemAtPosition(x: any, y: any) {
210
- const paddingX = (this.w - this.frontStageWidth) / 2;
211
- const index = (-this.offsetX + x / SCALE_FACTOR - paddingX) / (this.itemWidth + this.itemSpacing);
212
-
213
- const item = this.items.find((item) => index > item.index && Math.abs(index - item.index) < 1);
214
- if (!item) {
215
- return null;
216
- }
217
-
218
- if (index - item.index > 1 - this.itemSpacing / (this.itemWidth + this.itemSpacing)) {
219
- return null;
220
- }
221
-
222
- const ndc = new Vector3((x / SCALE_FACTOR / this.w) * 2 - 1, -(y / SCALE_FACTOR / this.h) * 2 + 1, 0.5);
223
- ndc.unproject(this.camera);
224
- const raycaster = new Raycaster(this.camera.position, ndc.sub(this.camera.position).normalize());
225
-
226
- // Create a combined bounding box from mesh to summary (if present)
227
- const combinedBox = new Box3().setFromObject(item.mesh);
228
- if (item.meshToShowOrHideIfCentered) {
229
- const summaryBox = new Box3().setFromObject(item.meshToShowOrHideIfCentered);
230
- combinedBox.union(summaryBox);
231
- }
232
-
233
- const hit = raycaster.ray.intersectBox(combinedBox, new Vector3());
234
- if (!hit) {
235
- return null;
236
- }
237
-
238
- return item.item;
239
- }
240
-
241
- render() {
242
- let changed = this.changed;
243
- if (this.tween) {
244
- this.tween.update();
245
- changed = true;
246
- }
247
- this.items.forEach((item) => {
248
- if (item.tween) {
249
- item.tween.update();
250
- changed = true;
251
- }
252
- if (item.enteredTween) {
253
- item.enteredTween.update();
254
- changed = true;
255
- }
256
- });
257
- this.leavingItems.forEach((item) => {
258
- if (item.enteredTween) {
259
- item.enteredTween.update();
260
- }
261
- changed = true;
262
- });
263
- this.changed = false;
264
- return changed;
265
- }
266
-
267
- isAnimating() {
268
- return this.tween !== undefined;
269
- }
270
- stop() {
271
- this.tween?.stop();
272
- this.tween = undefined;
273
- }
274
-
275
- private tween: Tween<{ x: number }> | undefined;
276
- pan(deltaX: number, animate = false) {
277
- const max = 0;
278
- const min =
279
- -(this.items.length - Math.min(this.items.length, this.itemsPerPage)) * (this.itemWidth + this.itemSpacing);
280
-
281
- this.changed = true;
282
- if (this.tween) {
283
- this.tween.stop();
284
- this.tween = undefined;
285
- }
286
-
287
- if (!animate) {
288
- this.offsetX += deltaX / SCALE_FACTOR;
289
-
290
- if (this.offsetX > max + this.w / 2) {
291
- this.offsetX = max + this.w / 2;
292
- }
293
- if (this.offsetX < min - this.w / 2) {
294
- this.offsetX = min - this.w / 2;
295
- }
296
-
297
- this.items.forEach((item) => this.positionItem(item));
298
- } else {
299
- // lock the offset to the nearest item
300
- let target = this.offsetX + deltaX / SCALE_FACTOR;
301
- const itemIndex = Math.round(target / (this.itemWidth + this.itemSpacing));
302
- target = itemIndex * (this.itemWidth + this.itemSpacing);
303
-
304
- if (target > max) {
305
- target = max;
306
- }
307
- if (target < min) {
308
- target = min;
309
- }
310
-
311
- const duration = 0.0001 + Math.min(750, Math.abs(target - this.offsetX));
312
-
313
- this.tween = new Tween({ x: this.offsetX })
314
- .onUpdate(({ x }) => {
315
- this.offsetX = x;
316
- this.items.forEach((item) => this.positionItem(item));
317
- })
318
- .easing(Easing.Quadratic.Out)
319
- .to({ x: target }, duration)
320
- .onComplete(() => {
321
- this.tween = undefined;
322
- })
323
- .start();
324
- }
325
- }
326
-
327
- positionItem(item: BuiltItem) {
328
- const index = item.index;
329
- const initialOffset = -(this.frontStageWidth / 2 - this.itemWidth / 2);
330
- const group = item.group;
331
- group.position.x = initialOffset + index * (this.itemWidth + this.itemSpacing) + this.offsetX;
332
-
333
- group.position.y = (1 - item.enteredAmount) * -this.h; // 5 is height of display?
334
-
335
- const zFactor = 3;
336
- const largestX = initialOffset + (this.itemsPerPage - 1) * (this.itemWidth + this.itemSpacing);
337
- if (group.position.x > largestX) {
338
- const overshot = group.position.x - largestX;
339
- group.position.x = largestX + Math.pow(overshot, 0.94);
340
- group.position.z = -overshot * zFactor;
341
- group.rotation.x = -overshot / (3000 / SCALE_FACTOR) - this.offsetAngle;
342
- if (item.meshToShowOrHideIfCentered) {
343
- item.meshToShowOrHideIfCentered.position.x = overshot * 3;
344
- item.meshToShowOrHideIfCentered.position.z = -overshot * 3;
345
- }
346
- } else if (group.position.x < initialOffset) {
347
- const overshot = Math.abs(initialOffset - group.position.x);
348
- group.position.x = initialOffset - Math.pow(overshot, 0.94);
349
- group.position.z = -overshot * zFactor;
350
- group.rotation.x = -overshot / (3000 / SCALE_FACTOR) - this.offsetAngle;
351
- if (item.meshToShowOrHideIfCentered) {
352
- item.meshToShowOrHideIfCentered.position.x = -overshot * 3;
353
- item.meshToShowOrHideIfCentered.position.z = -overshot * 3;
354
- }
355
- } else {
356
- if (item.meshToShowOrHideIfCentered) {
357
- item.meshToShowOrHideIfCentered.position.x = 0;
358
- item.meshToShowOrHideIfCentered.position.z = 0;
359
- }
360
- group.position.z = 0;
361
- group.rotation.x = -this.offsetAngle;
362
- }
363
-
364
- // group.rotation.x -= Math.min(1, item.depth / this.w);
365
- group.position.add(item.center);
366
- }
367
-
368
- scaleItem(item: BuiltItem, maximumWidth?: number, maximumHeight?: number) {
369
- if (item.mesh) {
370
- item.mesh.removeFromParent();
371
- }
372
-
373
- item.mesh = item.item.createMesh(this.sceneWrapper);
374
- const box3 = new Box3();
375
- box3.expandByObject(item.mesh);
376
- if (!box3.isEmpty()) {
377
- const size = box3.getSize(new Vector3());
378
- const center = box3.getCenter(new Vector3());
379
- const xScale = Math.min(this.itemWidth, (maximumWidth ?? Number.MAX_SAFE_INTEGER) / SCALE_FACTOR) / size.x;
380
- const yScale = Math.min(this.itemHeight, (maximumHeight ?? Number.MAX_SAFE_INTEGER) / SCALE_FACTOR) / size.y;
381
- const scale = Math.min(xScale, yScale);
382
- item.mesh.scale.set(scale, scale, scale);
383
- item.mesh.updateMatrix();
384
- item.center = center.multiplyScalar(scale).negate();
385
- item.center.z = 0; // i want to "floor" everything... but that is hard?
386
- item.height = size.y * scale;
387
- item.depth = size.z * scale;
388
- }
389
- item.group.add(item.mesh);
390
- }
391
-
392
- updateHelpText(item: BuiltItem) {
393
- const summary = item.item.summary;
394
- if (!summary || !this.showSummary) {
395
- item.summaryHeight = 0;
396
- return;
397
- }
398
-
399
- const height = (this.h - this.itemHeight) / 2 - this.theme.spacing * 2;
400
-
401
- const specs: RichTextRenderOptionsParameters = {
402
- align: "center",
403
- color: this.theme.dialogForegroundColor,
404
- ...(item.item.summaryRenderingOptions ?? {}),
405
- };
406
- if (!specs.fontSize) {
407
- specs.fontSize = this.theme.dialogFontSize;
408
- }
409
- specs.fontSize *= window.devicePixelRatio;
410
-
411
- const pad = this.theme.spacing * window.devicePixelRatio;
412
- const markdown = new MarkdownCanvasOperation(summary, item.item.summaryIconMap ?? {}, specs);
413
- const ops = new LayeredCanvasOperation([
414
- new ColorCanvasOperation(this.theme.gallerySummaryBackgroundColor, this.theme.gallerySummaryBackgroundOpacity),
415
- new PadCanvasOperation({ top: pad, bottom: pad, left: pad, right: pad }, markdown),
416
- ]);
417
-
418
- const stack1 = new CanvasStack(
419
- this.itemWidth * SCALE_FACTOR * window.devicePixelRatio,
420
- height * SCALE_FACTOR * window.devicePixelRatio,
421
- ops,
422
- );
423
- stack1.render();
424
- const stack2 = new CanvasStack(
425
- this.itemWidth * SCALE_FACTOR * window.devicePixelRatio,
426
- markdown.height + this.theme.spacing * 2 * window.devicePixelRatio,
427
- ops,
428
- );
429
- stack2.render();
430
-
431
- const material = stack2.material;
432
- material.transparent = true;
433
- material.depthWrite = true;
434
-
435
- const finalHeight = stack2.height / window.devicePixelRatio / SCALE_FACTOR;
436
- item.summaryHeight = finalHeight + this.theme.spacing / SCALE_FACTOR;
437
- const face = new PlaneGeometry(this.itemWidth, finalHeight);
438
- const m = new Mesh(face, material);
439
- // m.renderOrder = 2;
440
- // Position will be set by updateEffectiveItemHeightAndCamera based on effectiveItemHeight
441
- m.position.set(0, -this.effectiveItemHeight * 0.5 - finalHeight / 2 - this.theme.spacing / SCALE_FACTOR, 0);
442
-
443
- item.meshToShowOrHideIfCentered = m;
444
- item.group.add(m);
445
- }
446
-
447
- private _rawItems: GalleryItem[] = [];
448
- public setItems(items: GalleryItem[]) {
449
- this._rawItems = items;
450
- this.changed = true;
451
- const itemIndexOffset = items.length < this.itemsPerPage ? (this.itemsPerPage - items.length) / 2 : 0;
452
-
453
- const seenIds = new Set(Object.keys(this.itemLookup));
454
- items.forEach((item, i) => {
455
- seenIds.delete(item.id);
456
- if (!this.itemLookup[item.id]) {
457
- const builtItem: BuiltItem = (this.itemLookup[item.id] = {
458
- item,
459
- enteredAmount: 0,
460
- mesh: item.createMesh(this.sceneWrapper),
461
- group: new Group(),
462
- index: i + itemIndexOffset,
463
- center: new Vector3(),
464
- height: 0,
465
- depth: 0,
466
- summaryHeight: 0,
467
- targetIndex: i + itemIndexOffset,
468
- unsubscribe: item.registerUpdateHandler(() => {
469
- builtItem.group.removeFromParent();
470
- builtItem.mesh.removeFromParent();
471
- this.changed = true;
472
-
473
- builtItem.group = new Group();
474
-
475
- this.sceneWrapper.scene.add(builtItem.group);
476
-
477
- this.scaleItem(builtItem, item.maximumWidth, item.maximumHeight);
478
- this.positionItem(builtItem);
479
- this.updateHelpText(builtItem);
480
- this.updateEffectiveItemHeightAndCamera();
481
-
482
- TextureReferenaceCounter.update();
483
- }),
484
- });
485
- this.scaleItem(builtItem, item.maximumWidth, item.maximumHeight);
486
-
487
- // Also add your mesh to the scene:
488
- builtItem.mesh.removeFromParent();
489
- builtItem.group.removeFromParent();
490
- builtItem.group.add(builtItem.mesh);
491
- this.sceneWrapper.scene.add(builtItem.group);
492
- this.positionItem(builtItem);
493
- this.updateHelpText(builtItem);
494
-
495
- builtItem.enteredTween = new Tween({ x: 0 })
496
- .to({ x: 1 }, this.tweenDuration)
497
- .easing(Easing.Quadratic.Out)
498
- .onUpdate((obj) => {
499
- builtItem.enteredAmount = obj.x;
500
- this.positionItem(builtItem);
501
- })
502
- .onComplete(() => {
503
- this.positionItem(builtItem);
504
- builtItem.enteredTween = undefined;
505
- })
506
- .start();
507
- } else {
508
- const it = this.itemLookup[item.id];
509
- this.scaleItem(it, it.item.maximumWidth, it.item.maximumHeight);
510
- this.positionItem(it);
511
- }
512
- });
513
-
514
- [...seenIds].forEach((id) => {
515
- const item = this.itemLookup[id];
516
- item.unsubscribe();
517
- delete this.itemLookup[id];
518
- this.leavingItems.push(item);
519
-
520
- if (item.enteredTween) {
521
- item.enteredTween.stop();
522
- item.enteredTween = undefined;
523
- }
524
-
525
- item.enteredTween = new Tween({ x: item.enteredAmount })
526
- .to({ x: 0 }, this.tweenDuration)
527
- .easing(Easing.Quadratic.In)
528
- .onUpdate((obj) => {
529
- item.enteredAmount = obj.x;
530
- this.positionItem(item);
531
- })
532
- .onComplete(() => {
533
- item.enteredTween = undefined;
534
- item.mesh.parent?.remove(item.mesh);
535
- this.leavingItems = this.leavingItems.filter((i) => i !== item);
536
- })
537
- .start();
538
- });
539
-
540
- const hasChangedLength = this.items.length !== items.length;
541
- this.items = items.map((item) => this.itemLookup[item.id]);
542
-
543
- this.items.forEach((item, index) => {
544
- if (item.tween) {
545
- item.tween.stop();
546
- item.tween = undefined;
547
- }
548
- if (item.index !== index + itemIndexOffset) {
549
- item.targetIndex = index + itemIndexOffset;
550
-
551
- item.tween = new Tween({ x: item.index })
552
- .to({ x: item.targetIndex }, this.tweenDuration)
553
- .easing(Easing.Quadratic.InOut)
554
- .onUpdate((obj) => {
555
- item.index = obj.x;
556
- this.positionItem(item);
557
- })
558
- .onComplete(() => {
559
- item.tween = undefined;
560
- })
561
- .start();
562
- }
563
- });
564
-
565
- if (hasChangedLength && !this.tween) {
566
- this.pan(0, true);
567
- }
568
-
569
- this.updateEffectiveItemHeightAndCamera();
570
- this.sceneWrapper.markDirty();
571
- TextureReferenaceCounter.update();
572
- }
573
- }
574
-
575
- export function GalleryViewer({
576
- items,
577
- paused = false,
578
- galleryItemWidth = 200,
579
- fov = 15,
580
- angle = Math.PI * 0.1,
581
- onClose,
582
- itemSpacing = 50,
583
- tweenDuration = 250,
584
- w = 0,
585
- h = 0,
586
- galleryItemHeight = h * 0.7,
587
- showSummary = true,
588
- }: {
589
- items: GalleryItem[];
590
- w: number;
591
- h: number;
592
- fov?: number;
593
- angle?: number;
594
- itemSpacing: number;
595
- paused?: boolean;
596
- tweenDuration?: number;
597
- galleryItemWidth?: number;
598
- galleryItemHeight?: number;
599
- onClose?: () => void;
600
- showSummary?: boolean;
601
- }) {
602
- const calcedItemWidth = Math.min(...items.map((item) => item.preferredWidth ?? galleryItemWidth));
603
- const calcedItemHeight = Math.min(...items.map((item) => item.preferredHeight ?? galleryItemHeight));
604
-
605
- const [id] = useState(`GalleryViewer${ID_COUNTER++}`);
606
- const refContainer = useRef<HTMLCanvasElement>(null);
607
- const rendererWrapper = useWebGlRenderer();
608
- const theme = useGameTheme();
609
- const [galleryController] = useState(new GalleryController(new SceneWrapper(new Scene()), theme, angle, fov));
610
-
611
- galleryController.tweenDuration = tweenDuration;
612
- galleryController.showSummary = showSummary;
613
-
614
- useEffect(() => {
615
- if (!w || !h) {
616
- return;
617
- }
618
- if (!Number.isFinite(calcedItemHeight) || !Number.isFinite(calcedItemWidth)) {
619
- return;
620
- }
621
-
622
- galleryController.setSize(w, h, calcedItemWidth, calcedItemHeight, itemSpacing);
623
- }, [calcedItemWidth, itemSpacing, calcedItemHeight, w, h, galleryController]);
624
-
625
- useEffect(() => {
626
- galleryController.setItems(items);
627
- }, [items, galleryController]);
628
-
629
- useEffect(() => {
630
- const canvas = refContainer.current;
631
- if (!canvas || !rendererWrapper || paused) return;
632
- const ctx = canvas.getContext("2d");
633
- let cancelled = false;
634
-
635
- // FPS tracking variables
636
- let frameCount = 0;
637
- let fpsStartTime = performance.now();
638
- let isAnimating = false;
639
-
640
- const animate = () => {
641
- if (cancelled) return;
642
- requestSharedAnimationFrame(animate);
643
-
644
- const wasAnimating = isAnimating;
645
- isAnimating = galleryController.render();
646
-
647
- if (isAnimating) {
648
- if (!wasAnimating) {
649
- // Animation just started
650
- frameCount = 0;
651
- fpsStartTime = performance.now();
652
- }
653
-
654
- frameCount++;
655
- const elapsed = performance.now() - fpsStartTime;
656
-
657
- if (elapsed > 1000 && frameCount > 10) {
658
- // After 1 second and at least 10 frames
659
- const fps = (frameCount / elapsed) * 1000;
660
- console.log(`Gallery Animation FPS: ${fps.toFixed(1)}`);
661
- frameCount = 0;
662
- fpsStartTime = performance.now();
663
- }
664
-
665
- if (ctx) {
666
- // Set canvas size to match target dimensions
667
- ctx.canvas.width = w * rendererWrapper.pixelRatio;
668
- ctx.canvas.height = h * rendererWrapper.pixelRatio;
669
-
670
- // Clear canvas and render
671
- ctx.clearRect(0, 0, w * rendererWrapper.pixelRatio, h * rendererWrapper.pixelRatio);
672
- rendererWrapper.render(galleryController.sceneWrapper, galleryController.camera, ctx, theme);
673
- }
674
- }
675
- };
676
- animate();
677
- return () => {
678
- cancelled = true;
679
- };
680
- }, [id, rendererWrapper, galleryController, paused, theme, w, h]);
681
-
682
- useEffect(() => {
683
- const el = refContainer.current;
684
- if (!el) return;
685
- const hammer = new Hammer.Manager(el);
686
- hammer.add(new Hammer.Pan({ direction: Hammer.DIRECTION_HORIZONTAL }));
687
-
688
- const fixPosition = (ev: HammerInput) => {
689
- const rect = el.getBoundingClientRect();
690
- return { x: ev.center.x - rect.left, y: ev.center.y - rect.top };
691
- };
692
-
693
- hammer.add(new Hammer.Tap());
694
- hammer.on("tap", (ev) => {
695
- const pos = fixPosition(ev);
696
-
697
- if (galleryController.isAnimating()) {
698
- galleryController.pan(0, true); // goofy but fine? locks to closest slot?
699
- } else {
700
- const tappedItem = galleryController.getItemAtPosition(pos.x, pos.y);
701
- if (tappedItem) {
702
- if (tappedItem.onClick) {
703
- tappedItem.onClick();
704
-
705
- // // TODO: this is maybe not right? do we always want to close upon selection? I don't think so
706
- // if (onClose) {
707
- // setTimeout(onClose, 500);
708
- // }
709
- }
710
- } else if (onClose) {
711
- onClose();
712
- }
713
- }
714
- });
715
-
716
- let lastX: number | undefined = undefined;
717
- let lastVelocityX = 0;
718
- hammer.on("pan", (ev) => {
719
- if (lastX === undefined) {
720
- lastX = 0;
721
- } else {
722
- lastVelocityX = ev.velocityX;
723
- galleryController.pan(-(lastX - ev.deltaX));
724
- lastX = ev.deltaX;
725
- }
726
- ev.preventDefault();
727
- });
728
- hammer.on("panend", () => {
729
- lastX = undefined;
730
- galleryController.pan(lastVelocityX * 300, true);
731
- lastVelocityX = 0;
732
- });
733
-
734
- let timeout: NodeJS.Timeout;
735
- const wheelListener = (ev: any) => {
736
- const dy = ev.wheelDeltaY as number;
737
- galleryController.pan(dy / 3, false);
738
- ev.preventDefault();
739
- clearTimeout(timeout);
740
- timeout = setTimeout(() => galleryController.pan(0, true), 50);
741
- };
742
-
743
- addWheelListener(el, wheelListener);
744
- return () => {
745
- hammer.destroy();
746
- removeWheelListener(el, wheelListener);
747
- };
748
- }, [galleryController, onClose]);
749
-
750
- // Cleanup sceneWrapper on unmount
751
- useEffect(() => {
752
- TextureReferenaceCounter.registerInstance(galleryController);
753
- return () => {
754
- TextureReferenaceCounter.unregisterInstance(galleryController);
755
- galleryController.sceneWrapper.dispose();
756
- };
757
- }, [galleryController]);
758
-
759
- if (!w || !h) {
760
- return null;
761
- }
762
-
763
- return (
764
- <Box sx={{ position: "absolute", top: 0, right: 0, left: 0, bottom: 0 }}>
765
- <canvas
766
- width={w * rendererWrapper.pixelRatio}
767
- height={h * rendererWrapper.pixelRatio}
768
- style={{ width: w, height: h }}
769
- ref={refContainer}
770
- />
771
- </Box>
772
- );
773
- }
1
+ // This file is kept for backward compatibility
2
+ // The implementation has been moved to the Gallery folder for better organization
3
+ export { GalleryViewer } from "./Gallery";
4
+ export type { GalleryItem, GalleryItemSource } from "./Gallery";