Paint towers with some the colors of the wind
This commit is contained in:
parent
fec4433691
commit
04ead32846
15 changed files with 584 additions and 32 deletions
|
|
@ -27,6 +27,9 @@ namespace TD.UI
|
|||
[Tooltip("The local client's TowerPlacementController.")]
|
||||
[SerializeField] private TowerPlacementController placementController;
|
||||
|
||||
[Tooltip("The local client's TowerPaintController (drives the Paint tab + paint cursor).")]
|
||||
[SerializeField] private TowerPaintController paintController;
|
||||
|
||||
[Tooltip("The TowerPlacementManager NetworkObject in the scene.")]
|
||||
[SerializeField] private TowerPlacementManager placementManager;
|
||||
|
||||
|
|
@ -68,6 +71,9 @@ namespace TD.UI
|
|||
private VisualElement statLines;
|
||||
private VisualElement commandGrid;
|
||||
private VisualElement actionFrame; // hidden via display:none when no actions are available
|
||||
private VisualElement commandTabs; // Build/Paint tab row — shown only for a Builder selection
|
||||
private Button tabBuild;
|
||||
private Button tabPaint;
|
||||
private VisualElement buildProgressContainer; // info-panel sub-view, shown for BuildSiteVisual selections
|
||||
private VisualElement buildProgressFill; // width driven each frame from progress
|
||||
private Label buildProgressPercent;
|
||||
|
|
@ -110,6 +116,12 @@ namespace TD.UI
|
|||
|
||||
// ----- State ------------------------------------------------------
|
||||
|
||||
// Which command-grid tab is active for a Builder selection. Build = tower buttons
|
||||
// (default), Paint = color swatches. Reset to Build whenever a non-builder is
|
||||
// selected so reselecting a builder always starts on Build.
|
||||
private enum CommandTab { Build, Paint }
|
||||
private CommandTab activeTab = CommandTab.Build;
|
||||
|
||||
private Coroutine rejectionFadeCoroutine;
|
||||
private bool placementManagerReady; // true once TowerPlacementManager.Instance is non-null
|
||||
private bool uiInitialized;
|
||||
|
|
@ -249,6 +261,12 @@ namespace TD.UI
|
|||
statLines = Require<VisualElement>(root, "stat-lines");
|
||||
commandGrid = Require<VisualElement>(root, "command-grid");
|
||||
actionFrame = Require<VisualElement>(root, "action-frame");
|
||||
commandTabs = Require<VisualElement>(root, "command-tabs");
|
||||
tabBuild = Require<Button>(root, "tab-build");
|
||||
tabPaint = Require<Button>(root, "tab-paint");
|
||||
|
||||
if (tabBuild != null) tabBuild.clicked += () => SwitchTab(CommandTab.Build);
|
||||
if (tabPaint != null) tabPaint.clicked += () => SwitchTab(CommandTab.Paint);
|
||||
buildProgressContainer = Require<VisualElement>(root, "build-progress");
|
||||
buildProgressFill = Require<VisualElement>(root, "build-progress-fill");
|
||||
buildProgressPercent = Require<Label>(root, "build-progress-percent");
|
||||
|
|
@ -681,6 +699,19 @@ namespace TD.UI
|
|||
if (actionFrame != null)
|
||||
actionFrame.style.display = hasActions ? DisplayStyle.Flex : DisplayStyle.None;
|
||||
|
||||
// Build/Paint tabs only make sense for the builder's build menu. For any
|
||||
// other selection (or none), reset to the Build tab and exit paint mode so
|
||||
// the cursor never gets stuck as a brush after deselecting the builder.
|
||||
bool isBuilder = selection is Builder;
|
||||
if (!isBuilder)
|
||||
{
|
||||
activeTab = CommandTab.Build;
|
||||
paintController?.CancelPaint();
|
||||
}
|
||||
if (commandTabs != null)
|
||||
commandTabs.style.display = isBuilder ? DisplayStyle.Flex : DisplayStyle.None;
|
||||
RefreshTabActiveState();
|
||||
|
||||
commandGrid.Clear();
|
||||
if (!hasActions) return; // grid stays empty; frame is hidden anyway
|
||||
|
||||
|
|
@ -689,12 +720,24 @@ namespace TD.UI
|
|||
|
||||
if (selection is Builder)
|
||||
{
|
||||
int i = 0;
|
||||
foreach (var (def, typeId) in placementManager.GetAvailableDefinitions())
|
||||
if (activeTab == CommandTab.Paint)
|
||||
{
|
||||
if (i >= GRID_MAX) break;
|
||||
cells[i] = CreateTowerButton(def, typeId, HotkeyLayout[i]);
|
||||
i++;
|
||||
// Paint swatches: Red/Green/Blue then a Reset (None) brush, mapped to
|
||||
// the Q/W/E/R hotkey slots via the shared CreateActionButton wiring.
|
||||
cells[0] = CreatePaintButton(PaintColor.Red, HotkeyLayout[0]);
|
||||
cells[1] = CreatePaintButton(PaintColor.Green, HotkeyLayout[1]);
|
||||
cells[2] = CreatePaintButton(PaintColor.Blue, HotkeyLayout[2]);
|
||||
cells[3] = CreatePaintButton(PaintColor.None, HotkeyLayout[3]);
|
||||
}
|
||||
else
|
||||
{
|
||||
int i = 0;
|
||||
foreach (var (def, typeId) in placementManager.GetAvailableDefinitions())
|
||||
{
|
||||
if (i >= GRID_MAX) break;
|
||||
cells[i] = CreateTowerButton(def, typeId, HotkeyLayout[i]);
|
||||
i++;
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (selection is TowerInstance tower)
|
||||
|
|
@ -745,6 +788,63 @@ namespace TD.UI
|
|||
return btn;
|
||||
}
|
||||
|
||||
// ----- Build/Paint tabs -------------------------------------------
|
||||
|
||||
// Switch the active command-grid tab and rebuild for the current selection.
|
||||
// Leaving the Paint tab also exits paint mode so the cursor reverts.
|
||||
private void SwitchTab(CommandTab tab)
|
||||
{
|
||||
if (tab == CommandTab.Build)
|
||||
paintController?.CancelPaint();
|
||||
|
||||
activeTab = tab;
|
||||
PopulateGridForSelection(SelectionState.Instance?.SelectedObject);
|
||||
}
|
||||
|
||||
private void RefreshTabActiveState()
|
||||
{
|
||||
tabBuild?.EnableInClassList("active", activeTab == CommandTab.Build);
|
||||
tabPaint?.EnableInClassList("active", activeTab == CommandTab.Paint);
|
||||
}
|
||||
|
||||
// Paint swatch: clicking enters paint mode with that color (None = Reset brush).
|
||||
// Built on CreateActionButton so the Q/W/E/R hotkey wiring comes for free; the
|
||||
// icon placeholder is tinted to the swatch color.
|
||||
private VisualElement CreatePaintButton(PaintColor color, Key hotkey)
|
||||
{
|
||||
var btn = CreateActionButton(
|
||||
costText: "",
|
||||
hotkey: hotkey,
|
||||
onClick: () =>
|
||||
{
|
||||
if (paintController != null)
|
||||
paintController.BeginPaint(color);
|
||||
else
|
||||
Debug.LogWarning("[HUDController] No TowerPaintController assigned.");
|
||||
});
|
||||
|
||||
var icon = btn.Q<VisualElement>(null, "cmd-icon-placeholder");
|
||||
if (icon != null)
|
||||
icon.style.backgroundColor = PaintColors.Get(color);
|
||||
|
||||
string label = color == PaintColor.None ? "Reset" : color.ToString();
|
||||
btn.RegisterCallback<MouseEnterEvent>(_ => ShowPaintTooltip(label, color));
|
||||
btn.RegisterCallback<MouseLeaveEvent>(_ => ClearTooltip());
|
||||
return btn;
|
||||
}
|
||||
|
||||
// Lightweight tooltip for paint swatches — reuses the tooltip box (title + desc).
|
||||
private void ShowPaintTooltip(string label, PaintColor color)
|
||||
{
|
||||
if (ttTitle == null) return;
|
||||
ttTitle.text = label;
|
||||
ttDesc.text = color == PaintColor.None
|
||||
? "Clear paint — revert tower to its owner color."
|
||||
: "Paint your towers this color.";
|
||||
ttStats.text = "";
|
||||
ttCost.text = "";
|
||||
}
|
||||
|
||||
private static VisualElement CreateEmptySlot()
|
||||
{
|
||||
var slot = new VisualElement();
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue