UIHeader.hx 20 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511
  1. package arm.ui;
  2. import kha.System;
  3. import zui.Zui;
  4. import zui.Id;
  5. import iron.system.Input;
  6. import arm.shader.MakeMaterial;
  7. #if (is_paint || is_sculpt)
  8. import iron.RenderPath;
  9. import arm.util.UVUtil;
  10. import arm.util.RenderUtil;
  11. import arm.io.ImportAsset;
  12. import arm.sys.Path;
  13. #end
  14. @:access(zui.Zui)
  15. class UIHeader {
  16. public static var inst: UIHeader;
  17. public static inline var defaultHeaderH = 28;
  18. public static var headerh = defaultHeaderH;
  19. public var headerHandle = new Handle({ layout: Horizontal });
  20. public var worktab = Id.handle();
  21. public function new() {
  22. inst = this;
  23. }
  24. public function renderUI(g: kha.graphics2.Graphics) {
  25. var ui = UIBase.inst.ui;
  26. if (Config.raw.touch_ui) {
  27. headerh = defaultHeaderH + 6;
  28. }
  29. else {
  30. headerh = defaultHeaderH;
  31. }
  32. headerh = Std.int(headerh * ui.SCALE());
  33. if (Config.raw.layout[LayoutHeader] == 0) return;
  34. #if is_lab
  35. var nodesw = (UINodes.inst.show) ? Config.raw.layout[LayoutNodesW] : 0;
  36. var ww = System.windowWidth() - nodesw;
  37. #else
  38. var nodesw = (UINodes.inst.show || UIView2D.inst.show) ? Config.raw.layout[LayoutNodesW] : 0;
  39. var ww = System.windowWidth() - UIToolbar.inst.toolbarw - Config.raw.layout[LayoutSidebarW] - nodesw;
  40. #end
  41. if (ui.window(headerHandle, iron.App.x(), headerh, ww, headerh)) {
  42. ui._y += 2;
  43. drawToolProperties(ui);
  44. }
  45. }
  46. #if is_paint
  47. public function drawToolProperties(ui: Zui) {
  48. if (Context.raw.tool == ToolColorId) {
  49. ui.text(tr("Picked Color"));
  50. if (Context.raw.colorIdPicked) {
  51. ui.image(RenderPath.active.renderTargets.get("texpaint_colorid").image, 0xffffffff, 64);
  52. }
  53. ui.enabled = Context.raw.colorIdPicked;
  54. if (ui.button(tr("Clear"))) {
  55. Context.raw.colorIdPicked = false;
  56. UIToolbar.inst.toolbarHandle.redraws = 1;
  57. }
  58. ui.enabled = true;
  59. ui.text(tr("Color ID Map"));
  60. if (Project.assetNames.length > 0) {
  61. var cid = ui.combo(Context.raw.colorIdHandle, App.enumTexts("TEX_IMAGE"), tr("Color ID"));
  62. if (Context.raw.colorIdHandle.changed) {
  63. Context.raw.ddirty = 2;
  64. Context.raw.colorIdPicked = false;
  65. UIToolbar.inst.toolbarHandle.redraws = 1;
  66. }
  67. ui.image(Project.getImage(Project.assets[cid]));
  68. if (ui.isHovered) ui.tooltipImage(Project.getImage(Project.assets[cid]), 256);
  69. }
  70. if (ui.button(tr("Import"))) {
  71. UIFiles.show(Path.textureFormats.join(","), false, true, function(path: String) {
  72. ImportAsset.run(path, -1.0, -1.0, true, false);
  73. Context.raw.colorIdHandle.position = Project.assetNames.length - 1;
  74. for (a in Project.assets) {
  75. // Already imported
  76. if (a.file == path) Context.raw.colorIdHandle.position = Project.assets.indexOf(a);
  77. }
  78. Context.raw.ddirty = 2;
  79. Context.raw.colorIdPicked = false;
  80. UIToolbar.inst.toolbarHandle.redraws = 1;
  81. UIBase.inst.hwnds[2].redraws = 2;
  82. });
  83. }
  84. ui.enabled = Context.raw.colorIdPicked;
  85. if (ui.button(tr("To Mask"))) {
  86. if (Context.raw.layer.isMask()) Context.setLayer(Context.raw.layer.parent);
  87. var m = App.newMask(false, Context.raw.layer);
  88. function _next() {
  89. if (App.pipeMerge == null) App.makePipe();
  90. if (iron.data.ConstData.screenAlignedVB == null) iron.data.ConstData.createScreenAlignedData();
  91. m.texpaint.g4.begin();
  92. m.texpaint.g4.setPipeline(App.pipeColorIdToMask);
  93. m.texpaint.g4.setTexture(App.texpaintColorId, RenderPath.active.renderTargets.get("texpaint_colorid").image);
  94. m.texpaint.g4.setTexture(App.texColorId, Project.getImage(Project.assets[Context.raw.colorIdHandle.position]));
  95. m.texpaint.g4.setVertexBuffer(iron.data.ConstData.screenAlignedVB);
  96. m.texpaint.g4.setIndexBuffer(iron.data.ConstData.screenAlignedIB);
  97. m.texpaint.g4.drawIndexedVertices();
  98. m.texpaint.g4.end();
  99. Context.raw.colorIdPicked = false;
  100. UIToolbar.inst.toolbarHandle.redraws = 1;
  101. UIHeader.inst.headerHandle.redraws = 1;
  102. Context.raw.layerPreviewDirty = true;
  103. App.updateFillLayers();
  104. }
  105. App.notifyOnNextFrame(_next);
  106. History.newWhiteMask();
  107. }
  108. ui.enabled = true;
  109. }
  110. else if (Context.raw.tool == ToolPicker || Context.raw.tool == ToolMaterial) {
  111. var baseRPicked = Math.round(Context.raw.pickedColor.base.R * 10) / 10;
  112. var baseGPicked = Math.round(Context.raw.pickedColor.base.G * 10) / 10;
  113. var baseBPicked = Math.round(Context.raw.pickedColor.base.B * 10) / 10;
  114. var normalRPicked = Math.round(Context.raw.pickedColor.normal.R * 10) / 10;
  115. var normalGPicked = Math.round(Context.raw.pickedColor.normal.G * 10) / 10;
  116. var normalBPicked = Math.round(Context.raw.pickedColor.normal.B * 10) / 10;
  117. var occlusionPicked = Math.round(Context.raw.pickedColor.occlusion * 100) / 100;
  118. var roughnessPicked = Math.round(Context.raw.pickedColor.roughness * 100) / 100;
  119. var metallicPicked = Math.round(Context.raw.pickedColor.metallic * 100) / 100;
  120. var heightPicked = Math.round(Context.raw.pickedColor.height * 100) / 100;
  121. var opacityPicked = Math.round(Context.raw.pickedColor.opacity * 100) / 100;
  122. var h = Id.handle();
  123. h.color.R = baseRPicked;
  124. h.color.G = baseGPicked;
  125. h.color.B = baseBPicked;
  126. var state = ui.text("", 0, h.color);
  127. if (state == State.Started) {
  128. var mouse = Input.getMouse();
  129. var uix = ui._x;
  130. var uiy = ui._y;
  131. App.dragOffX = -(mouse.x - uix - ui._windowX - 3);
  132. App.dragOffY = -(mouse.y - uiy - ui._windowY + 1);
  133. App.dragSwatch = Project.cloneSwatch(Context.raw.pickedColor);
  134. }
  135. if (ui.isHovered) ui.tooltip(tr("Drag and drop picked color to swatches, materials, layers or to the node editor"));
  136. if (ui.isHovered && ui.inputReleased) {
  137. UIMenu.draw(function(ui) {
  138. ui.fill(0, 0, ui._w / ui.ops.scaleFactor, ui.t.ELEMENT_H * 9, ui.t.SEPARATOR_COL);
  139. ui.changed = false;
  140. zui.Ext.colorWheel(ui, h, false, null, 10 * ui.t.ELEMENT_H * ui.SCALE(), false);
  141. if (ui.changed) UIMenu.keepOpen = true;
  142. }, 10);
  143. }
  144. if (ui.button(tr("Add Swatch"))) {
  145. var newSwatch = Project.cloneSwatch(Context.raw.pickedColor);
  146. Context.setSwatch(newSwatch);
  147. Project.raw.swatches.push(newSwatch);
  148. UIBase.inst.hwnds[2].redraws = 1;
  149. }
  150. if (ui.isHovered) ui.tooltip(tr("Add picked color to swatches"));
  151. ui.text(tr("Base") + ' ($baseRPicked,$baseGPicked,$baseBPicked)');
  152. ui.text(tr("Normal") + ' ($normalRPicked,$normalGPicked,$normalBPicked)');
  153. ui.text(tr("Occlusion") + ' ($occlusionPicked)');
  154. ui.text(tr("Roughness") + ' ($roughnessPicked)');
  155. ui.text(tr("Metallic") + ' ($metallicPicked)');
  156. ui.text(tr("Height") + ' ($heightPicked)');
  157. ui.text(tr("Opacity") + ' ($opacityPicked)');
  158. Context.raw.pickerSelectMaterial = ui.check(Id.handle({ selected: Context.raw.pickerSelectMaterial }), tr("Select Material"));
  159. ui.combo(Context.raw.pickerMaskHandle, [tr("None"), tr("Material")], tr("Mask"), true);
  160. if (Context.raw.pickerMaskHandle.changed) {
  161. MakeMaterial.parsePaintMaterial();
  162. }
  163. }
  164. else if (Context.raw.tool == ToolBake) {
  165. ui.changed = false;
  166. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  167. var baking = Context.raw.pdirty > 0;
  168. var rtBake = Context.raw.bakeType == BakeAO || Context.raw.bakeType == BakeLightmap || Context.raw.bakeType == BakeBentNormal || Context.raw.bakeType == BakeThickness;
  169. if (baking && ui.button(tr("Stop"))) {
  170. Context.raw.pdirty = 0;
  171. Context.raw.rdirty = 2;
  172. }
  173. #else
  174. var baking = false;
  175. var rtBake = false;
  176. #end
  177. if (!baking && ui.button(tr("Bake"))) {
  178. Context.raw.pdirty = rtBake ? Context.raw.bakeSamples : 1;
  179. Context.raw.rdirty = 3;
  180. App.notifyOnNextFrame(function() {
  181. Context.raw.layerPreviewDirty = true;
  182. });
  183. UIBase.inst.hwnds[0].redraws = 2;
  184. History.pushUndo = true;
  185. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  186. arm.render.RenderPathRaytraceBake.currentSample = 0;
  187. #end
  188. }
  189. var bakeHandle = Id.handle({ position: Context.raw.bakeType });
  190. var bakes = [
  191. tr("AO"),
  192. tr("Curvature"),
  193. tr("Normal"),
  194. tr("Object Normal"),
  195. tr("Height"),
  196. tr("Derivative"),
  197. tr("Position"),
  198. tr("TexCoord"),
  199. tr("Material ID"),
  200. tr("Object ID"),
  201. tr("Vertex Color"),
  202. ];
  203. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  204. if (Krom.raytraceSupported()) {
  205. bakes.push(tr("Lightmap"));
  206. bakes.push(tr("Bent Normal"));
  207. bakes.push(tr("Thickness"));
  208. }
  209. else {
  210. bakes.shift(); // Remove AO
  211. }
  212. #end
  213. Context.raw.bakeType = ui.combo(bakeHandle, bakes, tr("Bake"));
  214. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  215. if (!Krom.raytraceSupported()) {
  216. Context.raw.bakeType += 1; // Offset for removed AO
  217. }
  218. #end
  219. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  220. if (rtBake) {
  221. var samplesHandle = Id.handle({ value: Context.raw.bakeSamples });
  222. Context.raw.bakeSamples = Std.int(ui.slider(samplesHandle, tr("Samples"), 1, 512, true, 1));
  223. }
  224. #end
  225. if (Context.raw.bakeType == BakeNormalObject || Context.raw.bakeType == BakePosition || Context.raw.bakeType == BakeBentNormal) {
  226. var bakeUpAxisHandle = Id.handle({ position: Context.raw.bakeUpAxis });
  227. Context.raw.bakeUpAxis = ui.combo(bakeUpAxisHandle, [tr("Z"), tr("Y")], tr("Up Axis"), true);
  228. }
  229. if (Context.raw.bakeType == BakeAO || Context.raw.bakeType == BakeCurvature) {
  230. var bakeAxisHandle = Id.handle({ position: Context.raw.bakeAxis });
  231. Context.raw.bakeAxis = ui.combo(bakeAxisHandle, [tr("XYZ"), tr("X"), tr("Y"), tr("Z"), tr("-X"), tr("-Y"), tr("-Z")], tr("Axis"), true);
  232. }
  233. if (Context.raw.bakeType == BakeAO) {
  234. var strengthHandle = Id.handle({ value: Context.raw.bakeAoStrength });
  235. Context.raw.bakeAoStrength = ui.slider(strengthHandle, tr("Strength"), 0.0, 2.0, true);
  236. var radiusHandle = Id.handle({ value: Context.raw.bakeAoRadius });
  237. Context.raw.bakeAoRadius = ui.slider(radiusHandle, tr("Radius"), 0.0, 2.0, true);
  238. var offsetHandle = Id.handle({ value: Context.raw.bakeAoOffset });
  239. Context.raw.bakeAoOffset = ui.slider(offsetHandle, tr("Offset"), 0.0, 2.0, true);
  240. }
  241. #if (kha_direct3d12 || kha_vulkan || kha_metal)
  242. if (rtBake) {
  243. var progress = arm.render.RenderPathRaytraceBake.currentSample / Context.raw.bakeSamples;
  244. if (progress > 1.0) progress = 1.0;
  245. // Progress bar
  246. ui.g.color = ui.t.SEPARATOR_COL;
  247. ui.drawRect(ui.g, true, ui._x + 1, ui._y, ui._w - 2, ui.ELEMENT_H());
  248. ui.g.color = ui.t.HIGHLIGHT_COL;
  249. ui.drawRect(ui.g, true, ui._x + 1, ui._y, (ui._w - 2) * progress, ui.ELEMENT_H());
  250. ui.g.color = 0xffffffff;
  251. ui.text(tr("Samples") + ": " + arm.render.RenderPathRaytraceBake.currentSample);
  252. ui.text(tr("Rays/pixel" + ": ") + arm.render.RenderPathRaytraceBake.raysPix);
  253. ui.text(tr("Rays/second" + ": ") + arm.render.RenderPathRaytraceBake.raysSec);
  254. }
  255. #end
  256. if (Context.raw.bakeType == BakeCurvature) {
  257. var strengthHandle = Id.handle({ value: Context.raw.bakeCurvStrength });
  258. Context.raw.bakeCurvStrength = ui.slider(strengthHandle, tr("Strength"), 0.0, 2.0, true);
  259. var radiusHandle = Id.handle({ value: Context.raw.bakeCurvRadius });
  260. Context.raw.bakeCurvRadius = ui.slider(radiusHandle, tr("Radius"), 0.0, 2.0, true);
  261. var offsetHandle = Id.handle({ value: Context.raw.bakeCurvOffset });
  262. Context.raw.bakeCurvOffset = ui.slider(offsetHandle, tr("Offset"), -2.0, 2.0, true);
  263. var smoothHandle = Id.handle({ value: Context.raw.bakeCurvSmooth });
  264. Context.raw.bakeCurvSmooth = Std.int(ui.slider(smoothHandle, tr("Smooth"), 0, 5, false, 1));
  265. }
  266. if (Context.raw.bakeType == BakeNormal || Context.raw.bakeType == BakeHeight || Context.raw.bakeType == BakeDerivative) {
  267. var ar = [for (p in Project.paintObjects) p.name];
  268. var polyHandle = Id.handle({ position: Context.raw.bakeHighPoly });
  269. Context.raw.bakeHighPoly = ui.combo(polyHandle, ar, tr("High Poly"));
  270. }
  271. if (ui.changed) {
  272. MakeMaterial.parsePaintMaterial();
  273. }
  274. }
  275. else if (Context.raw.tool == ToolBrush ||
  276. Context.raw.tool == ToolEraser ||
  277. Context.raw.tool == ToolFill ||
  278. Context.raw.tool == ToolDecal ||
  279. Context.raw.tool == ToolText ||
  280. Context.raw.tool == ToolClone ||
  281. Context.raw.tool == ToolBlur ||
  282. Context.raw.tool == ToolSmudge ||
  283. Context.raw.tool == ToolParticle) {
  284. var decal = Context.raw.tool == ToolDecal || Context.raw.tool == ToolText;
  285. var decalMask = decal && Operator.shortcut(Config.keymap.decal_mask, ShortcutDown);
  286. if (Context.raw.tool != ToolFill) {
  287. if (decalMask) {
  288. Context.raw.brushDecalMaskRadius = ui.slider(Context.raw.brushDecalMaskRadiusHandle, tr("Radius"), 0.01, 2.0, true);
  289. if (ui.isHovered) ui.tooltip(tr("Hold {brush_radius} and move mouse to the left or press {brush_radius_decrease} to decrease the radius\nHold {brush_radius} and move mouse to the right or press {brush_radius_increase} to increase the radius", ["brush_radius" => Config.keymap.brush_radius, "brush_radius_decrease" => Config.keymap.brush_radius_decrease, "brush_radius_increase" => Config.keymap.brush_radius_increase]));
  290. }
  291. else {
  292. Context.raw.brushRadius = ui.slider(Context.raw.brushRadiusHandle, tr("Radius"), 0.01, 2.0, true);
  293. if (ui.isHovered) ui.tooltip(tr("Hold {brush_radius} and move mouse to the left or press {brush_radius_decrease} to decrease the radius\nHold {brush_radius} and move mouse to the right or press {brush_radius_increase} to increase the radius", ["brush_radius" => Config.keymap.brush_radius, "brush_radius_decrease" => Config.keymap.brush_radius_decrease, "brush_radius_increase" => Config.keymap.brush_radius_increase]));
  294. }
  295. }
  296. if (Context.raw.tool == ToolDecal || Context.raw.tool == ToolText) {
  297. Context.raw.brushScaleX = ui.slider(Context.raw.brushScaleXHandle, tr("Scale X"), 0.01, 2.0, true);
  298. }
  299. if (Context.raw.tool == ToolBrush ||
  300. Context.raw.tool == ToolFill ||
  301. Context.raw.tool == ToolDecal ||
  302. Context.raw.tool == ToolText) {
  303. var brushScaleHandle = Id.handle({ value: Context.raw.brushScale });
  304. Context.raw.brushScale = ui.slider(brushScaleHandle, tr("UV Scale"), 0.01, 5.0, true);
  305. if (brushScaleHandle.changed) {
  306. if (Context.raw.tool == ToolDecal || Context.raw.tool == ToolText) {
  307. ui.g.end();
  308. RenderUtil.makeDecalPreview();
  309. ui.g.begin(false);
  310. }
  311. }
  312. Context.raw.brushAngle = ui.slider(Context.raw.brushAngleHandle, tr("Angle"), 0.0, 360.0, true, 1);
  313. if (ui.isHovered) ui.tooltip(tr("Hold {brush_angle} and move mouse to the left to decrease the angle\nHold {brush_angle} and move mouse to the right to increase the angle", ["brush_angle" => Config.keymap.brush_angle]));
  314. if (Context.raw.brushAngleHandle.changed) {
  315. MakeMaterial.parsePaintMaterial();
  316. }
  317. }
  318. Context.raw.brushOpacity = ui.slider(Context.raw.brushOpacityHandle, tr("Opacity"), 0.0, 1.0, true);
  319. if (ui.isHovered) ui.tooltip(tr("Hold {brush_opacity} and move mouse to the left to decrease the opacity\nHold {brush_opacity} and move mouse to the right to increase the opacity", ["brush_opacity" => Config.keymap.brush_opacity]));
  320. if (Context.raw.tool == ToolBrush || Context.raw.tool == ToolEraser || Context.raw.tool == ToolClone || decalMask) {
  321. Context.raw.brushHardness = ui.slider(Id.handle({ value: Context.raw.brushHardness }), tr("Hardness"), 0.0, 1.0, true);
  322. }
  323. if (Context.raw.tool != ToolEraser) {
  324. var brushBlendingHandle = Id.handle({ value: Context.raw.brushBlending });
  325. Context.raw.brushBlending = ui.combo(brushBlendingHandle, [
  326. tr("Mix"),
  327. tr("Darken"),
  328. tr("Multiply"),
  329. tr("Burn"),
  330. tr("Lighten"),
  331. tr("Screen"),
  332. tr("Dodge"),
  333. tr("Add"),
  334. tr("Overlay"),
  335. tr("Soft Light"),
  336. tr("Linear Light"),
  337. tr("Difference"),
  338. tr("Subtract"),
  339. tr("Divide"),
  340. tr("Hue"),
  341. tr("Saturation"),
  342. tr("Color"),
  343. tr("Value"),
  344. ], tr("Blending"));
  345. if (brushBlendingHandle.changed) {
  346. MakeMaterial.parsePaintMaterial();
  347. }
  348. }
  349. if (Context.raw.tool == ToolBrush || Context.raw.tool == ToolFill) {
  350. var paintHandle = Id.handle();
  351. Context.raw.brushPaint = ui.combo(paintHandle, [tr("UV Map"), tr("Triplanar"), tr("Project")], tr("TexCoord"));
  352. if (paintHandle.changed) {
  353. MakeMaterial.parsePaintMaterial();
  354. }
  355. }
  356. if (Context.raw.tool == ToolText) {
  357. var h = Id.handle();
  358. h.text = Context.raw.textToolText;
  359. var w = ui._w;
  360. if (ui.textSelectedHandle == h || ui.submitTextHandle == h) {
  361. ui._w *= 3;
  362. }
  363. Context.raw.textToolText = ui.textInput(h, "", Left, true, true);
  364. ui._w = w;
  365. if (h.changed) {
  366. ui.g.end();
  367. RenderUtil.makeTextPreview();
  368. RenderUtil.makeDecalPreview();
  369. ui.g.begin(false);
  370. }
  371. }
  372. if (Context.raw.tool == ToolFill) {
  373. ui.combo(Context.raw.fillTypeHandle, [tr("Object"), tr("Face"), tr("Angle"), tr("UV Island")], tr("Fill Mode"));
  374. if (Context.raw.fillTypeHandle.changed) {
  375. if (Context.raw.fillTypeHandle.position == FillFace) {
  376. ui.g.end();
  377. // UVUtil.cacheUVMap();
  378. UVUtil.cacheTriangleMap();
  379. ui.g.begin(false);
  380. // wireframeHandle.selected = drawWireframe = true;
  381. }
  382. MakeMaterial.parsePaintMaterial();
  383. MakeMaterial.parseMeshMaterial();
  384. }
  385. }
  386. else {
  387. var _w = ui._w;
  388. var sc = ui.SCALE();
  389. var touchHeader = (Config.raw.touch_ui && Config.raw.layout[LayoutHeader] == 1);
  390. if (touchHeader) ui._x -= 4 * sc;
  391. ui._w = Std.int((touchHeader ? 54 : 60) * sc);
  392. var xrayHandle = Id.handle({ selected: Context.raw.xray });
  393. Context.raw.xray = ui.check(xrayHandle, tr("X-Ray"));
  394. if (xrayHandle.changed) {
  395. MakeMaterial.parsePaintMaterial();
  396. }
  397. var symXHandle = Id.handle({ selected: false });
  398. var symYHandle = Id.handle({ selected: false });
  399. var symZHandle = Id.handle({ selected: false });
  400. if (Config.raw.layout[LayoutHeader] == 1) {
  401. if (Config.raw.touch_ui) {
  402. ui._w = Std.int(19 * sc);
  403. Context.raw.symX = ui.check(symXHandle, "");
  404. ui._x -= 4 * sc;
  405. Context.raw.symY = ui.check(symYHandle, "");
  406. ui._x -= 4 * sc;
  407. Context.raw.symZ = ui.check(symZHandle, "");
  408. ui._x -= 4 * sc;
  409. ui._w = Std.int(40 * sc);
  410. ui.text(tr("X") + tr("Y") + tr("Z"));
  411. }
  412. else {
  413. ui._w = Std.int(56 * sc);
  414. ui.text(tr("Symmetry"));
  415. ui._w = Std.int(25 * sc);
  416. Context.raw.symX = ui.check(symXHandle, tr("X"));
  417. Context.raw.symY = ui.check(symYHandle, tr("Y"));
  418. Context.raw.symZ = ui.check(symZHandle, tr("Z"));
  419. }
  420. ui._w = _w;
  421. }
  422. else {
  423. // Popup
  424. ui._w = _w;
  425. Context.raw.symX = ui.check(symXHandle, tr("Symmetry") + " " + tr("X"));
  426. Context.raw.symY = ui.check(symYHandle, tr("Symmetry") + " " + tr("Y"));
  427. Context.raw.symZ = ui.check(symZHandle, tr("Symmetry") + " " + tr("Z"));
  428. }
  429. if (symXHandle.changed || symYHandle.changed || symZHandle.changed) {
  430. MakeMaterial.parsePaintMaterial();
  431. }
  432. }
  433. #if arm_physics
  434. if (Context.raw.tool == ToolParticle) {
  435. ui._x += 10 * ui.SCALE();
  436. var physHandle = Id.handle({ selected: false });
  437. Context.raw.particlePhysics = ui.check(physHandle, tr("Physics"));
  438. if (physHandle.changed) {
  439. arm.util.ParticleUtil.initParticlePhysics();
  440. MakeMaterial.parsePaintMaterial();
  441. }
  442. }
  443. #end
  444. }
  445. }
  446. #end
  447. #if is_sculpt
  448. public function drawToolProperties(ui: Zui) {}
  449. #end
  450. #if is_lab
  451. public function drawToolProperties(ui: Zui) {
  452. if (Context.raw.tool == ToolPicker) {
  453. }
  454. else if (Context.raw.tool == ToolEraser ||
  455. Context.raw.tool == ToolClone ||
  456. Context.raw.tool == ToolBlur ||
  457. Context.raw.tool == ToolSmudge) {
  458. var inpaint = UINodes.inst.getNodes().nodesSelected.length > 0 && UINodes.inst.getNodes().nodesSelected[0].type == "InpaintNode";
  459. if (inpaint) {
  460. Context.raw.brushRadius = ui.slider(Context.raw.brushRadiusHandle, tr("Radius"), 0.01, 2.0, true);
  461. if (ui.isHovered) ui.tooltip(tr("Hold {brush_radius} and move mouse to the left or press {brush_radius_decrease} to decrease the radius\nHold {brush_radius} and move mouse to the right or press {brush_radius_increase} to increase the radius", ["brush_radius" => Config.keymap.brush_radius, "brush_radius_decrease" => Config.keymap.brush_radius_decrease, "brush_radius_increase" => Config.keymap.brush_radius_increase]));
  462. }
  463. }
  464. }
  465. #end
  466. }