@nice2dev/ui-graphics 1.0.0 → 1.0.3

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (146) hide show
  1. package/CHANGELOG.md +147 -1
  2. package/dist/cjs/animation/AnimatedPerson.js +2 -2
  3. package/dist/cjs/animation/AnimatedPerson.js.map +1 -1
  4. package/dist/cjs/animation/AnimationEditor.js +11 -6
  5. package/dist/cjs/animation/AnimationEditor.js.map +1 -1
  6. package/dist/cjs/animation/Audience.js +4 -3
  7. package/dist/cjs/animation/Audience.js.map +1 -1
  8. package/dist/cjs/animation/BodyRenderer.js +5 -2
  9. package/dist/cjs/animation/BodyRenderer.js.map +1 -1
  10. package/dist/cjs/animation/rig/RigPlayer.js +2 -2
  11. package/dist/cjs/animation/rig/RigPlayer.js.map +1 -1
  12. package/dist/cjs/animation/rig/RiggedBody.js +2 -2
  13. package/dist/cjs/animation/rig/RiggedBody.js.map +1 -1
  14. package/dist/cjs/animation/shapes/heads.js +4 -1
  15. package/dist/cjs/animation/shapes/heads.js.map +1 -1
  16. package/dist/cjs/core/LocalUI.js +1 -1
  17. package/dist/cjs/core/NiceBrushEngine.js +446 -0
  18. package/dist/cjs/core/NiceBrushEngine.js.map +1 -0
  19. package/dist/cjs/core/yjsCollaboration.js +292 -0
  20. package/dist/cjs/core/yjsCollaboration.js.map +1 -0
  21. package/dist/cjs/font/NiceFontEditor.js +89 -85
  22. package/dist/cjs/font/NiceFontEditor.js.map +1 -1
  23. package/dist/cjs/font/fontFormatUtils.js +468 -0
  24. package/dist/cjs/font/fontFormatUtils.js.map +1 -0
  25. package/dist/cjs/game/GameAsset2dEditor.js +38 -24
  26. package/dist/cjs/game/GameAsset2dEditor.js.map +1 -1
  27. package/dist/cjs/icon/NiceIconEditor.js +218 -133
  28. package/dist/cjs/icon/NiceIconEditor.js.map +1 -1
  29. package/dist/cjs/index.js +83 -1
  30. package/dist/cjs/index.js.map +1 -1
  31. package/dist/cjs/nice2dev-ui-graphics.css +1 -1
  32. package/dist/cjs/photo/NiceAITools.js +446 -0
  33. package/dist/cjs/photo/NiceAITools.js.map +1 -0
  34. package/dist/cjs/photo/PhotoEditor.js +2 -2
  35. package/dist/cjs/photo/PhotoEditor.js.map +1 -1
  36. package/dist/cjs/pixel/PixelEditor.js +16 -5
  37. package/dist/cjs/pixel/PixelEditor.js.map +1 -1
  38. package/dist/cjs/pixel/PixelEditor.module.css.js +1 -1
  39. package/dist/cjs/pixel/PixelEditorMenuBar.js +2 -1
  40. package/dist/cjs/pixel/PixelEditorMenuBar.js.map +1 -1
  41. package/dist/cjs/pixel/PixelEditorRightPanel.js +3 -2
  42. package/dist/cjs/pixel/PixelEditorRightPanel.js.map +1 -1
  43. package/dist/cjs/pixel/PixelEditorTimeline.js +2 -1
  44. package/dist/cjs/pixel/PixelEditorTimeline.js.map +1 -1
  45. package/dist/cjs/pixel/PixelEditorToolbar.js +2 -1
  46. package/dist/cjs/pixel/PixelEditorToolbar.js.map +1 -1
  47. package/dist/cjs/pixel/SpriteGeneratorPanel.js +224 -0
  48. package/dist/cjs/pixel/SpriteGeneratorPanel.js.map +1 -0
  49. package/dist/cjs/pixel/animalGeneratorPresets.js +654 -0
  50. package/dist/cjs/pixel/animalGeneratorPresets.js.map +1 -0
  51. package/dist/cjs/pixel/buildingGeneratorPresets.js +573 -0
  52. package/dist/cjs/pixel/buildingGeneratorPresets.js.map +1 -0
  53. package/dist/cjs/pixel/characterGeneratorPresets.js +563 -0
  54. package/dist/cjs/pixel/characterGeneratorPresets.js.map +1 -0
  55. package/dist/cjs/pixel/spriteGeneratorCore.js +297 -0
  56. package/dist/cjs/pixel/spriteGeneratorCore.js.map +1 -0
  57. package/dist/cjs/pixel/usePixelEditor.js +16 -0
  58. package/dist/cjs/pixel/usePixelEditor.js.map +1 -1
  59. package/dist/cjs/texture/Nice3DTexturePainter.js +123 -79
  60. package/dist/cjs/texture/Nice3DTexturePainter.js.map +1 -1
  61. package/dist/cjs/ui/NiceUIDesigner.js +175 -62
  62. package/dist/cjs/ui/NiceUIDesigner.js.map +1 -1
  63. package/dist/cjs/ui/dist/index.js +50089 -0
  64. package/dist/cjs/ui/dist/index.js.map +1 -0
  65. package/dist/cjs/vector/NiceSvgToCode.js +427 -0
  66. package/dist/cjs/vector/NiceSvgToCode.js.map +1 -0
  67. package/dist/cjs/vector/VectorEditor.js +7 -3
  68. package/dist/cjs/vector/VectorEditor.js.map +1 -1
  69. package/dist/cjs/vector/VectorEditor.module.css.js +1 -1
  70. package/dist/cjs/vector/VectorEditorMenuBar.js +5 -1
  71. package/dist/cjs/vector/VectorEditorMenuBar.js.map +1 -1
  72. package/dist/cjs/vector/VectorEditorRightPanel.js +23 -19
  73. package/dist/cjs/vector/VectorEditorRightPanel.js.map +1 -1
  74. package/dist/esm/animation/AnimatedPerson.js +2 -2
  75. package/dist/esm/animation/AnimatedPerson.js.map +1 -1
  76. package/dist/esm/animation/AnimationEditor.js +12 -8
  77. package/dist/esm/animation/AnimationEditor.js.map +1 -1
  78. package/dist/esm/animation/Audience.js +5 -4
  79. package/dist/esm/animation/Audience.js.map +1 -1
  80. package/dist/esm/animation/BodyRenderer.js +4 -2
  81. package/dist/esm/animation/BodyRenderer.js.map +1 -1
  82. package/dist/esm/animation/rig/RigPlayer.js +4 -4
  83. package/dist/esm/animation/rig/RigPlayer.js.map +1 -1
  84. package/dist/esm/animation/rig/RiggedBody.js +2 -2
  85. package/dist/esm/animation/rig/RiggedBody.js.map +1 -1
  86. package/dist/esm/animation/shapes/heads.js +4 -2
  87. package/dist/esm/animation/shapes/heads.js.map +1 -1
  88. package/dist/esm/core/LocalUI.js +4 -4
  89. package/dist/esm/core/NiceBrushEngine.js +442 -0
  90. package/dist/esm/core/NiceBrushEngine.js.map +1 -0
  91. package/dist/esm/core/yjsCollaboration.js +283 -0
  92. package/dist/esm/core/yjsCollaboration.js.map +1 -0
  93. package/dist/esm/font/NiceFontEditor.js +89 -85
  94. package/dist/esm/font/NiceFontEditor.js.map +1 -1
  95. package/dist/esm/font/fontFormatUtils.js +461 -0
  96. package/dist/esm/font/fontFormatUtils.js.map +1 -0
  97. package/dist/esm/game/GameAsset2dEditor.js +38 -25
  98. package/dist/esm/game/GameAsset2dEditor.js.map +1 -1
  99. package/dist/esm/icon/NiceIconEditor.js +218 -133
  100. package/dist/esm/icon/NiceIconEditor.js.map +1 -1
  101. package/dist/esm/index.js +21 -11
  102. package/dist/esm/index.js.map +1 -1
  103. package/dist/esm/nice2dev-ui-graphics.css +1 -1
  104. package/dist/esm/photo/NiceAITools.js +439 -0
  105. package/dist/esm/photo/NiceAITools.js.map +1 -0
  106. package/dist/esm/photo/PhotoEditor.js +2 -2
  107. package/dist/esm/photo/PhotoEditor.js.map +1 -1
  108. package/dist/esm/pixel/PixelEditor.js +16 -6
  109. package/dist/esm/pixel/PixelEditor.js.map +1 -1
  110. package/dist/esm/pixel/PixelEditor.module.css.js +1 -1
  111. package/dist/esm/pixel/PixelEditorMenuBar.js +2 -1
  112. package/dist/esm/pixel/PixelEditorMenuBar.js.map +1 -1
  113. package/dist/esm/pixel/PixelEditorRightPanel.js +3 -2
  114. package/dist/esm/pixel/PixelEditorRightPanel.js.map +1 -1
  115. package/dist/esm/pixel/PixelEditorTimeline.js +2 -1
  116. package/dist/esm/pixel/PixelEditorTimeline.js.map +1 -1
  117. package/dist/esm/pixel/PixelEditorToolbar.js +2 -1
  118. package/dist/esm/pixel/PixelEditorToolbar.js.map +1 -1
  119. package/dist/esm/pixel/SpriteGeneratorPanel.js +222 -0
  120. package/dist/esm/pixel/SpriteGeneratorPanel.js.map +1 -0
  121. package/dist/esm/pixel/animalGeneratorPresets.js +647 -0
  122. package/dist/esm/pixel/animalGeneratorPresets.js.map +1 -0
  123. package/dist/esm/pixel/buildingGeneratorPresets.js +566 -0
  124. package/dist/esm/pixel/buildingGeneratorPresets.js.map +1 -0
  125. package/dist/esm/pixel/characterGeneratorPresets.js +556 -0
  126. package/dist/esm/pixel/characterGeneratorPresets.js.map +1 -0
  127. package/dist/esm/pixel/spriteGeneratorCore.js +279 -0
  128. package/dist/esm/pixel/spriteGeneratorCore.js.map +1 -0
  129. package/dist/esm/pixel/usePixelEditor.js +16 -0
  130. package/dist/esm/pixel/usePixelEditor.js.map +1 -1
  131. package/dist/esm/texture/Nice3DTexturePainter.js +123 -79
  132. package/dist/esm/texture/Nice3DTexturePainter.js.map +1 -1
  133. package/dist/esm/ui/NiceUIDesigner.js +175 -62
  134. package/dist/esm/ui/NiceUIDesigner.js.map +1 -1
  135. package/dist/esm/ui/dist/index.js +49686 -0
  136. package/dist/esm/ui/dist/index.js.map +1 -0
  137. package/dist/esm/vector/NiceSvgToCode.js +423 -0
  138. package/dist/esm/vector/NiceSvgToCode.js.map +1 -0
  139. package/dist/esm/vector/VectorEditor.js +7 -4
  140. package/dist/esm/vector/VectorEditor.js.map +1 -1
  141. package/dist/esm/vector/VectorEditor.module.css.js +1 -1
  142. package/dist/esm/vector/VectorEditorMenuBar.js +5 -1
  143. package/dist/esm/vector/VectorEditorMenuBar.js.map +1 -1
  144. package/dist/esm/vector/VectorEditorRightPanel.js +23 -19
  145. package/dist/esm/vector/VectorEditorRightPanel.js.map +1 -1
  146. package/package.json +3 -4
