Add tile replacement to Field Item Editor

hold ctrl+alt(+shift for full map) to replace all items on the map that you tap, with the item from the editor.

don't mix & match field items (trees) with regular items, cuz we can't verify size matching for those. Field Items return "unknown size".
This commit is contained in:
Kurt 2021-02-05 09:15:52 -08:00
parent 5d84d92240
commit d47158587c
3 changed files with 74 additions and 0 deletions

View File

@ -142,5 +142,34 @@ public PlacedItemPermission IsOccupied(Item tile, in int x, in int y)
return PlacedItemPermission.NoCollision;
}
public int ReplaceAll(Item oldItem, Item newItem, in int xmin, in int ymin, in int width, in int height)
{
var sizeOld = ItemInfo.GetItemSize(oldItem);
var sizeNew = ItemInfo.GetItemSize(newItem);
if (sizeOld != sizeNew)
return -1;
int count = 0;
for (int x = xmin; x < xmin + width; x++)
{
for (int y = ymin; y < ymin + height; y++)
{
var t = GetTile(x, y);
if (!t.IsRoot)
continue;
if (!t.Equals(oldItem))
continue;
DeleteExtensionTiles(t, x, y);
t.CopyFrom(newItem);
SetExtensionTiles(t, x, y);
count++;
}
}
return count;
}
}
}

View File

@ -84,6 +84,14 @@ public int ModifyFieldItems(Func<int, int, int, int, int> action, in bool wholeM
: action(X, Y, layer.GridWidth, layer.GridHeight);
}
public int ReplaceFieldItems(Item oldItem, Item newItem, in bool wholeMap)
{
var layer = Map.CurrentLayer;
return wholeMap
? layer.ReplaceAll(oldItem, newItem, 0, 0, layer.MaxWidth, layer.MaxHeight)
: layer.ReplaceAll(oldItem, newItem, X, Y, layer.GridWidth, layer.GridHeight);
}
public void GetCursorCoordinates(in int mX, in int mY, out int x, out int y)
{
x = mX / MapScale;

View File

@ -189,6 +189,10 @@ private void OmniTile(Item tile, int x, int y)
default:
ViewTile(tile, x, y);
return;
case Keys.Alt | Keys.Control:
case Keys.Alt | Keys.Control | Keys.Shift:
ReplaceTile(tile, x, y);
return;
case Keys.Shift:
SetTile(tile, x, y);
return;
@ -362,6 +366,39 @@ private void SetTile(Item tile, int x, int y)
ReloadItems();
}
private void ReplaceTile(Item tile, int x, int y)
{
var l = Map.CurrentLayer;
var pgt = new Item();
ItemEdit.SetItem(pgt);
if (pgt.IsFieldItem && CHK_FieldItemSnap.Checked)
{
// coordinates must be even (not odd-half)
x &= 0xFFFE;
y &= 0xFFFE;
tile = l.GetTile(x, y);
}
var permission = l.IsOccupied(pgt, x, y);
switch (permission)
{
case PlacedItemPermission.OutOfBounds:
System.Media.SystemSounds.Asterisk.Play();
return;
}
bool wholeMap = (ModifierKeys & Keys.Shift) != 0;
var count = View.ReplaceFieldItems(tile, pgt, wholeMap);
if (count == 0)
{
WinFormsUtil.Alert(MessageStrings.MsgFieldItemModifyNone);
return;
}
LoadItemGridAcre();
WinFormsUtil.Alert(string.Format(MessageStrings.MsgFieldItemModifyCount, count));
}
private void RotateTile(TerrainTile tile)
{
bool rotated = tile.Rotate();