@@ -1 +1 @@
1
- .PixelEditor-module_root__3gidG{background:var(--editor-bg-deep);color:var(--gray-200);display:flex;flex-direction:column;font-family:Segoe UI,Consolas,monospace;font-size:12px;height:100%;overflow:hidden;user-select:none}.PixelEditor-module_menuBar__8JFld{align-items:center;background:var(--editor-bg-deeper);border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;gap:0;height:28px;padding:0 4px}.PixelEditor-module_menuBtn__w-GQC{background:none;border:none;border-radius:3px;color:var(--editor-text-light);cursor:pointer;font-size:11px;padding:4px 10px}.PixelEditor-module_menuBtn__w-GQC:hover{background:var(--editor-bg-dark);color:var(--color-white)}.PixelEditor-module_menuSep__pNZsR{background:var(--gray-850);height:16px;margin:0 4px;width:1px}.PixelEditor-module_toolbar__paCGq{background:var(--editor-panel);border-right:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;gap:2px;overflow-y:auto;padding:4px 2px;width:38px}.PixelEditor-module_toolBtn__wD1Kj{align-items:center;background:none;border:1px solid transparent;border-radius:4px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:16px;height:32px;justify-content:center;transition:all .1s;width:32px}.PixelEditor-module_toolBtn__wD1Kj:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.PixelEditor-module_toolBtnActive__R51U0{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_mainArea__Z0x6l{display:flex;flex:1;min-height:0}.PixelEditor-module_canvasContainer__8z2AY{background:var(--editor-bg-deepest);cursor:crosshair;flex:1;overflow:hidden;position:relative}.PixelEditor-module_canvasContainer__8z2AY canvas{image-rendering:pixelated;position:absolute}.PixelEditor-module_rightPanel__ZjrCh{background:var(--editor-bg-deep);border-left:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:220px}.PixelEditor-module_panelSection__3l225{border-bottom:1px solid var(--editor-bg-dark);padding:6px 8px}.PixelEditor-module_panelTitle__vYyeO{align-items:center;color:var(--editor-text-secondary);display:flex;font-size:10px;justify-content:space-between;letter-spacing:.5px;margin-bottom:4px;text-transform:uppercase}.PixelEditor-module_panelTitle__vYyeO button{background:none;border:none;color:var(--editor-text-secondary);cursor:pointer;font-size:14px;line-height:1;padding:0 2px}.PixelEditor-module_panelTitle__vYyeO button:hover{color:var(--gray-500)}.PixelEditor-module_layerItem__J-gtn{align-items:center;border-radius:3px;cursor:pointer;display:flex;font-size:11px;gap:4px;padding:3px 4px}.PixelEditor-module_layerItem__J-gtn:hover{background:hsla(0,0%,100%,.04)}.PixelEditor-module_layerItemActive__yPt29{background:var(--editor-surface)!important;border:1px solid var(--accent-blue-dark)}.PixelEditor-module_layerVis__Uj7n2{align-items:center;cursor:pointer;display:flex;flex-shrink:0;font-size:10px;height:16px;justify-content:center;opacity:.6;width:16px}.PixelEditor-module_layerVis__Uj7n2:hover{opacity:1}.PixelEditor-module_layerName__HovwJ{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.PixelEditor-module_layerOpacity__qmWvu{color:var(--gray-600);font-size:10px;text-align:right;width:36px}.PixelEditor-module_paletteGrid__knY-n{display:grid;gap:2px;grid-template-columns:repeat(8,1fr)}.PixelEditor-module_paletteSwatch__MUbha{aspect-ratio:1;border:1px solid hsla(0,0%,100%,.08);border-radius:2px;cursor:pointer;transition:transform .1s}.PixelEditor-module_paletteSwatch__MUbha:hover{transform:scale(1.15);z-index:1}.PixelEditor-module_paletteSwatchActive__wDR4T{border-color:var(--color-white)!important;box-shadow:0 0 0 1px var(--editor-accent)}.PixelEditor-module_colorPickers__sQlBN{align-items:center;display:flex;gap:6px;margin-top:6px}.PixelEditor-module_colorSample__GN7Rd{border:2px solid hsla(0,0%,100%,.2);border-radius:4px;height:28px;width:28px}.PixelEditor-module_bottomPanel__rviLF{background:var(--editor-bg-deeper);border-top:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;height:80px}.PixelEditor-module_timelineControls__Laroq{align-items:center;border-bottom:1px solid #224;display:flex;font-size:11px;gap:6px;padding:2px 8px}.PixelEditor-module_timelineControls__Laroq button{background:var(--editor-bg-dark);border:none;border-radius:3px;color:var(--gray-500);cursor:pointer;font-size:11px;padding:2px 8px}.PixelEditor-module_timelineControls__Laroq button:hover{background:var(--editor-bg-mid);color:var(--color-white)}.PixelEditor-module_timelineControls__Laroq label{color:var(--gray-700)}.PixelEditor-module_timelineControls__Laroq input[type=number]{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);font-size:11px;padding:1px 4px;text-align:center;width:40px}.PixelEditor-module_timelineControls__Laroq input[type=checkbox]{accent-color:var(--editor-accent)}.PixelEditor-module_timelineFrames__dw06F{align-items:stretch;display:flex;flex:1;gap:2px;overflow-x:auto;padding:4px 8px}.PixelEditor-module_frameThumb__2E9mG{align-items:center;background:var(--gray-900);border:2px solid transparent;border-radius:4px;cursor:pointer;display:flex;flex-direction:column;justify-content:center;min-width:44px;overflow:hidden;position:relative;width:44px}.PixelEditor-module_frameThumb__2E9mG canvas{height:36px;image-rendering:pixelated;object-fit:contain;width:36px}.PixelEditor-module_frameThumb__2E9mG:hover{border-color:var(--gray-800)}.PixelEditor-module_frameThumbActive__Z0eK4{background:var(--editor-surface);border-color:var(--editor-accent)!important}.PixelEditor-module_frameNum__PoGQC{bottom:1px;color:var(--gray-700);font-size:8px;position:absolute;right:3px}.PixelEditor-module_statusBar__QnphD{align-items:center;background:var(--gray-950);border-top:1px solid var(--gray-900);color:var(--gray-700);display:flex;flex-shrink:0;font-size:10px;gap:12px;height:20px;padding:2px 8px}.PixelEditor-module_dialogOverlay__IgyFy{align-items:center;background:rgba(0,0,0,.6);display:flex;inset:0;justify-content:center;position:absolute;z-index:100}.PixelEditor-module_dialog__OnkAG{background:var(--editor-panel);border:1px solid var(--editor-bg-mid);border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.5);min-width:300px;padding:20px}.PixelEditor-module_dialog__OnkAG h3{color:var(--gray-300);font-size:14px;margin:0 0 12px}.PixelEditor-module_dialog__OnkAG label{color:var(--gray-600);display:block;font-size:11px;margin:8px 0 2px}.PixelEditor-module_dialog__OnkAG input,.PixelEditor-module_dialog__OnkAG select{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:4px;color:var(--gray-200);font-size:12px;padding:4px 8px;width:100%}.PixelEditor-module_dialogActions__fOa7a{display:flex;gap:8px;justify-content:flex-end;margin-top:16px}.PixelEditor-module_dialogActions__fOa7a button{border:none;border-radius:4px;cursor:pointer;font-size:12px;padding:4px 16px}.PixelEditor-module_btnPrimary__FYlTy{background:var(--editor-accent);color:var(--color-white)}.PixelEditor-module_btnPrimary__FYlTy:hover{background:#67d}.PixelEditor-module_btnSecondary__qLfyJ{background:var(--gray-850);color:var(--gray-500)}.PixelEditor-module_btnSecondary__qLfyJ:hover{background:var(--gray-800);color:var(--gray-200)}.PixelEditor-module_brushSlider__UxQ38{align-items:center;border-bottom:1px solid var(--editor-bg-dark);display:flex;gap:4px;padding:4px 8px}.PixelEditor-module_brushSlider__UxQ38 label{color:var(--gray-700);font-size:10px}.PixelEditor-module_brushSlider__UxQ38 input[type=range]{accent-color:var(--editor-accent);flex:1;height:4px}.PixelEditor-module_brushSlider__UxQ38 span{color:var(--gray-500);font-size:10px;min-width:16px;text-align:center}.PixelEditor-module_toolSep__YIu-E{background:var(--gray-850);height:1px;margin:4px 2px;width:28px}.PixelEditor-module_toolGroup__xA2lN{display:flex;flex-direction:column;gap:1px;padding:2px 0}.PixelEditor-module_miniBtn__tg5N0{align-items:center;background:hsla(0,0%,100%,.04);border:1px solid transparent;border-radius:3px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:10px;height:20px;justify-content:center;transition:all .1s;width:32px}.PixelEditor-module_miniBtn__tg5N0:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.PixelEditor-module_miniBtnActive__gpveu{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_colorSwatches__jFuRX{align-items:center;border-top:1px solid var(--gray-850);display:flex;flex-direction:column;gap:4px;margin-top:4px;padding:6px 0}.PixelEditor-module_brushShapes__2bBfl{display:flex;flex-wrap:wrap;gap:2px;padding:2px 0}.PixelEditor-module_pressureToggles__AITuh{display:flex;flex-direction:column;gap:2px;padding:4px 0}.PixelEditor-module_checkLabel__-d-TA{align-items:center;color:var(--gray-550);cursor:pointer;display:flex;font-size:10px;gap:4px}.PixelEditor-module_checkLabel__-d-TA input[type=checkbox]{accent-color:var(--editor-accent);height:12px;width:12px}.PixelEditor-module_hsvPicker__0ERIh{display:flex;flex-direction:column;gap:4px;padding:4px 0}.PixelEditor-module_hsvRow__M3fhN{align-items:center;display:flex;gap:4px}.PixelEditor-module_hsvLabel__O2MkX{color:var(--gray-700);font-size:9px;min-width:16px;text-align:right}.PixelEditor-module_hsvSlider__KKMMJ{accent-color:var(--editor-accent);cursor:pointer;flex:1;height:6px;min-width:0}.PixelEditor-module_hsvVal__MgQ8W{color:var(--gray-500);font-size:9px;min-width:28px;text-align:right}.PixelEditor-module_hsvNumInput__Wn4kG{text-align:center;width:36px}.PixelEditor-module_hsvHexInput__MU5Ms,.PixelEditor-module_hsvNumInput__Wn4kG{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);font-size:10px;padding:1px 4px}.PixelEditor-module_hsvHexInput__MU5Ms{flex:1}.PixelEditor-module_layerLock__xeWnc{align-items:center;cursor:pointer;display:flex;flex-shrink:0;font-size:10px;height:16px;justify-content:center;opacity:.6;width:16px}.PixelEditor-module_layerLock__xeWnc:hover{opacity:1}.PixelEditor-module_layerNameInput__ZiOKv{background:var(--gray-950);border:1px solid var(--editor-accent);border-radius:2px;color:var(--gray-100);flex:1;font-size:11px;min-width:0;outline:none;padding:0 4px}.PixelEditor-module_layerControls__MrpXo{align-items:center;border-top:1px solid hsla(0,0%,100%,.05);display:flex;gap:4px;margin-top:4px;padding:4px 4px 2px}.PixelEditor-module_blendSelect__QCwns{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-300);cursor:pointer;flex:1;font-size:10px;padding:1px 4px}.PixelEditor-module_layerOpSlider__Vw-qs{accent-color:var(--editor-accent);cursor:pointer;height:4px;width:60px}.VectorEditor-module_root__rtRWo{background:var(--editor-bg-deep);color:var(--gray-200);display:flex;flex-direction:column;font-family:Segoe UI,Consolas,monospace;font-size:12px;height:100%;overflow:hidden;user-select:none}.VectorEditor-module_menuBar__o25XM{align-items:center;background:var(--editor-bg-deeper);border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;gap:0;height:28px;padding:0 4px}.VectorEditor-module_menuBtn__aP4vp{background:none;border:none;border-radius:3px;color:var(--editor-text-light);cursor:pointer;font-size:11px;padding:4px 10px}.VectorEditor-module_menuBtn__aP4vp:hover{background:var(--editor-bg-dark);color:var(--color-white)}.VectorEditor-module_menuSep__3-kTv{background:var(--gray-850);height:16px;margin:0 4px;width:1px}.VectorEditor-module_menuLabel__Bsm0e{align-items:center;color:var(--gray-600);cursor:pointer;display:flex;font-size:10px;gap:2px;padding:0 4px}.VectorEditor-module_toolbar__fakYL{background:var(--editor-panel);border-right:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;gap:2px;padding:4px 2px;width:38px}.VectorEditor-module_toolBtn__Zh7D3{align-items:center;background:none;border:1px solid transparent;border-radius:4px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:16px;height:32px;justify-content:center;transition:all .1s;width:32px}.VectorEditor-module_toolBtn__Zh7D3:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.VectorEditor-module_toolBtnActive__0xZlr{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.VectorEditor-module_mainArea__3o89F{display:flex;flex:1;min-height:0}.VectorEditor-module_canvasContainer__hOUAx{background:var(--editor-bg-deepest);flex:1;overflow:hidden;position:relative}.VectorEditor-module_canvasContainer__hOUAx svg{height:100%;inset:0;position:absolute;width:100%}.VectorEditor-module_rightPanel__3hzcS{background:var(--editor-bg-deep);border-left:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:220px}.VectorEditor-module_panelSection__uteDQ{border-bottom:1px solid var(--editor-bg-dark);padding:6px 8px}.VectorEditor-module_panelTitle__WBUxr{align-items:center;color:var(--editor-text-secondary);display:flex;font-size:10px;justify-content:space-between;letter-spacing:.5px;margin-bottom:4px;text-transform:uppercase}.VectorEditor-module_panelTitle__WBUxr button{background:none;border:none;color:var(--editor-text-secondary);cursor:pointer;font-size:14px;line-height:1;padding:0 2px}.VectorEditor-module_panelTitle__WBUxr button:hover{color:var(--gray-500)}.VectorEditor-module_shapeItem__bu2E2{align-items:center;border-radius:3px;cursor:pointer;display:flex;font-size:11px;gap:6px;padding:3px 4px}.VectorEditor-module_shapeItem__bu2E2:hover{background:hsla(0,0%,100%,.04)}.VectorEditor-module_shapeItemActive__E2lK7{background:var(--editor-surface)!important;border:1px solid var(--accent-blue-dark)}.VectorEditor-module_shapeIcon__M4j6X{flex-shrink:0;font-size:14px;opacity:.7}.VectorEditor-module_shapeName__2QctO{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.VectorEditor-module_propRow__Alc4S{align-items:center;display:flex;gap:6px;margin-bottom:4px}.VectorEditor-module_propLabel__J0lxK{color:var(--gray-600);font-size:10px;min-width:40px}.VectorEditor-module_propInput__3my2d{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);flex:1;font-size:11px;padding:2px 4px}.VectorEditor-module_propColorSwatch__JL97Z{border:1px solid hsla(0,0%,100%,.15);border-radius:3px;cursor:pointer;height:24px;position:relative;width:24px}.VectorEditor-module_propColorSwatch__JL97Z input{cursor:pointer;height:100%;inset:0;opacity:0;position:absolute;width:100%}.VectorEditor-module_statusBar__jMwan{align-items:center;background:var(--gray-950);border-top:1px solid var(--gray-900);color:var(--gray-700);display:flex;flex-shrink:0;font-size:10px;gap:12px;height:20px;padding:2px 8px}.VectorEditor-module_dialogOverlay__NLiCg{align-items:center;background:rgba(0,0,0,.6);display:flex;inset:0;justify-content:center;position:absolute;z-index:100}.VectorEditor-module_dialog__NDNK2{background:var(--editor-panel);border:1px solid var(--editor-bg-mid);border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.5);max-width:500px;min-width:300px;padding:20px}.VectorEditor-module_dialog__NDNK2 h3{color:var(--gray-300);font-size:14px;margin:0 0 12px}.VectorEditor-module_dialog__NDNK2 label{color:var(--gray-600);display:block;font-size:11px;margin:8px 0 2px}.VectorEditor-module_dialog__NDNK2 input,.VectorEditor-module_dialog__NDNK2 select,.VectorEditor-module_dialog__NDNK2 textarea{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:4px;color:var(--gray-200);font-size:12px;padding:4px 8px;width:100%}.VectorEditor-module_dialog__NDNK2 textarea{font-family:monospace;min-height:120px;resize:vertical}.VectorEditor-module_dialogActions__0Sy4X{display:flex;gap:8px;justify-content:flex-end;margin-top:16px}.VectorEditor-module_dialogActions__0Sy4X button{border:none;border-radius:4px;cursor:pointer;font-size:12px;padding:4px 16px}.VectorEditor-module_btnPrimary__f9AaS{background:var(--editor-accent);color:var(--color-white)}.VectorEditor-module_btnPrimary__f9AaS:hover{background:#67d}.VectorEditor-module_btnSecondary__wDps2{background:var(--gray-850);color:var(--gray-500)}.VectorEditor-module_btnSecondary__wDps2:hover{background:var(--gray-800);color:var(--gray-200)}.VectorEditor-module_handleGroup__sMkQj circle{fill:var(--editor-accent);stroke:var(--color-white);stroke-width:1;cursor:pointer}.VectorEditor-module_handleGroup__sMkQj circle:hover{fill:#78e}.PhotoEditor-module_wrapper__jrHYj{background:#1a1a1e;border-radius:12px;color:#eee;display:flex;flex-direction:column;font-family:Segoe UI,sans-serif;font-size:13px;max-height:85vh;overflow:hidden;width:100%}.PhotoEditor-module_loadingWrap__QUTon{align-items:center;color:#aaa;display:flex;justify-content:center;min-height:400px;width:100%}.PhotoEditor-module_mainContent__TCVxf{display:flex;flex:1;min-height:0;overflow:hidden}.PhotoEditor-module_toolbar__RY-Ty{align-items:center;background:#222226;border-bottom:1px solid #333;display:flex;justify-content:space-between;padding:8px 14px}.PhotoEditor-module_toolbarGroup__PXw0-{display:flex;gap:6.5px}.PhotoEditor-module_toolbarDivider__o3kFV{background:#444;margin:0 4px;width:1px}.PhotoEditor-module_toolbarTitle__P1o18{font-size:14px;font-weight:700}.PhotoEditor-module_leftPanel__DnHLU{background:#222226;border-right:1px solid #333;display:flex;flex-direction:column;min-width:280px;overflow:hidden;width:280px}.PhotoEditor-module_tabBar__DZ3MG{border-bottom:1px solid #333;display:flex;flex-wrap:wrap}.PhotoEditor-module_tabButton__BLi97{align-items:center;background:transparent;border:none;border-bottom:2px solid transparent;color:#888;cursor:pointer;display:flex;flex:1 0 auto;flex-direction:column;font-size:10px;font-weight:600;gap:1px;min-width:34px;padding:8px 0;transition:all .15s}.PhotoEditor-module_tabButtonActive__KlQG0{background:#2a2a30}.PhotoEditor-module_tabIcon__-Mq19{font-size:14px}.PhotoEditor-module_panelContent__l5i5t{flex:1;overflow-y:auto;padding:10px 12px}.PhotoEditor-module_sectionTitle__tMvCm{font-size:12px;font-weight:600;margin-bottom:6px}.PhotoEditor-module_sectionTitleMb8__PQ-lV{margin-bottom:8px}.PhotoEditor-module_sectionInfo__bWxW5{color:#aaa;font-size:11px}.PhotoEditor-module_sectionInfoMb__Hk6V-{margin-bottom:10px}.PhotoEditor-module_pillRow__DGJUb{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:10px}.PhotoEditor-module_pillRowMb8__AQrth{margin-bottom:8px}.PhotoEditor-module_pillRowGap3__Y46Vu{display:flex;flex-wrap:wrap;gap:3px;margin-bottom:8px}.PhotoEditor-module_pill__wTFac{background:transparent;border:1px solid #444;border-radius:12px;color:#aaa;cursor:pointer;font-size:11px;font-weight:600;padding:3px 10px}.PhotoEditor-module_pillActive__AfdZR{color:#fff}.PhotoEditor-module_pillCrop__Nsisp{border-radius:6px;padding:4px 12px}.PhotoEditor-module_pillCropActive__p6csO{color:#fff}.PhotoEditor-module_pillEmoji__I42DJ{border-radius:10px;padding:2px 8px}.PhotoEditor-module_pillEmojiActive__0-EM7{color:#fff}.PhotoEditor-module_filterGrid__-29PS{display:grid;gap:6px;grid-template-columns:repeat(3,1fr)}.PhotoEditor-module_emojiGrid__whqqK{display:grid;gap:2px;grid-template-columns:repeat(6,1fr);max-height:260px;overflow-y:auto}.PhotoEditor-module_shapeGrid__TawIy{margin-bottom:16px}.PhotoEditor-module_frameGrid__R09dd,.PhotoEditor-module_shapeGrid__TawIy{display:grid;gap:4px;grid-template-columns:repeat(5,1fr)}.PhotoEditor-module_sliderRow__jsWDQ{align-items:center;display:flex;gap:6px;margin-bottom:8px}.PhotoEditor-module_sliderLabel__zOZ49{color:#aaa;font-size:11px}.PhotoEditor-module_sliderLabelSelf__EwYKU{align-self:center;margin-right:4px}.PhotoEditor-module_sliderValue__qFuTw{font-size:11px;font-weight:600;min-width:28px}.PhotoEditor-module_sliderValueSm__U7FrJ{font-size:10px;min-width:28px}.PhotoEditor-module_adjustColumn__y---T{display:flex;flex-direction:column;gap:8px}.PhotoEditor-module_adjustHeader__6s9zV{display:flex;font-size:11px;justify-content:space-between;margin-bottom:2px}.PhotoEditor-module_adjustIcon__d56rY{text-align:center;width:14px}.PhotoEditor-module_adjustValue__aUUmg{cursor:pointer;font-weight:600;min-width:30px;text-align:right}.PhotoEditor-module_intensitySection__dhe5h{margin-top:12px;padding:8px 0}.PhotoEditor-module_intensityHeader__-KKu6{display:flex;font-size:11px;justify-content:space-between;margin-bottom:4px}.PhotoEditor-module_colorInput__xkF1h{border:none;cursor:pointer;height:28px;padding:0;width:28px}.PhotoEditor-module_colorInputLg__W2KrK{border:none;cursor:pointer;height:30px;padding:0;width:32px}.PhotoEditor-module_colorInputDraw__KYcdG{border:none;cursor:pointer;height:28px;padding:0;width:32px}.PhotoEditor-module_overlayToolbar__hfspp{border-bottom:1px solid #333;display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px;padding:6px 0}.PhotoEditor-module_overlayToolbarLabel__mc4pU{align-self:center;color:#aaa;font-size:11px;margin-right:4px}.PhotoEditor-module_overlayToolbarBtn__AdTmZ{font-size:11px;padding:2px 6px}.PhotoEditor-module_overlaySection__IIl4r{border-top:1px solid #333;margin-top:12px;padding-top:8px}.PhotoEditor-module_overlaySectionTitle__FRx3e{color:#aaa;font-size:11px;font-weight:600;margin-bottom:4px}.PhotoEditor-module_overlayItem__DGUCN{align-items:center;background:transparent;border-radius:4px;color:#ccc;cursor:pointer;display:flex;font-size:11px;gap:6px;margin-bottom:2px;padding:3px 6px}.PhotoEditor-module_overlayIcon__G0pFk{text-align:center;width:18px}.PhotoEditor-module_overlayName__JVh64{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.PhotoEditor-module_overlayDeleteBtn__Ontxv{background:none;border:none;color:#f55;cursor:pointer;font-size:11px;padding:0}.PhotoEditor-module_emojiBtn__jxG9m{background:transparent;border:none;border-radius:6px;cursor:pointer;font-size:22px;line-height:1;padding:4px 0}.PhotoEditor-module_shapeBtn__xZdSV{font-size:20px}.PhotoEditor-module_frameBtn__coMkZ,.PhotoEditor-module_shapeBtn__xZdSV{background:transparent;border:1px solid #444;border-radius:6px;color:#eee;cursor:pointer;line-height:1;padding:6px 0}.PhotoEditor-module_frameBtn__coMkZ{font-size:18px}.PhotoEditor-module_removeFrameBtn__oCuua{background:transparent;border:1px solid #444;border-radius:6px;color:#f55;cursor:pointer;font-size:14px;padding:6px 0}.PhotoEditor-module_textFormatBtn__7Z9RJ{min-width:32px}.PhotoEditor-module_textFormatBtnSm__3ptcG{min-width:28px}.PhotoEditor-module_drawActionBtn__teYz4{flex:1}.PhotoEditor-module_textArea__sBGlB{background:#2a2a30;border:1px solid #444;border-radius:6px;color:#eee;font-size:13px;margin-bottom:8px;resize:none}.PhotoEditor-module_textAreaSm__6xZnY{font-size:12px;margin-bottom:0}.PhotoEditor-module_textBtnRow__AcEnd{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px}.PhotoEditor-module_textGapRow__Dq2uz{display:flex;gap:4px;margin-top:6px}.PhotoEditor-module_editSelectedSection__bgNEh{border-top:1px solid #333;margin-top:12px;padding-top:8px}.PhotoEditor-module_editSelectedLabel__u2rmS{color:#aaa;font-size:11px;margin-bottom:4px}.PhotoEditor-module_shapeColorRow__ip5--{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px}.PhotoEditor-module_shapeColorLabel__nVcbU{align-self:center;color:#aaa;font-size:11px;margin-right:2px}.PhotoEditor-module_shapeColorLabelMl__KiM2d{margin-left:4px}.PhotoEditor-module_shapeFillToggle__BXJ8C{font-size:10px;padding:2px 6px}.PhotoEditor-module_frameColorRow__KRAHz{display:flex;gap:4px;margin-bottom:8px}.PhotoEditor-module_frameThicknessWrap__lXCoC{align-items:center;display:flex;flex:1;gap:4px}.PhotoEditor-module_frameThicknessValue__SAEuc{font-size:10px}.PhotoEditor-module_drawPreview__WPbiv{display:flex;justify-content:center;margin-bottom:12px}.PhotoEditor-module_drawActionRow__CUSWS{display:flex;gap:4px}.PhotoEditor-module_quickColorRow__DTy5E{align-items:center;display:flex;gap:6px;margin-bottom:8px}.PhotoEditor-module_quickColorSwatch__ZjgoA{border:1px solid #555;border-radius:3px;cursor:pointer;height:18px;width:18px}.PhotoEditor-module_transformRow__LKRjS{display:flex;gap:6px;margin-bottom:16px}.PhotoEditor-module_transformZoomRow__h2NlB{align-items:center;display:flex;gap:8px}.PhotoEditor-module_transformZoomValue__LXa51{font-size:11px;font-weight:600;min-width:40px}.PhotoEditor-module_transformInfo__zXP9l{background:#2a2a30;border-radius:8px;color:#aaa;font-size:11px;margin-top:16px;padding:10px}.PhotoEditor-module_canvasViewport__OMBIL{align-items:center;background:#111115;display:flex;flex:1;justify-content:center;overflow:auto;padding:20px;position:relative}.PhotoEditor-module_zoomWrap__JjfiJ{max-height:100%;max-width:100%;position:relative;transform-origin:center center;transition:transform .15s ease}.PhotoEditor-module_compareWrap__-J5ku{cursor:ew-resize;display:inline-block;position:relative}.PhotoEditor-module_canvasOriginal__Apf91{max-width:100%}.PhotoEditor-module_canvasEdited__Eroz7,.PhotoEditor-module_canvasOriginal__Apf91{display:block;max-height:60vh;object-fit:contain}.PhotoEditor-module_compareClip__5qG2I{bottom:0;left:0;overflow:hidden;position:absolute;top:0}.PhotoEditor-module_compareSlider__OIIIK{bottom:0;position:absolute;top:0;transform:translateX(-50%);width:3px}.PhotoEditor-module_compareSliderKnob__VohI9{align-items:center;border-radius:50%;box-shadow:0 2px 8px rgba(0,0,0,.4);display:flex;height:28px;justify-content:center;left:50%;position:absolute;top:50%;transform:translate(-50%,-50%);width:28px}.PhotoEditor-module_compareSliderIcon__pXcct{color:#fff;font-size:12px}.PhotoEditor-module_compareLabelOriginal__GaBoj{background:rgba(0,0,0,.6);left:8px}.PhotoEditor-module_compareLabelEdited__Fr836,.PhotoEditor-module_compareLabelOriginal__GaBoj{border-radius:4px;color:#fff;font-size:11px;font-weight:600;padding:2px 8px;position:absolute;top:8px}.PhotoEditor-module_compareLabelEdited__Fr836{right:8px}.PhotoEditor-module_regularWrap__8umPV{display:inline-block;position:relative}.PhotoEditor-module_canvasRegular__wxapL{border-radius:6px;box-shadow:0 4px 20px rgba(0,0,0,.4);display:block;max-height:60vh;max-width:100%;object-fit:contain}.PhotoEditor-module_cropOverlay__MJk1Y{inset:0;pointer-events:none;position:absolute;z-index:2}.PhotoEditor-module_cropDarkBg__m3axV{background:rgba(0,0,0,.55);inset:0;position:absolute}.PhotoEditor-module_cropGridContainer__NfHdT{inset:0;position:absolute}.PhotoEditor-module_cropSizeLabel__fV2mF{background:rgba(0,0,0,.75);border-radius:3px;bottom:-24px;color:#fff;font-size:10px;left:50%;padding:2px 8px;position:absolute;transform:translateX(-50%);white-space:nowrap}.PhotoEditor-module_cropInfo__Z1SCE{color:#aaa;font-size:11px;margin-bottom:10px}.PhotoEditor-module_cropAspectLabel__dieL-{font-size:12px;font-weight:600;margin-bottom:6px}.PhotoEditor-module_cropAspectRow__scRj3{display:flex;flex-wrap:wrap;gap:4px}.PhotoEditor-module_accentBtn__tgaEx{color:#fff;font-weight:600;width:100%}.GameAsset2dEditor-module_root__WVJBM{background:#1a1a2e;color:#e0e0e0;display:flex;flex-direction:column;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,sans-serif;font-size:13px;height:100%;min-height:600px;user-select:none}.GameAsset2dEditor-module_menuBar__WaEaU{align-items:center;background:#16213e;border-bottom:1px solid #0f3460;display:flex;gap:8px;padding:6px 12px}.GameAsset2dEditor-module_menuBar__WaEaU h3{color:#ffd369;font-size:14px;font-weight:600;margin:0}.GameAsset2dEditor-module_menuGroup__EOreB{display:flex;gap:2px}.GameAsset2dEditor-module_menuBtn__JYWXn{align-items:center;background:transparent;border:none;border-radius:4px;color:#b0b0b0;cursor:pointer;display:flex;font-size:12px;gap:4px;padding:4px 8px;transition:all .15s}.GameAsset2dEditor-module_menuBtn__JYWXn:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_menuBtn__JYWXn:disabled{cursor:not-allowed;opacity:.4}.GameAsset2dEditor-module_spacer__fPVeq{flex:1}.GameAsset2dEditor-module_modeTabs__iKh7C{background:#1f2940;border-bottom:1px solid #0f3460;display:flex;gap:2px;padding:4px 12px}.GameAsset2dEditor-module_modeTab__C12zt{background:transparent;border:none;border-radius:4px 4px 0 0;color:#8892a8;cursor:pointer;font-size:12px;font-weight:500;padding:6px 16px;transition:all .15s}.GameAsset2dEditor-module_modeTab__C12zt:hover{background:hsla(0,0%,100%,.05);color:#c0c8d8}.GameAsset2dEditor-module_modeTab__C12zt.GameAsset2dEditor-module_active__DUroI{background:#1a1a2e;color:#ffd369}.GameAsset2dEditor-module_mainArea__jwDUa{display:flex;flex:1;overflow:hidden}.GameAsset2dEditor-module_leftPanel__xxAg5{background:#16213e;border-right:1px solid #0f3460;display:flex;flex-direction:column;overflow:hidden;width:220px}.GameAsset2dEditor-module_centerArea__xr-Hn{display:flex;flex:1;flex-direction:column;overflow:hidden}.GameAsset2dEditor-module_rightPanel__YoNuc{background:#16213e;border-left:1px solid #0f3460;display:flex;flex-direction:column;overflow:hidden;width:260px}.GameAsset2dEditor-module_toolbar__hEC9S{align-items:center;background:#1f2940;border-bottom:1px solid #0f3460;display:flex;gap:8px;padding:6px 12px}.GameAsset2dEditor-module_toolGroup__Zbn47{background:rgba(0,0,0,.2);border-radius:4px;display:flex;gap:2px;padding:2px}.GameAsset2dEditor-module_toolBtn__5U7Rw{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;font-size:14px;height:28px;justify-content:center;transition:all .15s;width:28px}.GameAsset2dEditor-module_toolBtn__5U7Rw:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_toolBtn__5U7Rw.GameAsset2dEditor-module_active__DUroI{background:#0f3460;color:#ffd369}.GameAsset2dEditor-module_toolBtn__5U7Rw:disabled{cursor:not-allowed;opacity:.3}.GameAsset2dEditor-module_viewport__vEKEv{background:#0a0a14;flex:1;overflow:hidden;position:relative}.GameAsset2dEditor-module_viewportCanvas__FJ5qA{image-rendering:pixelated;image-rendering:crisp-edges;left:50%;position:absolute;top:50%}.GameAsset2dEditor-module_gridOverlay__K8B97{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0}.GameAsset2dEditor-module_panelHeader__xm2As{align-items:center;background:#0f3460;color:#8892a8;display:flex;font-size:11px;font-weight:600;justify-content:space-between;letter-spacing:.5px;padding:8px 12px;text-transform:uppercase}.GameAsset2dEditor-module_panelContent__dvOGq{flex:1;overflow-y:auto;padding:8px}.GameAsset2dEditor-module_panelSection__RQQDr{margin-bottom:16px}.GameAsset2dEditor-module_panelLabel__Ks-Wa{color:#8892a8;display:block;font-size:11px;letter-spacing:.5px;margin-bottom:6px;text-transform:uppercase}.GameAsset2dEditor-module_panelInput__cxNiG{background:#0a0a14;border:1px solid #2a3a5e;border-radius:4px;color:#e0e0e0;font-size:12px;padding:6px 8px;width:100%}.GameAsset2dEditor-module_panelInput__cxNiG:focus{border-color:#ffd369;outline:none}.GameAsset2dEditor-module_tilePalette__OpzmV{display:grid;gap:4px;grid-template-columns:repeat(auto-fill,minmax(40px,1fr));padding:8px}.GameAsset2dEditor-module_tileItem__uWNS9{aspect-ratio:1;background:#0a0a14;border:2px solid transparent;border-radius:4px;cursor:pointer;overflow:hidden;transition:all .15s}.GameAsset2dEditor-module_tileItem__uWNS9:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_tileItem__uWNS9.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_tileItem__uWNS9 img{height:100%;image-rendering:pixelated;object-fit:contain;width:100%}.GameAsset2dEditor-module_layersList__anFaG{display:flex;flex-direction:column;gap:2px}.GameAsset2dEditor-module_layerItem__XSGlu{align-items:center;background:#1f2940;border-radius:4px;cursor:pointer;display:flex;gap:8px;padding:6px 8px;transition:all .15s}.GameAsset2dEditor-module_layerItem__XSGlu:hover{background:#2a3a5e}.GameAsset2dEditor-module_layerItem__XSGlu.GameAsset2dEditor-module_selected__216IN{background:#0f3460;border-left:3px solid #ffd369}.GameAsset2dEditor-module_layerVisibility__RpHjV{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_layerVisibility__RpHjV:hover{background:hsla(0,0%,100%,.1)}.GameAsset2dEditor-module_layerVisibility__RpHjV.GameAsset2dEditor-module_hidden__mukOG{opacity:.4}.GameAsset2dEditor-module_layerName__WBxq5{color:#c0c8d8;flex:1;font-size:12px}.GameAsset2dEditor-module_layerOpacity__FpzL-{color:#8892a8;font-size:10px;text-align:right;width:40px}.GameAsset2dEditor-module_framesList__vg1oO{display:grid;gap:8px;grid-template-columns:repeat(auto-fill,minmax(60px,1fr));padding:8px}.GameAsset2dEditor-module_frameItem__fkEfb{aspect-ratio:1;background:#0a0a14;border:2px solid transparent;border-radius:4px;cursor:pointer;overflow:hidden;position:relative;transition:all .15s}.GameAsset2dEditor-module_frameItem__fkEfb:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_frameItem__fkEfb.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_frameItem__fkEfb canvas{height:100%;image-rendering:pixelated;object-fit:contain;width:100%}.GameAsset2dEditor-module_frameLabel__5IGW8{background:rgba(0,0,0,.7);bottom:0;color:#b0b0b0;font-size:9px;left:0;padding:2px 4px;position:absolute;right:0;text-align:center}.GameAsset2dEditor-module_timeline__dPJk6{background:#16213e;border-top:1px solid #0f3460;padding:8px}.GameAsset2dEditor-module_timelineTrack__mr20w{background:#0a0a14;border-radius:4px;display:flex;gap:4px;overflow-x:auto;padding:4px}.GameAsset2dEditor-module_timelineFrame__AQyGe{background:#1f2940;border:2px solid transparent;border-radius:4px;cursor:pointer;flex-shrink:0;height:48px;overflow:hidden;width:48px}.GameAsset2dEditor-module_timelineFrame__AQyGe:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_timelineFrame__AQyGe.GameAsset2dEditor-module_current__3sAfL{border-color:#ffd369}.GameAsset2dEditor-module_stateGraph__qAWlU{background:#0a0a14;flex:1;overflow:hidden;position:relative}.GameAsset2dEditor-module_stateNode__W9Z-g{background:#1f2940;border:2px solid #2a3a5e;border-radius:8px;cursor:move;min-width:120px;padding:8px 12px;position:absolute;transition:border-color .15s}.GameAsset2dEditor-module_stateNode__W9Z-g:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_stateNode__W9Z-g.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_stateNode__W9Z-g.GameAsset2dEditor-module_entry__cmA9n{border-color:#4ade80}.GameAsset2dEditor-module_stateNodeName__TK5vs{color:#e0e0e0;font-size:12px;font-weight:500;text-align:center}.GameAsset2dEditor-module_stateNodeAnim__VGwnV{color:#8892a8;font-size:10px;margin-top:4px;text-align:center}.GameAsset2dEditor-module_transition__FBbno{stroke:#4a5a7e;stroke-width:2;fill:none;marker-end:url(#arrowhead)}.GameAsset2dEditor-module_transition__FBbno:hover{stroke:#ffd369}.GameAsset2dEditor-module_effectsList__vHq4I{display:flex;flex-direction:column;gap:8px}.GameAsset2dEditor-module_effectItem__6-1li{background:#1f2940;border-radius:6px;overflow:hidden}.GameAsset2dEditor-module_effectHeader__cgVN-{align-items:center;cursor:pointer;display:flex;gap:8px;padding:8px}.GameAsset2dEditor-module_effectToggle__lKE36{background:#0a0a14;border:1px solid #2a3a5e;border-radius:3px;cursor:pointer;height:18px;width:18px}.GameAsset2dEditor-module_effectToggle__lKE36.GameAsset2dEditor-module_enabled__wgDzp{background:#ffd369;border-color:#ffd369}.GameAsset2dEditor-module_effectName__NQCWj{color:#c0c8d8;flex:1;font-size:12px}.GameAsset2dEditor-module_effectRemove__TSSdI{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_effectRemove__TSSdI:hover{background:#ef4444;color:#fff}.GameAsset2dEditor-module_effectParams__UqTBd{background:rgba(0,0,0,.2);padding:8px}.GameAsset2dEditor-module_effectParam__hEsVY{align-items:center;display:flex;gap:8px;margin-bottom:8px}.GameAsset2dEditor-module_effectParam__hEsVY:last-child{margin-bottom:0}.GameAsset2dEditor-module_effectParamLabel__u0Qoc{color:#8892a8;flex:0 0 80px;font-size:11px}.GameAsset2dEditor-module_effectParamInput__aqxdv{background:#0a0a14;border:1px solid #2a3a5e;border-radius:3px;color:#e0e0e0;flex:1;font-size:11px;height:24px;padding:0 8px}.GameAsset2dEditor-module_statusBar__eOrNe{align-items:center;background:#0f3460;color:#8892a8;display:flex;font-size:11px;gap:16px;padding:4px 12px}.GameAsset2dEditor-module_statusItem__kKLHF{align-items:center;display:flex;gap:4px}.GameAsset2dEditor-module_zoomControl__4YD9G{align-items:center;display:flex;gap:4px;margin-left:auto}.GameAsset2dEditor-module_zoomBtn__hxYik{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_zoomBtn__hxYik:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_dialogOverlay__dZYwO{align-items:center;background:rgba(0,0,0,.6);bottom:0;display:flex;justify-content:center;left:0;position:fixed;right:0;top:0;z-index:1000}.GameAsset2dEditor-module_dialog__mfLFL{background:#16213e;border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.4);max-width:500px;min-width:300px;padding:24px}.GameAsset2dEditor-module_dialog__mfLFL h3{color:#ffd369;font-size:16px;margin:0 0 16px}.GameAsset2dEditor-module_dialogActions__vhDXe{display:flex;gap:8px;justify-content:flex-end;margin-top:20px}.GameAsset2dEditor-module_btnPrimary__Gzc25{background:#ffd369;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;font-size:12px;font-weight:600;padding:8px 16px;transition:all .15s}.GameAsset2dEditor-module_btnPrimary__Gzc25:hover{background:#ffe599}.GameAsset2dEditor-module_btnSecondary__G5nK5{background:transparent;border:1px solid #4a5a7e;border-radius:4px;color:#c0c8d8;cursor:pointer;font-size:12px;padding:8px 16px;transition:all .15s}.GameAsset2dEditor-module_btnSecondary__G5nK5:hover{background:hsla(0,0%,100%,.05);border-color:#6a7a9e}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar{width:6px}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-track{background:#0a0a14}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-thumb{background:#2a3a5e;border-radius:3px}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-thumb:hover{background:#4a5a7e}.GameAsset2dEditor-module_dropZone__Z7sYz{border:2px dashed #4a5a7e;border-radius:8px;color:#8892a8;cursor:pointer;padding:24px;text-align:center;transition:all .15s}.GameAsset2dEditor-module_dropZone__Z7sYz:hover{border-color:#ffd369;color:#c0c8d8}.GameAsset2dEditor-module_dropZone__Z7sYz.GameAsset2dEditor-module_active__DUroI{background:rgba(255,211,105,.1);border-color:#ffd369}.GameAsset2dEditor-module_emptyState__3wryk{align-items:center;color:#8892a8;display:flex;flex-direction:column;justify-content:center;padding:32px;text-align:center}.GameAsset2dEditor-module_emptyState__3wryk svg{height:48px;margin-bottom:12px;opacity:.5;width:48px}.GameAsset2dEditor-module_emptyStateText__Q5V1a{font-size:12px;margin-bottom:12px}
1
+ .PixelEditor-module_root__3gidG{background:var(--editor-bg-deep);color:var(--gray-200);display:flex;flex-direction:column;font-family:Segoe UI,Consolas,monospace;font-size:12px;height:100%;overflow:hidden;user-select:none}.PixelEditor-module_menuBar__8JFld{align-items:center;background:var(--editor-bg-deeper);border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;gap:0;height:28px;padding:0 4px}.PixelEditor-module_menuBtn__w-GQC{background:none;border:none;border-radius:3px;color:var(--editor-text-light);cursor:pointer;font-size:11px;padding:4px 10px}.PixelEditor-module_menuBtn__w-GQC:hover{background:var(--editor-bg-dark);color:var(--color-white)}.PixelEditor-module_menuSep__pNZsR{background:var(--gray-850);height:16px;margin:0 4px;width:1px}.PixelEditor-module_toolbar__paCGq{background:var(--editor-panel);border-right:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;gap:2px;overflow-y:auto;padding:4px 2px;width:38px}.PixelEditor-module_toolBtn__wD1Kj{align-items:center;background:none;border:1px solid transparent;border-radius:4px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:16px;height:32px;justify-content:center;transition:all .1s;width:32px}.PixelEditor-module_toolBtn__wD1Kj:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.PixelEditor-module_toolBtnActive__R51U0{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_mainArea__Z0x6l{display:flex;flex:1;min-height:0}.PixelEditor-module_canvasContainer__8z2AY{background:var(--editor-bg-deepest);cursor:crosshair;flex:1;overflow:hidden;position:relative}.PixelEditor-module_canvasContainer__8z2AY canvas{image-rendering:pixelated;position:absolute}.PixelEditor-module_rightPanel__ZjrCh{background:var(--editor-bg-deep);border-left:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:220px}.PixelEditor-module_panelSection__3l225{border-bottom:1px solid var(--editor-bg-dark);padding:6px 8px}.PixelEditor-module_panelTitle__vYyeO{align-items:center;color:var(--editor-text-secondary);display:flex;font-size:10px;justify-content:space-between;letter-spacing:.5px;margin-bottom:4px;text-transform:uppercase}.PixelEditor-module_panelTitle__vYyeO button{background:none;border:none;color:var(--editor-text-secondary);cursor:pointer;font-size:14px;line-height:1;padding:0 2px}.PixelEditor-module_panelTitle__vYyeO button:hover{color:var(--gray-500)}.PixelEditor-module_layerItem__J-gtn{align-items:center;border-radius:3px;cursor:pointer;display:flex;font-size:11px;gap:4px;padding:3px 4px}.PixelEditor-module_layerItem__J-gtn:hover{background:hsla(0,0%,100%,.04)}.PixelEditor-module_layerItemActive__yPt29{background:var(--editor-surface)!important;border:1px solid var(--accent-blue-dark)}.PixelEditor-module_layerVis__Uj7n2{align-items:center;cursor:pointer;display:flex;flex-shrink:0;font-size:10px;height:16px;justify-content:center;opacity:.6;width:16px}.PixelEditor-module_layerVis__Uj7n2:hover{opacity:1}.PixelEditor-module_layerName__HovwJ{flex:1;min-width:0;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.PixelEditor-module_layerOpacity__qmWvu{color:var(--gray-600);font-size:10px;text-align:right;width:36px}.PixelEditor-module_paletteGrid__knY-n{display:grid;gap:2px;grid-template-columns:repeat(8,1fr)}.PixelEditor-module_paletteSwatch__MUbha{aspect-ratio:1;border:1px solid hsla(0,0%,100%,.08);border-radius:2px;cursor:pointer;transition:transform .1s}.PixelEditor-module_paletteSwatch__MUbha:hover{transform:scale(1.15);z-index:1}.PixelEditor-module_paletteSwatchActive__wDR4T{border-color:var(--color-white)!important;box-shadow:0 0 0 1px var(--editor-accent)}.PixelEditor-module_colorPickers__sQlBN{align-items:center;display:flex;gap:6px;margin-top:6px}.PixelEditor-module_colorSample__GN7Rd{border:2px solid hsla(0,0%,100%,.2);border-radius:4px;height:28px;width:28px}.PixelEditor-module_bottomPanel__rviLF{background:var(--editor-bg-deeper);border-top:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;height:80px}.PixelEditor-module_timelineControls__Laroq{align-items:center;border-bottom:1px solid #224;display:flex;font-size:11px;gap:6px;padding:2px 8px}.PixelEditor-module_timelineControls__Laroq button{background:var(--editor-bg-dark);border:none;border-radius:3px;color:var(--gray-500);cursor:pointer;font-size:11px;padding:2px 8px}.PixelEditor-module_timelineControls__Laroq button:hover{background:var(--editor-bg-mid);color:var(--color-white)}.PixelEditor-module_timelineControls__Laroq label{color:var(--gray-700)}.PixelEditor-module_timelineControls__Laroq input[type=number]{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);font-size:11px;padding:1px 4px;text-align:center;width:40px}.PixelEditor-module_timelineControls__Laroq input[type=checkbox]{accent-color:var(--editor-accent)}.PixelEditor-module_timelineFrames__dw06F{align-items:stretch;display:flex;flex:1;gap:2px;overflow-x:auto;padding:4px 8px}.PixelEditor-module_frameThumb__2E9mG{align-items:center;background:var(--gray-900);border:2px solid transparent;border-radius:4px;cursor:pointer;display:flex;flex-direction:column;justify-content:center;min-width:44px;overflow:hidden;position:relative;width:44px}.PixelEditor-module_frameThumb__2E9mG canvas{height:36px;image-rendering:pixelated;object-fit:contain;width:36px}.PixelEditor-module_frameThumb__2E9mG:hover{border-color:var(--gray-800)}.PixelEditor-module_frameThumbActive__Z0eK4{background:var(--editor-surface);border-color:var(--editor-accent)!important}.PixelEditor-module_frameNum__PoGQC{bottom:1px;color:var(--gray-700);font-size:8px;position:absolute;right:3px}.PixelEditor-module_statusBar__QnphD{align-items:center;background:var(--gray-950);border-top:1px solid var(--gray-900);color:var(--gray-700);display:flex;flex-shrink:0;font-size:10px;gap:12px;height:20px;padding:2px 8px}.PixelEditor-module_dialogOverlay__IgyFy{align-items:center;background:rgba(0,0,0,.6);display:flex;inset:0;justify-content:center;position:absolute;z-index:100}.PixelEditor-module_dialog__OnkAG{background:var(--editor-panel);border:1px solid var(--editor-bg-mid);border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.5);min-width:300px;padding:20px}.PixelEditor-module_dialog__OnkAG h3{color:var(--gray-300);font-size:14px;margin:0 0 12px}.PixelEditor-module_dialog__OnkAG label{color:var(--gray-600);display:block;font-size:11px;margin:8px 0 2px}.PixelEditor-module_dialog__OnkAG input,.PixelEditor-module_dialog__OnkAG select{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:4px;color:var(--gray-200);font-size:12px;padding:4px 8px;width:100%}.PixelEditor-module_dialogActions__fOa7a{display:flex;gap:8px;justify-content:flex-end;margin-top:16px}.PixelEditor-module_dialogActions__fOa7a button{border:none;border-radius:4px;cursor:pointer;font-size:12px;padding:4px 16px}.PixelEditor-module_btnPrimary__FYlTy{background:var(--editor-accent);color:var(--color-white)}.PixelEditor-module_btnPrimary__FYlTy:hover{background:#67d}.PixelEditor-module_btnSecondary__qLfyJ{background:var(--gray-850);color:var(--gray-500)}.PixelEditor-module_btnSecondary__qLfyJ:hover{background:var(--gray-800);color:var(--gray-200)}.PixelEditor-module_brushSlider__UxQ38{align-items:center;border-bottom:1px solid var(--editor-bg-dark);display:flex;gap:4px;padding:4px 8px}.PixelEditor-module_brushSlider__UxQ38 label{color:var(--gray-700);font-size:10px}.PixelEditor-module_brushSlider__UxQ38 input[type=range]{accent-color:var(--editor-accent);flex:1;height:4px}.PixelEditor-module_brushSlider__UxQ38 span{color:var(--gray-500);font-size:10px;min-width:16px;text-align:center}.PixelEditor-module_toolSep__YIu-E{background:var(--gray-850);height:1px;margin:4px 2px;width:28px}.PixelEditor-module_toolGroup__xA2lN{display:flex;flex-direction:column;gap:1px;padding:2px 0}.PixelEditor-module_miniBtn__tg5N0{align-items:center;background:hsla(0,0%,100%,.04);border:1px solid transparent;border-radius:3px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:10px;height:20px;justify-content:center;transition:all .1s;width:32px}.PixelEditor-module_miniBtn__tg5N0:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.PixelEditor-module_miniBtnActive__gpveu{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_colorSwatches__jFuRX{align-items:center;border-top:1px solid var(--gray-850);display:flex;flex-direction:column;gap:4px;margin-top:4px;padding:6px 0}.PixelEditor-module_brushShapes__2bBfl{display:flex;flex-wrap:wrap;gap:2px;padding:2px 0}.PixelEditor-module_pressureToggles__AITuh{display:flex;flex-direction:column;gap:2px;padding:4px 0}.PixelEditor-module_checkLabel__-d-TA{align-items:center;color:var(--gray-550);cursor:pointer;display:flex;font-size:10px;gap:4px}.PixelEditor-module_checkLabel__-d-TA input[type=checkbox]{accent-color:var(--editor-accent);height:12px;width:12px}.PixelEditor-module_hsvPicker__0ERIh{display:flex;flex-direction:column;gap:4px;padding:4px 0}.PixelEditor-module_hsvRow__M3fhN{align-items:center;display:flex;gap:4px}.PixelEditor-module_hsvLabel__O2MkX{color:var(--gray-700);font-size:9px;min-width:16px;text-align:right}.PixelEditor-module_hsvSlider__KKMMJ{accent-color:var(--editor-accent);cursor:pointer;flex:1;height:6px;min-width:0}.PixelEditor-module_hsvVal__MgQ8W{color:var(--gray-500);font-size:9px;min-width:28px;text-align:right}.PixelEditor-module_hsvNumInput__Wn4kG{text-align:center;width:36px}.PixelEditor-module_hsvHexInput__MU5Ms,.PixelEditor-module_hsvNumInput__Wn4kG{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);font-size:10px;padding:1px 4px}.PixelEditor-module_hsvHexInput__MU5Ms{flex:1}.PixelEditor-module_layerLock__xeWnc{align-items:center;cursor:pointer;display:flex;flex-shrink:0;font-size:10px;height:16px;justify-content:center;opacity:.6;width:16px}.PixelEditor-module_layerLock__xeWnc:hover{opacity:1}.PixelEditor-module_layerNameInput__ZiOKv{background:var(--gray-950);border:1px solid var(--editor-accent);border-radius:2px;color:var(--gray-100);flex:1;font-size:11px;min-width:0;outline:none;padding:0 4px}.PixelEditor-module_layerControls__MrpXo{align-items:center;border-top:1px solid hsla(0,0%,100%,.05);display:flex;gap:4px;margin-top:4px;padding:4px 4px 2px}.PixelEditor-module_blendSelect__QCwns{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-300);cursor:pointer;flex:1;font-size:10px;padding:1px 4px}.PixelEditor-module_layerOpSlider__Vw-qs{accent-color:var(--editor-accent);cursor:pointer;height:4px;width:60px}.PixelEditor-module_genPanel__99Md8{background:var(--editor-panel);border:1px solid var(--editor-bg-mid);border-radius:10px;box-shadow:0 12px 48px rgba(0,0,0,.6);display:flex;flex-direction:column;height:600px;max-height:85vh;max-width:95vw;overflow:hidden;width:820px}.PixelEditor-module_genHeader__xN4FZ{align-items:center;border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;justify-content:space-between;padding:10px 16px}.PixelEditor-module_genHeader__xN4FZ h3{color:var(--gray-300);font-size:14px;margin:0}.PixelEditor-module_genTabs__No5Za{background:var(--editor-bg-deeper);border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0}.PixelEditor-module_genTabBtn__e2VhB{background:none;border:none;border-bottom:2px solid transparent;color:var(--editor-text-secondary);cursor:pointer;flex:1;font-size:11px;padding:6px 8px;transition:all .15s}.PixelEditor-module_genTabBtn__e2VhB:hover{background:var(--editor-panel);color:var(--gray-500)}.PixelEditor-module_genTabBtnActive__Rt3jQ{background:var(--editor-panel)!important;border-bottom-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_genBody__MuiQy{display:flex;flex:1;min-height:0;overflow:hidden}.PixelEditor-module_genLeft__JdEw6{border-right:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:200px}.PixelEditor-module_genCenter__c5X0S{align-items:center;display:flex;flex:1;flex-direction:column;gap:8px;overflow-y:auto;padding:8px}.PixelEditor-module_genRight__qFz11{border-left:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:200px}.PixelEditor-module_genPreviewWrap__360F-{align-items:center;background:var(--editor-bg-deepest);border:1px solid var(--editor-bg-dark);border-radius:6px;display:flex;flex:1;justify-content:center;min-height:120px;overflow:hidden;width:100%}.PixelEditor-module_genPreviewCanvas__75Lw2{image-rendering:pixelated;max-height:100%;max-width:100%;min-height:64px;min-width:64px;object-fit:contain}.PixelEditor-module_genDirGrid__xjEp7{display:flex;flex-wrap:wrap;gap:2px;justify-content:center}.PixelEditor-module_genRow__awCw9{align-items:center;display:flex;gap:4px;width:100%}.PixelEditor-module_genPresetGrid__f9XK6{display:flex;flex-wrap:wrap;gap:2px}.PixelEditor-module_genPresetBtn__5C2We{background:hsla(0,0%,100%,.04);border:1px solid transparent;border-radius:3px;color:var(--editor-text-muted);cursor:pointer;font-size:9px;padding:3px 6px;transition:all .1s}.PixelEditor-module_genPresetBtn__5C2We:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.PixelEditor-module_genPresetBtnActive__WAGew{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.PixelEditor-module_genPartGrid__l17oc{display:flex;flex-wrap:wrap;gap:2px}.PixelEditor-module_genColorSwatches__acI6q{display:flex;gap:2px;margin-top:2px}.PixelEditor-module_genColorSwatch__JE8BO{border:1px solid hsla(0,0%,100%,.1);border-radius:2px;height:16px;width:16px}.PixelEditor-module_genAssemblyItem__zNL2P{align-items:center;border-radius:3px;display:flex;font-size:10px;gap:4px;padding:2px 4px}.PixelEditor-module_genAssemblyItem__zNL2P:hover{background:hsla(0,0%,100%,.04)}.PixelEditor-module_genAssemblyName__GU-kr{color:var(--gray-400);flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.PixelEditor-module_genFooter__WkyJp{border-top:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;gap:8px;justify-content:flex-end;padding:10px 16px}.PixelEditor-module_btnIcon__O59l9{background:none;border:none;color:var(--gray-600);cursor:pointer;font-size:14px;line-height:1;padding:2px}.PixelEditor-module_btnIcon__O59l9:hover{color:var(--gray-300)}.PixelEditor-module_propSelect__4P0Qi{flex:1}.PixelEditor-module_propInput__Q-kr2,.PixelEditor-module_propSelect__4P0Qi{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);font-size:11px;min-width:0;padding:2px 4px}.VectorEditor-module_root__rtRWo{background:var(--editor-bg-deep);color:var(--gray-200);display:flex;flex-direction:column;font-family:Segoe UI,Consolas,monospace;font-size:12px;height:100%;overflow:hidden;user-select:none}.VectorEditor-module_menuBar__o25XM{align-items:center;background:var(--editor-bg-deeper);border-bottom:1px solid var(--editor-bg-dark);display:flex;flex-shrink:0;gap:0;height:28px;padding:0 4px}.VectorEditor-module_menuBtn__aP4vp{background:none;border:none;border-radius:3px;color:var(--editor-text-light);cursor:pointer;font-size:11px;padding:4px 10px}.VectorEditor-module_menuBtn__aP4vp:hover{background:var(--editor-bg-dark);color:var(--color-white)}.VectorEditor-module_menuSep__3-kTv{background:var(--gray-850);height:16px;margin:0 4px;width:1px}.VectorEditor-module_menuLabel__Bsm0e{align-items:center;color:var(--gray-600);cursor:pointer;display:flex;font-size:10px;gap:2px;padding:0 4px}.VectorEditor-module_toolbar__fakYL{background:var(--editor-panel);border-right:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;gap:2px;padding:4px 2px;width:38px}.VectorEditor-module_toolBtn__Zh7D3{align-items:center;background:none;border:1px solid transparent;border-radius:4px;color:var(--editor-text-muted);cursor:pointer;display:flex;font-size:16px;height:32px;justify-content:center;transition:all .1s;width:32px}.VectorEditor-module_toolBtn__Zh7D3:hover{background:var(--editor-bg-dark);color:var(--gray-300)}.VectorEditor-module_toolBtnActive__0xZlr{background:var(--editor-bg-mid)!important;border-color:var(--editor-accent)!important;color:var(--color-white)!important}.VectorEditor-module_mainArea__3o89F{display:flex;flex:1;min-height:0}.VectorEditor-module_canvasContainer__hOUAx{background:var(--editor-bg-deepest);flex:1;overflow:hidden;position:relative}.VectorEditor-module_canvasContainer__hOUAx svg{height:100%;inset:0;position:absolute;width:100%}.VectorEditor-module_rightPanel__3hzcS{background:var(--editor-bg-deep);border-left:1px solid var(--editor-bg-dark);display:flex;flex-direction:column;flex-shrink:0;overflow-y:auto;width:220px}.VectorEditor-module_panelSection__uteDQ{border-bottom:1px solid var(--editor-bg-dark);padding:6px 8px}.VectorEditor-module_panelTitle__WBUxr{align-items:center;color:var(--editor-text-secondary);display:flex;font-size:10px;justify-content:space-between;letter-spacing:.5px;margin-bottom:4px;text-transform:uppercase}.VectorEditor-module_panelTitle__WBUxr button{background:none;border:none;color:var(--editor-text-secondary);cursor:pointer;font-size:14px;line-height:1;padding:0 2px}.VectorEditor-module_panelTitle__WBUxr button:hover{color:var(--gray-500)}.VectorEditor-module_shapeItem__bu2E2{align-items:center;border-radius:3px;cursor:pointer;display:flex;font-size:11px;gap:6px;padding:3px 4px}.VectorEditor-module_shapeItem__bu2E2:hover{background:hsla(0,0%,100%,.04)}.VectorEditor-module_shapeItemActive__E2lK7{background:var(--editor-surface)!important;border:1px solid var(--accent-blue-dark)}.VectorEditor-module_shapeIcon__M4j6X{flex-shrink:0;font-size:14px;opacity:.7}.VectorEditor-module_shapeName__2QctO{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.VectorEditor-module_propRow__Alc4S{align-items:center;display:flex;gap:6px;margin-bottom:4px}.VectorEditor-module_propLabel__J0lxK{color:var(--gray-600);font-size:10px;min-width:40px}.VectorEditor-module_propInput__3my2d{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:3px;color:var(--gray-200);flex:1;font-size:11px;padding:2px 4px}.VectorEditor-module_propColorSwatch__JL97Z{border:1px solid hsla(0,0%,100%,.15);border-radius:3px;cursor:pointer;height:24px;position:relative;width:24px}.VectorEditor-module_propColorSwatch__JL97Z input{cursor:pointer;height:100%;inset:0;opacity:0;position:absolute;width:100%}.VectorEditor-module_statusBar__jMwan{align-items:center;background:var(--gray-950);border-top:1px solid var(--gray-900);color:var(--gray-700);display:flex;flex-shrink:0;font-size:10px;gap:12px;height:20px;padding:2px 8px}.VectorEditor-module_dialogOverlay__NLiCg{align-items:center;background:rgba(0,0,0,.6);display:flex;inset:0;justify-content:center;position:absolute;z-index:100}.VectorEditor-module_dialog__NDNK2{background:var(--editor-panel);border:1px solid var(--editor-bg-mid);border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.5);max-width:500px;min-width:300px;padding:20px}.VectorEditor-module_dialog__NDNK2 h3{color:var(--gray-300);font-size:14px;margin:0 0 12px}.VectorEditor-module_dialog__NDNK2 label{color:var(--gray-600);display:block;font-size:11px;margin:8px 0 2px}.VectorEditor-module_dialog__NDNK2 input,.VectorEditor-module_dialog__NDNK2 select,.VectorEditor-module_dialog__NDNK2 textarea{background:var(--gray-950);border:1px solid var(--gray-850);border-radius:4px;color:var(--gray-200);font-size:12px;padding:4px 8px;width:100%}.VectorEditor-module_dialog__NDNK2 textarea{font-family:monospace;min-height:120px;resize:vertical}.VectorEditor-module_dialogActions__0Sy4X{display:flex;gap:8px;justify-content:flex-end;margin-top:16px}.VectorEditor-module_dialogActions__0Sy4X button{border:none;border-radius:4px;cursor:pointer;font-size:12px;padding:4px 16px}.VectorEditor-module_btnPrimary__f9AaS{background:var(--editor-accent);color:var(--color-white)}.VectorEditor-module_btnPrimary__f9AaS:hover{background:#67d}.VectorEditor-module_btnSecondary__wDps2{background:var(--gray-850);color:var(--gray-500)}.VectorEditor-module_btnSecondary__wDps2:hover{background:var(--gray-800);color:var(--gray-200)}.VectorEditor-module_handleGroup__sMkQj circle{fill:var(--editor-accent);stroke:var(--color-white);stroke-width:1;cursor:pointer}.VectorEditor-module_handleGroup__sMkQj circle:hover{fill:#78e}.PhotoEditor-module_wrapper__jrHYj{background:#1a1a1e;border-radius:12px;color:#eee;display:flex;flex-direction:column;font-family:Segoe UI,sans-serif;font-size:13px;max-height:85vh;overflow:hidden;width:100%}.PhotoEditor-module_loadingWrap__QUTon{align-items:center;color:#aaa;display:flex;justify-content:center;min-height:400px;width:100%}.PhotoEditor-module_mainContent__TCVxf{display:flex;flex:1;min-height:0;overflow:hidden}.PhotoEditor-module_toolbar__RY-Ty{align-items:center;background:#222226;border-bottom:1px solid #333;display:flex;justify-content:space-between;padding:8px 14px}.PhotoEditor-module_toolbarGroup__PXw0-{display:flex;gap:6.5px}.PhotoEditor-module_toolbarDivider__o3kFV{background:#444;margin:0 4px;width:1px}.PhotoEditor-module_toolbarTitle__P1o18{font-size:14px;font-weight:700}.PhotoEditor-module_leftPanel__DnHLU{background:#222226;border-right:1px solid #333;display:flex;flex-direction:column;min-width:280px;overflow:hidden;width:280px}.PhotoEditor-module_tabBar__DZ3MG{border-bottom:1px solid #333;display:flex;flex-wrap:wrap}.PhotoEditor-module_tabButton__BLi97{align-items:center;background:transparent;border:none;border-bottom:2px solid transparent;color:#888;cursor:pointer;display:flex;flex:1 0 auto;flex-direction:column;font-size:10px;font-weight:600;gap:1px;min-width:34px;padding:8px 0;transition:all .15s}.PhotoEditor-module_tabButtonActive__KlQG0{background:#2a2a30}.PhotoEditor-module_tabIcon__-Mq19{font-size:14px}.PhotoEditor-module_panelContent__l5i5t{flex:1;overflow-y:auto;padding:10px 12px}.PhotoEditor-module_sectionTitle__tMvCm{font-size:12px;font-weight:600;margin-bottom:6px}.PhotoEditor-module_sectionTitleMb8__PQ-lV{margin-bottom:8px}.PhotoEditor-module_sectionInfo__bWxW5{color:#aaa;font-size:11px}.PhotoEditor-module_sectionInfoMb__Hk6V-{margin-bottom:10px}.PhotoEditor-module_pillRow__DGJUb{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:10px}.PhotoEditor-module_pillRowMb8__AQrth{margin-bottom:8px}.PhotoEditor-module_pillRowGap3__Y46Vu{display:flex;flex-wrap:wrap;gap:3px;margin-bottom:8px}.PhotoEditor-module_pill__wTFac{background:transparent;border:1px solid #444;border-radius:12px;color:#aaa;cursor:pointer;font-size:11px;font-weight:600;padding:3px 10px}.PhotoEditor-module_pillActive__AfdZR{color:#fff}.PhotoEditor-module_pillCrop__Nsisp{border-radius:6px;padding:4px 12px}.PhotoEditor-module_pillCropActive__p6csO{color:#fff}.PhotoEditor-module_pillEmoji__I42DJ{border-radius:10px;padding:2px 8px}.PhotoEditor-module_pillEmojiActive__0-EM7{color:#fff}.PhotoEditor-module_filterGrid__-29PS{display:grid;gap:6px;grid-template-columns:repeat(3,1fr)}.PhotoEditor-module_emojiGrid__whqqK{display:grid;gap:2px;grid-template-columns:repeat(6,1fr);max-height:260px;overflow-y:auto}.PhotoEditor-module_shapeGrid__TawIy{margin-bottom:16px}.PhotoEditor-module_frameGrid__R09dd,.PhotoEditor-module_shapeGrid__TawIy{display:grid;gap:4px;grid-template-columns:repeat(5,1fr)}.PhotoEditor-module_sliderRow__jsWDQ{align-items:center;display:flex;gap:6px;margin-bottom:8px}.PhotoEditor-module_sliderLabel__zOZ49{color:#aaa;font-size:11px}.PhotoEditor-module_sliderLabelSelf__EwYKU{align-self:center;margin-right:4px}.PhotoEditor-module_sliderValue__qFuTw{font-size:11px;font-weight:600;min-width:28px}.PhotoEditor-module_sliderValueSm__U7FrJ{font-size:10px;min-width:28px}.PhotoEditor-module_adjustColumn__y---T{display:flex;flex-direction:column;gap:8px}.PhotoEditor-module_adjustHeader__6s9zV{display:flex;font-size:11px;justify-content:space-between;margin-bottom:2px}.PhotoEditor-module_adjustIcon__d56rY{text-align:center;width:14px}.PhotoEditor-module_adjustValue__aUUmg{cursor:pointer;font-weight:600;min-width:30px;text-align:right}.PhotoEditor-module_intensitySection__dhe5h{margin-top:12px;padding:8px 0}.PhotoEditor-module_intensityHeader__-KKu6{display:flex;font-size:11px;justify-content:space-between;margin-bottom:4px}.PhotoEditor-module_colorInput__xkF1h{border:none;cursor:pointer;height:28px;padding:0;width:28px}.PhotoEditor-module_colorInputLg__W2KrK{border:none;cursor:pointer;height:30px;padding:0;width:32px}.PhotoEditor-module_colorInputDraw__KYcdG{border:none;cursor:pointer;height:28px;padding:0;width:32px}.PhotoEditor-module_overlayToolbar__hfspp{border-bottom:1px solid #333;display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px;padding:6px 0}.PhotoEditor-module_overlayToolbarLabel__mc4pU{align-self:center;color:#aaa;font-size:11px;margin-right:4px}.PhotoEditor-module_overlayToolbarBtn__AdTmZ{font-size:11px;padding:2px 6px}.PhotoEditor-module_overlaySection__IIl4r{border-top:1px solid #333;margin-top:12px;padding-top:8px}.PhotoEditor-module_overlaySectionTitle__FRx3e{color:#aaa;font-size:11px;font-weight:600;margin-bottom:4px}.PhotoEditor-module_overlayItem__DGUCN{align-items:center;background:transparent;border-radius:4px;color:#ccc;cursor:pointer;display:flex;font-size:11px;gap:6px;margin-bottom:2px;padding:3px 6px}.PhotoEditor-module_overlayIcon__G0pFk{text-align:center;width:18px}.PhotoEditor-module_overlayName__JVh64{flex:1;overflow:hidden;text-overflow:ellipsis;white-space:nowrap}.PhotoEditor-module_overlayDeleteBtn__Ontxv{background:none;border:none;color:#f55;cursor:pointer;font-size:11px;padding:0}.PhotoEditor-module_emojiBtn__jxG9m{background:transparent;border:none;border-radius:6px;cursor:pointer;font-size:22px;line-height:1;padding:4px 0}.PhotoEditor-module_shapeBtn__xZdSV{font-size:20px}.PhotoEditor-module_frameBtn__coMkZ,.PhotoEditor-module_shapeBtn__xZdSV{background:transparent;border:1px solid #444;border-radius:6px;color:#eee;cursor:pointer;line-height:1;padding:6px 0}.PhotoEditor-module_frameBtn__coMkZ{font-size:18px}.PhotoEditor-module_removeFrameBtn__oCuua{background:transparent;border:1px solid #444;border-radius:6px;color:#f55;cursor:pointer;font-size:14px;padding:6px 0}.PhotoEditor-module_textFormatBtn__7Z9RJ{min-width:32px}.PhotoEditor-module_textFormatBtnSm__3ptcG{min-width:28px}.PhotoEditor-module_drawActionBtn__teYz4{flex:1}.PhotoEditor-module_textArea__sBGlB{background:#2a2a30;border:1px solid #444;border-radius:6px;color:#eee;font-size:13px;margin-bottom:8px;resize:none}.PhotoEditor-module_textAreaSm__6xZnY{font-size:12px;margin-bottom:0}.PhotoEditor-module_textBtnRow__AcEnd{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px}.PhotoEditor-module_textGapRow__Dq2uz{display:flex;gap:4px;margin-top:6px}.PhotoEditor-module_editSelectedSection__bgNEh{border-top:1px solid #333;margin-top:12px;padding-top:8px}.PhotoEditor-module_editSelectedLabel__u2rmS{color:#aaa;font-size:11px;margin-bottom:4px}.PhotoEditor-module_shapeColorRow__ip5--{display:flex;flex-wrap:wrap;gap:4px;margin-bottom:8px}.PhotoEditor-module_shapeColorLabel__nVcbU{align-self:center;color:#aaa;font-size:11px;margin-right:2px}.PhotoEditor-module_shapeColorLabelMl__KiM2d{margin-left:4px}.PhotoEditor-module_shapeFillToggle__BXJ8C{font-size:10px;padding:2px 6px}.PhotoEditor-module_frameColorRow__KRAHz{display:flex;gap:4px;margin-bottom:8px}.PhotoEditor-module_frameThicknessWrap__lXCoC{align-items:center;display:flex;flex:1;gap:4px}.PhotoEditor-module_frameThicknessValue__SAEuc{font-size:10px}.PhotoEditor-module_drawPreview__WPbiv{display:flex;justify-content:center;margin-bottom:12px}.PhotoEditor-module_drawActionRow__CUSWS{display:flex;gap:4px}.PhotoEditor-module_quickColorRow__DTy5E{align-items:center;display:flex;gap:6px;margin-bottom:8px}.PhotoEditor-module_quickColorSwatch__ZjgoA{border:1px solid #555;border-radius:3px;cursor:pointer;height:18px;width:18px}.PhotoEditor-module_transformRow__LKRjS{display:flex;gap:6px;margin-bottom:16px}.PhotoEditor-module_transformZoomRow__h2NlB{align-items:center;display:flex;gap:8px}.PhotoEditor-module_transformZoomValue__LXa51{font-size:11px;font-weight:600;min-width:40px}.PhotoEditor-module_transformInfo__zXP9l{background:#2a2a30;border-radius:8px;color:#aaa;font-size:11px;margin-top:16px;padding:10px}.PhotoEditor-module_canvasViewport__OMBIL{align-items:center;background:#111115;display:flex;flex:1;justify-content:center;overflow:auto;padding:20px;position:relative}.PhotoEditor-module_zoomWrap__JjfiJ{max-height:100%;max-width:100%;position:relative;transform-origin:center center;transition:transform .15s ease}.PhotoEditor-module_compareWrap__-J5ku{cursor:ew-resize;display:inline-block;position:relative}.PhotoEditor-module_canvasOriginal__Apf91{max-width:100%}.PhotoEditor-module_canvasEdited__Eroz7,.PhotoEditor-module_canvasOriginal__Apf91{display:block;max-height:60vh;object-fit:contain}.PhotoEditor-module_compareClip__5qG2I{bottom:0;left:0;overflow:hidden;position:absolute;top:0}.PhotoEditor-module_compareSlider__OIIIK{bottom:0;position:absolute;top:0;transform:translateX(-50%);width:3px}.PhotoEditor-module_compareSliderKnob__VohI9{align-items:center;border-radius:50%;box-shadow:0 2px 8px rgba(0,0,0,.4);display:flex;height:28px;justify-content:center;left:50%;position:absolute;top:50%;transform:translate(-50%,-50%);width:28px}.PhotoEditor-module_compareSliderIcon__pXcct{color:#fff;font-size:12px}.PhotoEditor-module_compareLabelOriginal__GaBoj{background:rgba(0,0,0,.6);left:8px}.PhotoEditor-module_compareLabelEdited__Fr836,.PhotoEditor-module_compareLabelOriginal__GaBoj{border-radius:4px;color:#fff;font-size:11px;font-weight:600;padding:2px 8px;position:absolute;top:8px}.PhotoEditor-module_compareLabelEdited__Fr836{right:8px}.PhotoEditor-module_regularWrap__8umPV{display:inline-block;position:relative}.PhotoEditor-module_canvasRegular__wxapL{border-radius:6px;box-shadow:0 4px 20px rgba(0,0,0,.4);display:block;max-height:60vh;max-width:100%;object-fit:contain}.PhotoEditor-module_cropOverlay__MJk1Y{inset:0;pointer-events:none;position:absolute;z-index:2}.PhotoEditor-module_cropDarkBg__m3axV{background:rgba(0,0,0,.55);inset:0;position:absolute}.PhotoEditor-module_cropGridContainer__NfHdT{inset:0;position:absolute}.PhotoEditor-module_cropSizeLabel__fV2mF{background:rgba(0,0,0,.75);border-radius:3px;bottom:-24px;color:#fff;font-size:10px;left:50%;padding:2px 8px;position:absolute;transform:translateX(-50%);white-space:nowrap}.PhotoEditor-module_cropInfo__Z1SCE{color:#aaa;font-size:11px;margin-bottom:10px}.PhotoEditor-module_cropAspectLabel__dieL-{font-size:12px;font-weight:600;margin-bottom:6px}.PhotoEditor-module_cropAspectRow__scRj3{display:flex;flex-wrap:wrap;gap:4px}.PhotoEditor-module_accentBtn__tgaEx{color:#fff;font-weight:600;width:100%}.GameAsset2dEditor-module_root__WVJBM{background:#1a1a2e;color:#e0e0e0;display:flex;flex-direction:column;font-family:-apple-system,BlinkMacSystemFont,Segoe UI,Roboto,sans-serif;font-size:13px;height:100%;min-height:600px;user-select:none}.GameAsset2dEditor-module_menuBar__WaEaU{align-items:center;background:#16213e;border-bottom:1px solid #0f3460;display:flex;gap:8px;padding:6px 12px}.GameAsset2dEditor-module_menuBar__WaEaU h3{color:#ffd369;font-size:14px;font-weight:600;margin:0}.GameAsset2dEditor-module_menuGroup__EOreB{display:flex;gap:2px}.GameAsset2dEditor-module_menuBtn__JYWXn{align-items:center;background:transparent;border:none;border-radius:4px;color:#b0b0b0;cursor:pointer;display:flex;font-size:12px;gap:4px;padding:4px 8px;transition:all .15s}.GameAsset2dEditor-module_menuBtn__JYWXn:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_menuBtn__JYWXn:disabled{cursor:not-allowed;opacity:.4}.GameAsset2dEditor-module_spacer__fPVeq{flex:1}.GameAsset2dEditor-module_modeTabs__iKh7C{background:#1f2940;border-bottom:1px solid #0f3460;display:flex;gap:2px;padding:4px 12px}.GameAsset2dEditor-module_modeTab__C12zt{background:transparent;border:none;border-radius:4px 4px 0 0;color:#8892a8;cursor:pointer;font-size:12px;font-weight:500;padding:6px 16px;transition:all .15s}.GameAsset2dEditor-module_modeTab__C12zt:hover{background:hsla(0,0%,100%,.05);color:#c0c8d8}.GameAsset2dEditor-module_modeTab__C12zt.GameAsset2dEditor-module_active__DUroI{background:#1a1a2e;color:#ffd369}.GameAsset2dEditor-module_mainArea__jwDUa{display:flex;flex:1;overflow:hidden}.GameAsset2dEditor-module_leftPanel__xxAg5{background:#16213e;border-right:1px solid #0f3460;display:flex;flex-direction:column;overflow:hidden;width:220px}.GameAsset2dEditor-module_centerArea__xr-Hn{display:flex;flex:1;flex-direction:column;overflow:hidden}.GameAsset2dEditor-module_rightPanel__YoNuc{background:#16213e;border-left:1px solid #0f3460;display:flex;flex-direction:column;overflow:hidden;width:260px}.GameAsset2dEditor-module_toolbar__hEC9S{align-items:center;background:#1f2940;border-bottom:1px solid #0f3460;display:flex;gap:8px;padding:6px 12px}.GameAsset2dEditor-module_toolGroup__Zbn47{background:rgba(0,0,0,.2);border-radius:4px;display:flex;gap:2px;padding:2px}.GameAsset2dEditor-module_toolBtn__5U7Rw{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;font-size:14px;height:28px;justify-content:center;transition:all .15s;width:28px}.GameAsset2dEditor-module_toolBtn__5U7Rw:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_toolBtn__5U7Rw.GameAsset2dEditor-module_active__DUroI{background:#0f3460;color:#ffd369}.GameAsset2dEditor-module_toolBtn__5U7Rw:disabled{cursor:not-allowed;opacity:.3}.GameAsset2dEditor-module_viewport__vEKEv{background:#0a0a14;flex:1;overflow:hidden;position:relative}.GameAsset2dEditor-module_viewportCanvas__FJ5qA{image-rendering:pixelated;image-rendering:crisp-edges;left:50%;position:absolute;top:50%}.GameAsset2dEditor-module_gridOverlay__K8B97{bottom:0;left:0;pointer-events:none;position:absolute;right:0;top:0}.GameAsset2dEditor-module_panelHeader__xm2As{align-items:center;background:#0f3460;color:#8892a8;display:flex;font-size:11px;font-weight:600;justify-content:space-between;letter-spacing:.5px;padding:8px 12px;text-transform:uppercase}.GameAsset2dEditor-module_panelContent__dvOGq{flex:1;overflow-y:auto;padding:8px}.GameAsset2dEditor-module_panelSection__RQQDr{margin-bottom:16px}.GameAsset2dEditor-module_panelLabel__Ks-Wa{color:#8892a8;display:block;font-size:11px;letter-spacing:.5px;margin-bottom:6px;text-transform:uppercase}.GameAsset2dEditor-module_panelInput__cxNiG{background:#0a0a14;border:1px solid #2a3a5e;border-radius:4px;color:#e0e0e0;font-size:12px;padding:6px 8px;width:100%}.GameAsset2dEditor-module_panelInput__cxNiG:focus{border-color:#ffd369;outline:none}.GameAsset2dEditor-module_tilePalette__OpzmV{display:grid;gap:4px;grid-template-columns:repeat(auto-fill,minmax(40px,1fr));padding:8px}.GameAsset2dEditor-module_tileItem__uWNS9{aspect-ratio:1;background:#0a0a14;border:2px solid transparent;border-radius:4px;cursor:pointer;overflow:hidden;transition:all .15s}.GameAsset2dEditor-module_tileItem__uWNS9:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_tileItem__uWNS9.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_tileItem__uWNS9 img{height:100%;image-rendering:pixelated;object-fit:contain;width:100%}.GameAsset2dEditor-module_layersList__anFaG{display:flex;flex-direction:column;gap:2px}.GameAsset2dEditor-module_layerItem__XSGlu{align-items:center;background:#1f2940;border-radius:4px;cursor:pointer;display:flex;gap:8px;padding:6px 8px;transition:all .15s}.GameAsset2dEditor-module_layerItem__XSGlu:hover{background:#2a3a5e}.GameAsset2dEditor-module_layerItem__XSGlu.GameAsset2dEditor-module_selected__216IN{background:#0f3460;border-left:3px solid #ffd369}.GameAsset2dEditor-module_layerVisibility__RpHjV{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_layerVisibility__RpHjV:hover{background:hsla(0,0%,100%,.1)}.GameAsset2dEditor-module_layerVisibility__RpHjV.GameAsset2dEditor-module_hidden__mukOG{opacity:.4}.GameAsset2dEditor-module_layerName__WBxq5{color:#c0c8d8;flex:1;font-size:12px}.GameAsset2dEditor-module_layerOpacity__FpzL-{color:#8892a8;font-size:10px;text-align:right;width:40px}.GameAsset2dEditor-module_framesList__vg1oO{display:grid;gap:8px;grid-template-columns:repeat(auto-fill,minmax(60px,1fr));padding:8px}.GameAsset2dEditor-module_frameItem__fkEfb{aspect-ratio:1;background:#0a0a14;border:2px solid transparent;border-radius:4px;cursor:pointer;overflow:hidden;position:relative;transition:all .15s}.GameAsset2dEditor-module_frameItem__fkEfb:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_frameItem__fkEfb.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_frameItem__fkEfb canvas{height:100%;image-rendering:pixelated;object-fit:contain;width:100%}.GameAsset2dEditor-module_frameLabel__5IGW8{background:rgba(0,0,0,.7);bottom:0;color:#b0b0b0;font-size:9px;left:0;padding:2px 4px;position:absolute;right:0;text-align:center}.GameAsset2dEditor-module_timeline__dPJk6{background:#16213e;border-top:1px solid #0f3460;padding:8px}.GameAsset2dEditor-module_timelineTrack__mr20w{background:#0a0a14;border-radius:4px;display:flex;gap:4px;overflow-x:auto;padding:4px}.GameAsset2dEditor-module_timelineFrame__AQyGe{background:#1f2940;border:2px solid transparent;border-radius:4px;cursor:pointer;flex-shrink:0;height:48px;overflow:hidden;width:48px}.GameAsset2dEditor-module_timelineFrame__AQyGe:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_timelineFrame__AQyGe.GameAsset2dEditor-module_current__3sAfL{border-color:#ffd369}.GameAsset2dEditor-module_stateGraph__qAWlU{background:#0a0a14;flex:1;overflow:hidden;position:relative}.GameAsset2dEditor-module_stateNode__W9Z-g{background:#1f2940;border:2px solid #2a3a5e;border-radius:8px;cursor:move;min-width:120px;padding:8px 12px;position:absolute;transition:border-color .15s}.GameAsset2dEditor-module_stateNode__W9Z-g:hover{border-color:#4a5a7e}.GameAsset2dEditor-module_stateNode__W9Z-g.GameAsset2dEditor-module_selected__216IN{border-color:#ffd369}.GameAsset2dEditor-module_stateNode__W9Z-g.GameAsset2dEditor-module_entry__cmA9n{border-color:#4ade80}.GameAsset2dEditor-module_stateNodeName__TK5vs{color:#e0e0e0;font-size:12px;font-weight:500;text-align:center}.GameAsset2dEditor-module_stateNodeAnim__VGwnV{color:#8892a8;font-size:10px;margin-top:4px;text-align:center}.GameAsset2dEditor-module_transition__FBbno{stroke:#4a5a7e;stroke-width:2;fill:none;marker-end:url(#arrowhead)}.GameAsset2dEditor-module_transition__FBbno:hover{stroke:#ffd369}.GameAsset2dEditor-module_effectsList__vHq4I{display:flex;flex-direction:column;gap:8px}.GameAsset2dEditor-module_effectItem__6-1li{background:#1f2940;border-radius:6px;overflow:hidden}.GameAsset2dEditor-module_effectHeader__cgVN-{align-items:center;cursor:pointer;display:flex;gap:8px;padding:8px}.GameAsset2dEditor-module_effectToggle__lKE36{background:#0a0a14;border:1px solid #2a3a5e;border-radius:3px;cursor:pointer;height:18px;width:18px}.GameAsset2dEditor-module_effectToggle__lKE36.GameAsset2dEditor-module_enabled__wgDzp{background:#ffd369;border-color:#ffd369}.GameAsset2dEditor-module_effectName__NQCWj{color:#c0c8d8;flex:1;font-size:12px}.GameAsset2dEditor-module_effectRemove__TSSdI{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_effectRemove__TSSdI:hover{background:#ef4444;color:#fff}.GameAsset2dEditor-module_effectParams__UqTBd{background:rgba(0,0,0,.2);padding:8px}.GameAsset2dEditor-module_effectParam__hEsVY{align-items:center;display:flex;gap:8px;margin-bottom:8px}.GameAsset2dEditor-module_effectParam__hEsVY:last-child{margin-bottom:0}.GameAsset2dEditor-module_effectParamLabel__u0Qoc{color:#8892a8;flex:0 0 80px;font-size:11px}.GameAsset2dEditor-module_effectParamInput__aqxdv{background:#0a0a14;border:1px solid #2a3a5e;border-radius:3px;color:#e0e0e0;flex:1;font-size:11px;height:24px;padding:0 8px}.GameAsset2dEditor-module_statusBar__eOrNe{align-items:center;background:#0f3460;color:#8892a8;display:flex;font-size:11px;gap:16px;padding:4px 12px}.GameAsset2dEditor-module_statusItem__kKLHF{align-items:center;display:flex;gap:4px}.GameAsset2dEditor-module_zoomControl__4YD9G{align-items:center;display:flex;gap:4px;margin-left:auto}.GameAsset2dEditor-module_zoomBtn__hxYik{align-items:center;background:transparent;border:none;border-radius:3px;color:#8892a8;cursor:pointer;display:flex;height:20px;justify-content:center;width:20px}.GameAsset2dEditor-module_zoomBtn__hxYik:hover{background:hsla(0,0%,100%,.1);color:#fff}.GameAsset2dEditor-module_dialogOverlay__dZYwO{align-items:center;background:rgba(0,0,0,.6);bottom:0;display:flex;justify-content:center;left:0;position:fixed;right:0;top:0;z-index:1000}.GameAsset2dEditor-module_dialog__mfLFL{background:#16213e;border-radius:8px;box-shadow:0 8px 32px rgba(0,0,0,.4);max-width:500px;min-width:300px;padding:24px}.GameAsset2dEditor-module_dialog__mfLFL h3{color:#ffd369;font-size:16px;margin:0 0 16px}.GameAsset2dEditor-module_dialogActions__vhDXe{display:flex;gap:8px;justify-content:flex-end;margin-top:20px}.GameAsset2dEditor-module_btnPrimary__Gzc25{background:#ffd369;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;font-size:12px;font-weight:600;padding:8px 16px;transition:all .15s}.GameAsset2dEditor-module_btnPrimary__Gzc25:hover{background:#ffe599}.GameAsset2dEditor-module_btnSecondary__G5nK5{background:transparent;border:1px solid #4a5a7e;border-radius:4px;color:#c0c8d8;cursor:pointer;font-size:12px;padding:8px 16px;transition:all .15s}.GameAsset2dEditor-module_btnSecondary__G5nK5:hover{background:hsla(0,0%,100%,.05);border-color:#6a7a9e}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar{width:6px}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-track{background:#0a0a14}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-thumb{background:#2a3a5e;border-radius:3px}.GameAsset2dEditor-module_panelContent__dvOGq::-webkit-scrollbar-thumb:hover{background:#4a5a7e}.GameAsset2dEditor-module_dropZone__Z7sYz{border:2px dashed #4a5a7e;border-radius:8px;color:#8892a8;cursor:pointer;padding:24px;text-align:center;transition:all .15s}.GameAsset2dEditor-module_dropZone__Z7sYz:hover{border-color:#ffd369;color:#c0c8d8}.GameAsset2dEditor-module_dropZone__Z7sYz.GameAsset2dEditor-module_active__DUroI{background:rgba(255,211,105,.1);border-color:#ffd369}.GameAsset2dEditor-module_emptyState__3wryk{align-items:center;color:#8892a8;display:flex;flex-direction:column;justify-content:center;padding:32px;text-align:center}.GameAsset2dEditor-module_emptyState__3wryk svg{height:48px;margin-bottom:12px;opacity:.5;width:48px}.GameAsset2dEditor-module_emptyStateText__Q5V1a{font-size:12px;margin-bottom:12px}
@@ -0,0 +1,439 @@
1
+ import { jsxs, jsx } from 'react/jsx-runtime';
2
+ import { useState, useCallback } from 'react';
3
+
4
+ function luminance(r, g, b) {
5
+ return 0.299 * r + 0.587 * g + 0.114 * b;
6
+ }
7
+ /**
8
+ * Auto-colorize a grayscale image using heuristic color mapping.
9
+ * Maps luminance regions to plausible colors (sky-blue for bright areas,
10
+ * earth tones for dark areas, greens for mid-tones).
11
+ */
12
+ function autoColorize(source, options) {
13
+ const { intensity, temperature, saturation } = options;
14
+ const result = new ImageData(new Uint8ClampedArray(source.data), source.width, source.height);
15
+ const data = result.data;
16
+ // Temperature bias
17
+ const tempBias = temperature === 'warm' ? [20, 5, -15] : temperature === 'cool' ? [-10, 0, 15] : [0, 0, 0];
18
+ for (let i = 0; i < data.length; i += 4) {
19
+ const lum = luminance(data[i], data[i + 1], data[i + 2]);
20
+ const isGray = Math.abs(data[i] - data[i + 1]) < 15 && Math.abs(data[i + 1] - data[i + 2]) < 15;
21
+ if (isGray) {
22
+ // Map grayscale to heuristic colors based on luminance
23
+ let cr, cg, cb;
24
+ if (lum > 200) {
25
+ // Very bright → sky blue / white
26
+ cr = 200 + (lum - 200) * 0.8;
27
+ cg = 210 + (lum - 200) * 0.6;
28
+ cb = 230;
29
+ }
30
+ else if (lum > 140) {
31
+ // Upper mid → warm tones
32
+ cr = lum * 1.05;
33
+ cg = lum * 0.95;
34
+ cb = lum * 0.85;
35
+ }
36
+ else if (lum > 80) {
37
+ // Mid tones → greenish
38
+ cr = lum * 0.85;
39
+ cg = lum * 1.1;
40
+ cb = lum * 0.8;
41
+ }
42
+ else {
43
+ // Dark → earth/brown
44
+ cr = lum * 1.15;
45
+ cg = lum * 0.9;
46
+ cb = lum * 0.7;
47
+ }
48
+ // Apply temperature bias
49
+ cr = Math.max(0, Math.min(255, cr + tempBias[0]));
50
+ cg = Math.max(0, Math.min(255, cg + tempBias[1]));
51
+ cb = Math.max(0, Math.min(255, cb + tempBias[2]));
52
+ // Apply saturation
53
+ const avg = (cr + cg + cb) / 3;
54
+ cr = avg + (cr - avg) * saturation;
55
+ cg = avg + (cg - avg) * saturation;
56
+ cb = avg + (cb - avg) * saturation;
57
+ // Blend with original based on intensity
58
+ data[i] = Math.max(0, Math.min(255, data[i] * (1 - intensity) + cr * intensity));
59
+ data[i + 1] = Math.max(0, Math.min(255, data[i + 1] * (1 - intensity) + cg * intensity));
60
+ data[i + 2] = Math.max(0, Math.min(255, data[i + 2] * (1 - intensity) + cb * intensity));
61
+ }
62
+ }
63
+ return result;
64
+ }
65
+ /**
66
+ * Remove background using edge-based foreground detection.
67
+ * Uses Sobel edge detection + flood fill from edges to find background.
68
+ */
69
+ function removeBackground(source, options) {
70
+ const { threshold, iterations, featherRadius, replacementColor } = options;
71
+ const w = source.width;
72
+ const h = source.height;
73
+ const result = new ImageData(new Uint8ClampedArray(source.data), w, h);
74
+ const data = result.data;
75
+ // 1. Compute edge magnitude (Sobel)
76
+ const edges = new Float32Array(w * h);
77
+ for (let y = 1; y < h - 1; y++) {
78
+ for (let x = 1; x < w - 1; x++) {
79
+ const idx = (y * w + x) * 4;
80
+ const tl = luminance(source.data[idx - w * 4 - 4], source.data[idx - w * 4 - 3], source.data[idx - w * 4 - 2]);
81
+ const tc = luminance(source.data[idx - w * 4], source.data[idx - w * 4 + 1], source.data[idx - w * 4 + 2]);
82
+ const tr = luminance(source.data[idx - w * 4 + 4], source.data[idx - w * 4 + 5], source.data[idx - w * 4 + 6]);
83
+ const ml = luminance(source.data[idx - 4], source.data[idx - 3], source.data[idx - 2]);
84
+ const mr = luminance(source.data[idx + 4], source.data[idx + 5], source.data[idx + 6]);
85
+ const bl = luminance(source.data[idx + w * 4 - 4], source.data[idx + w * 4 - 3], source.data[idx + w * 4 - 2]);
86
+ const bc = luminance(source.data[idx + w * 4], source.data[idx + w * 4 + 1], source.data[idx + w * 4 + 2]);
87
+ const br = luminance(source.data[idx + w * 4 + 4], source.data[idx + w * 4 + 5], source.data[idx + w * 4 + 6]);
88
+ const gx = -tl - 2 * ml - bl + tr + 2 * mr + br;
89
+ const gy = -tl - 2 * tc - tr + bl + 2 * bc + br;
90
+ edges[y * w + x] = Math.sqrt(gx * gx + gy * gy) / 255;
91
+ }
92
+ }
93
+ // 2. Create foreground mask from edge density
94
+ const mask = new Float32Array(w * h);
95
+ const edgeThreshold = threshold * 0.5;
96
+ // Mark edges as definite foreground
97
+ for (let i = 0; i < edges.length; i++) {
98
+ mask[i] = edges[i] > edgeThreshold ? 1 : 0;
99
+ }
100
+ // 3. Dilate foreground mask (iterations)
101
+ for (let iter = 0; iter < iterations; iter++) {
102
+ const temp = new Float32Array(mask);
103
+ for (let y = 1; y < h - 1; y++) {
104
+ for (let x = 1; x < w - 1; x++) {
105
+ const idx = y * w + x;
106
+ if (temp[idx] > 0)
107
+ continue;
108
+ // Check 4-neighbors
109
+ if (temp[idx - 1] > 0 || temp[idx + 1] > 0 || temp[idx - w] > 0 || temp[idx + w] > 0) {
110
+ // Check color similarity with neighbor
111
+ const pi = idx * 4;
112
+ let isFg = false;
113
+ for (const ni of [idx - 1, idx + 1, idx - w, idx + w]) {
114
+ if (temp[ni] > 0) {
115
+ const npi = ni * 4;
116
+ const diff = (Math.abs(source.data[pi] - source.data[npi]) +
117
+ Math.abs(source.data[pi + 1] - source.data[npi + 1]) +
118
+ Math.abs(source.data[pi + 2] - source.data[npi + 2])) / 3;
119
+ if (diff < threshold * 255) {
120
+ isFg = true;
121
+ break;
122
+ }
123
+ }
124
+ }
125
+ if (isFg)
126
+ mask[idx] = 1;
127
+ }
128
+ }
129
+ }
130
+ }
131
+ // 4. Flood fill from border pixels as background (anything not foreground and reachable from edge)
132
+ const visited = new Uint8Array(w * h);
133
+ const queue = [];
134
+ // Seed from border
135
+ for (let x = 0; x < w; x++) {
136
+ if (mask[x] === 0) {
137
+ queue.push(x);
138
+ visited[x] = 1;
139
+ }
140
+ const bi = (h - 1) * w + x;
141
+ if (mask[bi] === 0) {
142
+ queue.push(bi);
143
+ visited[bi] = 1;
144
+ }
145
+ }
146
+ for (let y = 0; y < h; y++) {
147
+ const li = y * w;
148
+ if (mask[li] === 0) {
149
+ queue.push(li);
150
+ visited[li] = 1;
151
+ }
152
+ const ri = y * w + w - 1;
153
+ if (mask[ri] === 0) {
154
+ queue.push(ri);
155
+ visited[ri] = 1;
156
+ }
157
+ }
158
+ // BFS flood fill
159
+ let head = 0;
160
+ while (head < queue.length) {
161
+ const idx = queue[head++];
162
+ const x = idx % w;
163
+ const y = (idx - x) / w;
164
+ for (const [dx, dy] of [[0, -1], [0, 1], [-1, 0], [1, 0]]) {
165
+ const nx = x + dx;
166
+ const ny = y + dy;
167
+ if (nx < 0 || nx >= w || ny < 0 || ny >= h)
168
+ continue;
169
+ const ni = ny * w + nx;
170
+ if (visited[ni] || mask[ni] > 0)
171
+ continue;
172
+ visited[ni] = 1;
173
+ queue.push(ni);
174
+ }
175
+ }
176
+ // 5. Apply mask with optional feathering
177
+ const replacement = replacementColor ? hexToRGB(replacementColor) : null;
178
+ for (let i = 0; i < w * h; i++) {
179
+ let alpha = visited[i] ? 0 : 1; // background = 0, foreground = 1
180
+ // Feather edges
181
+ if (featherRadius > 0 && alpha > 0) {
182
+ const x = i % w;
183
+ const y = (i - x) / w;
184
+ let minDistSq = featherRadius * featherRadius + 1;
185
+ for (let fy = -featherRadius; fy <= featherRadius; fy++) {
186
+ for (let fx = -featherRadius; fx <= featherRadius; fx++) {
187
+ const nx = x + fx;
188
+ const ny = y + fy;
189
+ if (nx >= 0 && nx < w && ny >= 0 && ny < h) {
190
+ if (visited[ny * w + nx]) {
191
+ const d = fx * fx + fy * fy;
192
+ if (d < minDistSq)
193
+ minDistSq = d;
194
+ }
195
+ }
196
+ }
197
+ }
198
+ if (minDistSq <= featherRadius * featherRadius) {
199
+ alpha = Math.sqrt(minDistSq) / featherRadius;
200
+ }
201
+ }
202
+ const pi = i * 4;
203
+ if (replacement) {
204
+ data[pi] = Math.round(data[pi] * alpha + replacement[0] * (1 - alpha));
205
+ data[pi + 1] = Math.round(data[pi + 1] * alpha + replacement[1] * (1 - alpha));
206
+ data[pi + 2] = Math.round(data[pi + 2] * alpha + replacement[2] * (1 - alpha));
207
+ }
208
+ else {
209
+ data[pi + 3] = Math.round(alpha * 255);
210
+ }
211
+ }
212
+ return result;
213
+ }
214
+ function hexToRGB(hex) {
215
+ const h = hex.replace('#', '');
216
+ return [parseInt(h.slice(0, 2), 16), parseInt(h.slice(2, 4), 16), parseInt(h.slice(4, 6), 16)];
217
+ }
218
+ /**
219
+ * Upscale image using Lanczos interpolation.
220
+ */
221
+ function upscaleImage(source, options) {
222
+ const { scale, sharpen } = options;
223
+ const sw = source.width;
224
+ const sh = source.height;
225
+ const dw = sw * scale;
226
+ const dh = sh * scale;
227
+ const result = new ImageData(dw, dh);
228
+ const srcData = source.data;
229
+ const dstData = result.data;
230
+ // Lanczos kernel
231
+ const a = 3; // Lanczos-3
232
+ function lanczos(x) {
233
+ if (x === 0)
234
+ return 1;
235
+ if (Math.abs(x) >= a)
236
+ return 0;
237
+ const pix = Math.PI * x;
238
+ return (a * Math.sin(pix) * Math.sin(pix / a)) / (pix * pix);
239
+ }
240
+ // Bicubic Lanczos resampling
241
+ for (let dy = 0; dy < dh; dy++) {
242
+ const sy = (dy + 0.5) / scale - 0.5;
243
+ const sy0 = Math.floor(sy) - a + 1;
244
+ const sy1 = Math.floor(sy) + a;
245
+ for (let dx = 0; dx < dw; dx++) {
246
+ const sx = (dx + 0.5) / scale - 0.5;
247
+ const sx0 = Math.floor(sx) - a + 1;
248
+ const sx1 = Math.floor(sx) + a;
249
+ let r = 0, g = 0, b = 0, aa = 0, wSum = 0;
250
+ for (let iy = sy0; iy <= sy1; iy++) {
251
+ const wy = lanczos(sy - iy);
252
+ const cy = Math.max(0, Math.min(sh - 1, iy));
253
+ for (let ix = sx0; ix <= sx1; ix++) {
254
+ const wx = lanczos(sx - ix);
255
+ const w = wx * wy;
256
+ const cx = Math.max(0, Math.min(sw - 1, ix));
257
+ const si = (cy * sw + cx) * 4;
258
+ r += srcData[si] * w;
259
+ g += srcData[si + 1] * w;
260
+ b += srcData[si + 2] * w;
261
+ aa += srcData[si + 3] * w;
262
+ wSum += w;
263
+ }
264
+ }
265
+ const di = (dy * dw + dx) * 4;
266
+ if (wSum > 0) {
267
+ dstData[di] = Math.max(0, Math.min(255, r / wSum));
268
+ dstData[di + 1] = Math.max(0, Math.min(255, g / wSum));
269
+ dstData[di + 2] = Math.max(0, Math.min(255, b / wSum));
270
+ dstData[di + 3] = Math.max(0, Math.min(255, aa / wSum));
271
+ }
272
+ }
273
+ }
274
+ // Post-sharpen with unsharp mask
275
+ if (sharpen > 0) {
276
+ const blurred = new Float32Array(dw * dh * 4);
277
+ // Quick box blur
278
+ for (let y = 1; y < dh - 1; y++) {
279
+ for (let x = 1; x < dw - 1; x++) {
280
+ const di = (y * dw + x) * 4;
281
+ for (let c = 0; c < 3; c++) {
282
+ blurred[di + c] = (dstData[di + c - dw * 4] +
283
+ dstData[di + c + dw * 4] +
284
+ dstData[di + c - 4] +
285
+ dstData[di + c + 4] +
286
+ dstData[di + c] * 4) / 8;
287
+ }
288
+ }
289
+ }
290
+ // Apply unsharp mask
291
+ for (let i = 0; i < dstData.length; i += 4) {
292
+ for (let c = 0; c < 3; c++) {
293
+ const sharp = dstData[i + c] + (dstData[i + c] - blurred[i + c]) * sharpen * 2;
294
+ dstData[i + c] = Math.max(0, Math.min(255, sharp));
295
+ }
296
+ }
297
+ }
298
+ return result;
299
+ }
300
+ /**
301
+ * Denoise image using bilateral filter approximation.
302
+ */
303
+ function denoiseImage(source, options) {
304
+ const { strength, detailPreservation, luminanceWeight } = options;
305
+ const w = source.width;
306
+ const h = source.height;
307
+ const result = new ImageData(new Uint8ClampedArray(source.data), w, h);
308
+ const data = result.data;
309
+ const radius = Math.max(1, Math.round(strength * 5));
310
+ const sigmaSpace = radius * 0.5;
311
+ const sigmaColor = (1 - detailPreservation) * 150 + 10;
312
+ for (let y = 0; y < h; y++) {
313
+ for (let x = 0; x < w; x++) {
314
+ const ci = (y * w + x) * 4;
315
+ let rSum = 0, gSum = 0, bSum = 0, wSum = 0;
316
+ for (let dy = -radius; dy <= radius; dy++) {
317
+ for (let dx = -radius; dx <= radius; dx++) {
318
+ const nx = x + dx;
319
+ const ny = y + dy;
320
+ if (nx < 0 || nx >= w || ny < 0 || ny >= h)
321
+ continue;
322
+ const ni = (ny * w + nx) * 4;
323
+ const spatialDist = Math.sqrt(dx * dx + dy * dy);
324
+ const spatialW = Math.exp(-(spatialDist * spatialDist) / (2 * sigmaSpace * sigmaSpace));
325
+ // Color distance (weighted luminance vs chroma)
326
+ const lumDiff = luminance(source.data[ni], source.data[ni + 1], source.data[ni + 2]) -
327
+ luminance(source.data[ci], source.data[ci + 1], source.data[ci + 2]);
328
+ const chromaDiff = Math.sqrt((source.data[ni] - source.data[ci]) ** 2 +
329
+ (source.data[ni + 1] - source.data[ci + 1]) ** 2 +
330
+ (source.data[ni + 2] - source.data[ci + 2]) ** 2);
331
+ const colorDiff = lumDiff * luminanceWeight + chromaDiff * (1 - luminanceWeight);
332
+ const colorW = Math.exp(-(colorDiff * colorDiff) / (2 * sigmaColor * sigmaColor));
333
+ const weight = spatialW * colorW;
334
+ rSum += source.data[ni] * weight;
335
+ gSum += source.data[ni + 1] * weight;
336
+ bSum += source.data[ni + 2] * weight;
337
+ wSum += weight;
338
+ }
339
+ }
340
+ if (wSum > 0) {
341
+ data[ci] = Math.round(rSum / wSum);
342
+ data[ci + 1] = Math.round(gSum / wSum);
343
+ data[ci + 2] = Math.round(bSum / wSum);
344
+ }
345
+ }
346
+ }
347
+ return result;
348
+ }
349
+ /* ── Hook ── */
350
+ function useAITools(sourceImage) {
351
+ const [isProcessing, setIsProcessing] = useState(false);
352
+ const [activeTool, setActiveTool] = useState('colorize');
353
+ const [lastResult, setLastResult] = useState(null);
354
+ const [colorizeOptions, setColorizeOptions] = useState({
355
+ intensity: 0.7, temperature: 'neutral', saturation: 1.2,
356
+ });
357
+ const [bgRemoveOptions, setBgRemoveOptions] = useState({
358
+ edgeSoftness: 2, threshold: 0.35, iterations: 8, featherRadius: 3, replacementColor: null,
359
+ });
360
+ const [upscaleOptions, setUpscaleOptions] = useState({
361
+ scale: 2, method: 'lanczos', sharpen: 0.3,
362
+ });
363
+ const [denoiseOptions, setDenoiseOptions] = useState({
364
+ strength: 0.5, detailPreservation: 0.6, luminanceWeight: 0.7,
365
+ });
366
+ const process = useCallback(async () => {
367
+ if (!sourceImage)
368
+ return null;
369
+ setIsProcessing(true);
370
+ const start = performance.now();
371
+ let imageData;
372
+ try {
373
+ switch (activeTool) {
374
+ case 'colorize':
375
+ imageData = autoColorize(sourceImage, colorizeOptions);
376
+ break;
377
+ case 'background-remove':
378
+ imageData = removeBackground(sourceImage, bgRemoveOptions);
379
+ break;
380
+ case 'upscale':
381
+ imageData = upscaleImage(sourceImage, upscaleOptions);
382
+ break;
383
+ case 'denoise':
384
+ imageData = denoiseImage(sourceImage, denoiseOptions);
385
+ break;
386
+ default:
387
+ return null;
388
+ }
389
+ const result = {
390
+ imageData,
391
+ processingTimeMs: performance.now() - start,
392
+ tool: activeTool,
393
+ };
394
+ setLastResult(result);
395
+ return result;
396
+ }
397
+ finally {
398
+ setIsProcessing(false);
399
+ }
400
+ }, [sourceImage, activeTool, colorizeOptions, bgRemoveOptions, upscaleOptions, denoiseOptions]);
401
+ return {
402
+ activeTool, setActiveTool,
403
+ colorizeOptions, setColorizeOptions,
404
+ bgRemoveOptions, setBgRemoveOptions,
405
+ upscaleOptions, setUpscaleOptions,
406
+ denoiseOptions, setDenoiseOptions,
407
+ process, isProcessing, lastResult,
408
+ };
409
+ }
410
+ /* ── Component ── */
411
+ const TOOL_LABELS = {
412
+ colorize: '🎨 Auto-Colorize',
413
+ 'background-remove': '✂️ Remove Background',
414
+ upscale: '🔍 Upscale (ESRGAN)',
415
+ denoise: '🔇 Denoise',
416
+ };
417
+ const NiceAITools = ({ sourceImage, onResult, className = '' }) => {
418
+ var _a;
419
+ const ai = useAITools(sourceImage);
420
+ const handleProcess = async () => {
421
+ const result = await ai.process();
422
+ if (result && onResult)
423
+ onResult(result);
424
+ };
425
+ return (jsxs("div", { className: `nice-ai-tools ${className}`, style: { display: 'grid', gap: 8, fontSize: 13 }, children: [jsx("strong", { children: "\uD83E\uDD16 AI Tools" }), jsx("div", { style: { display: 'flex', gap: 2, flexWrap: 'wrap' }, children: Object.entries(TOOL_LABELS).map(([key, label]) => (jsx("button", { type: "button", onClick: () => ai.setActiveTool(key), style: {
426
+ flex: 1, padding: '4px 6px', fontSize: 11, cursor: 'pointer', borderRadius: 4,
427
+ border: '1px solid var(--border, #e2e8f0)',
428
+ background: ai.activeTool === key ? 'var(--accent, #6366f1)' : 'transparent',
429
+ color: ai.activeTool === key ? '#fff' : 'inherit',
430
+ minWidth: 100,
431
+ }, children: label }, key))) }), ai.activeTool === 'colorize' && (jsxs("div", { style: { display: 'grid', gap: 4 }, children: [jsxs("label", { children: ["Intensity: ", ai.colorizeOptions.intensity.toFixed(2), jsx("input", { type: "range", min: 0, max: 1, step: 0.05, value: ai.colorizeOptions.intensity, onChange: (e) => ai.setColorizeOptions({ ...ai.colorizeOptions, intensity: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { children: ["Saturation: ", ai.colorizeOptions.saturation.toFixed(1), jsx("input", { type: "range", min: 0, max: 2, step: 0.1, value: ai.colorizeOptions.saturation, onChange: (e) => ai.setColorizeOptions({ ...ai.colorizeOptions, saturation: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { children: ["Temperature:", jsxs("select", { value: ai.colorizeOptions.temperature, onChange: (e) => ai.setColorizeOptions({ ...ai.colorizeOptions, temperature: e.target.value }), style: { width: '100%' }, children: [jsx("option", { value: "warm", children: "Warm" }), jsx("option", { value: "neutral", children: "Neutral" }), jsx("option", { value: "cool", children: "Cool" })] })] })] })), ai.activeTool === 'background-remove' && (jsxs("div", { style: { display: 'grid', gap: 4 }, children: [jsxs("label", { children: ["Threshold: ", ai.bgRemoveOptions.threshold.toFixed(2), jsx("input", { type: "range", min: 0.1, max: 0.9, step: 0.05, value: ai.bgRemoveOptions.threshold, onChange: (e) => ai.setBgRemoveOptions({ ...ai.bgRemoveOptions, threshold: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { children: ["Iterations: ", ai.bgRemoveOptions.iterations, jsx("input", { type: "range", min: 1, max: 20, step: 1, value: ai.bgRemoveOptions.iterations, onChange: (e) => ai.setBgRemoveOptions({ ...ai.bgRemoveOptions, iterations: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { children: ["Feather: ", ai.bgRemoveOptions.featherRadius, "px", jsx("input", { type: "range", min: 0, max: 10, step: 1, value: ai.bgRemoveOptions.featherRadius, onChange: (e) => ai.setBgRemoveOptions({ ...ai.bgRemoveOptions, featherRadius: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { style: { display: 'flex', gap: 4, alignItems: 'center' }, children: ["Replace BG:", jsx("input", { type: "color", value: (_a = ai.bgRemoveOptions.replacementColor) !== null && _a !== void 0 ? _a : '#ffffff', onChange: (e) => ai.setBgRemoveOptions({ ...ai.bgRemoveOptions, replacementColor: e.target.value }) }), jsx("button", { type: "button", onClick: () => ai.setBgRemoveOptions({ ...ai.bgRemoveOptions, replacementColor: null }), style: { fontSize: 10 }, children: "Transparent" })] })] })), ai.activeTool === 'upscale' && (jsxs("div", { style: { display: 'grid', gap: 4 }, children: [jsxs("label", { children: ["Scale:", jsxs("select", { value: ai.upscaleOptions.scale, onChange: (e) => ai.setUpscaleOptions({ ...ai.upscaleOptions, scale: +e.target.value }), style: { width: '100%' }, children: [jsx("option", { value: 2, children: "2x" }), jsx("option", { value: 3, children: "3x" }), jsx("option", { value: 4, children: "4x" })] })] }), jsxs("label", { children: ["Sharpen: ", ai.upscaleOptions.sharpen.toFixed(2), jsx("input", { type: "range", min: 0, max: 1, step: 0.05, value: ai.upscaleOptions.sharpen, onChange: (e) => ai.setUpscaleOptions({ ...ai.upscaleOptions, sharpen: +e.target.value }), style: { width: '100%' } })] })] })), ai.activeTool === 'denoise' && (jsxs("div", { style: { display: 'grid', gap: 4 }, children: [jsxs("label", { children: ["Strength: ", ai.denoiseOptions.strength.toFixed(2), jsx("input", { type: "range", min: 0, max: 1, step: 0.05, value: ai.denoiseOptions.strength, onChange: (e) => ai.setDenoiseOptions({ ...ai.denoiseOptions, strength: +e.target.value }), style: { width: '100%' } })] }), jsxs("label", { children: ["Detail: ", ai.denoiseOptions.detailPreservation.toFixed(2), jsx("input", { type: "range", min: 0, max: 1, step: 0.05, value: ai.denoiseOptions.detailPreservation, onChange: (e) => ai.setDenoiseOptions({ ...ai.denoiseOptions, detailPreservation: +e.target.value }), style: { width: '100%' } })] })] })), jsx("button", { type: "button", onClick: handleProcess, disabled: ai.isProcessing || !sourceImage, style: {
432
+ background: ai.isProcessing ? '#94a3b8' : 'var(--accent, #6366f1)',
433
+ color: '#fff', border: 'none', borderRadius: 4, padding: '8px 12px',
434
+ cursor: ai.isProcessing ? 'wait' : 'pointer',
435
+ }, children: ai.isProcessing ? '⏳ Processing…' : `▶️ ${TOOL_LABELS[ai.activeTool]}` }), ai.lastResult && (jsxs("div", { style: { fontSize: 11, color: 'var(--muted, #64748b)' }, children: ["Processed in ", ai.lastResult.processingTimeMs.toFixed(0), "ms", ai.activeTool === 'upscale' && ` → ${ai.lastResult.imageData.width}×${ai.lastResult.imageData.height}`] }))] }));
436
+ };
437
+
438
+ export { NiceAITools, autoColorize, denoiseImage, removeBackground, upscaleImage, useAITools };
439
+ //# sourceMappingURL=NiceAITools.js.map