mirror of
https://git.do.srb2.org/STJr/UltimateZoneBuilder.git
synced 2024-11-27 22:22:32 +00:00
13c3155db5
Added "Paste Properties Special" actions in "Classic" and "Visual" categories. They work the same way as "Paste Special" action. Added: "Copy Properties", "Paste Properties" and "Paste Properties Special" options are now shown in the Edit menu if current classic mode supports them. Changed, Paste Properties Special window: only options relevant to current map format are now displayed. Changed, Paste Properties Special window, UDMF: all UI-managed options are now available. Fixed: MAPINFO parser was unable to process "include" directives. Fixed, General interface: selection info was reset to "Nothing selected" after few seconds regardless of current selection. Fixed, Visual mode: thing bounding boxes were not updated when changing things positions using Randomize mode. Fixed, Visual mode: event lines were displayed at incorrect height when entering Visual mode for the first time. Fixed, Texture Browser window: when MixTexturesFlats Game Configuration option is disabled, textures/flats are no longer shown in the Used group when flats/textures with the same names are used in the map. Fixed(?): probably fixed an exception some users reported when trying to initialize a Classic mode after switching from Visual mode with "Sync cameras" option enabled. Changed, Game configurations, Thing Categories: a block must have at least one thing category property to be recognized as a thing category. Changed, Visplane Explorer: the plugin now outputs more info when it fails to initialize vpo.dll. Cosmetic, Thing Edit window, Doom/Hexen map format: adjusted UI layout so thing flags control no longer displays scrollbars in Hexen map format. Internal: merged methods from UDMFTools into UniFields, removed UDMFTools. Updated Inno Setup script (added VC++ 2008 SP1 distributive). Updated ZDoom_DECORATE.cfg (A_CheckBlock). Updated documentation (added "System Requirements" page).
222 lines
7.3 KiB
C#
222 lines
7.3 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Drawing;
|
|
using System.Reflection;
|
|
using System.Windows.Forms;
|
|
using CodeImp.DoomBuilder.Controls;
|
|
using CodeImp.DoomBuilder.Map;
|
|
using CodeImp.DoomBuilder.Windows;
|
|
|
|
namespace CodeImp.DoomBuilder.BuilderModes
|
|
{
|
|
public partial class SelectSimilarElementOptionsPanel : DelayedForm
|
|
{
|
|
private static Size size = Size.Empty;
|
|
private static Point location = Point.Empty;
|
|
private static readonly object[] flags = {
|
|
new SectorPropertiesCopySettings(),
|
|
new LinedefPropertiesCopySettings(),
|
|
new SidedefPropertiesCopySettings(),
|
|
new ThingPropertiesCopySettings(),
|
|
new VertexPropertiesCopySettings()
|
|
};
|
|
|
|
private BaseClassicMode mode;
|
|
private List<TabPage> showntabs;
|
|
private readonly Dictionary<CheckboxArrayControl, object> typecontrols;
|
|
|
|
public SelectSimilarElementOptionsPanel()
|
|
{
|
|
InitializeComponent();
|
|
|
|
//apply window size and location
|
|
if(!size.IsEmpty && !location.IsEmpty)
|
|
{
|
|
this.StartPosition = FormStartPosition.Manual;
|
|
this.Size = size;
|
|
this.Location = location;
|
|
}
|
|
|
|
//create a collection
|
|
typecontrols = new Dictionary<CheckboxArrayControl, object>
|
|
{
|
|
{ sectorflags, flags[0] },
|
|
{ lineflags, flags[1] },
|
|
{ sideflags, flags[2] },
|
|
{ thingflags, flags[3] },
|
|
{ vertexflags, flags[4] }
|
|
};
|
|
}
|
|
|
|
public bool Setup(BaseClassicMode mode)
|
|
{
|
|
this.mode = mode;
|
|
|
|
//which tabs should we display?
|
|
TabPage[] activetabs = null;
|
|
if(General.Editing.Mode is ThingsMode)
|
|
{
|
|
if(General.Map.Map.GetSelectedThings(true).Count == 0) return SetupFailed("This action requires selection...");
|
|
activetabs = new[] { things };
|
|
}
|
|
else if(General.Editing.Mode is VerticesMode && General.Map.UDMF)
|
|
{
|
|
if(General.Map.Map.GetSelectedVertices(true).Count == 0) return SetupFailed("This action requires selection...");
|
|
activetabs = new[] { vertices };
|
|
}
|
|
else if(General.Editing.Mode is LinedefsMode)
|
|
{
|
|
if(General.Map.Map.GetSelectedLinedefs(true).Count == 0) return SetupFailed("This action requires selection...");
|
|
activetabs = new[] { linedefs, sidedefs };
|
|
}
|
|
else if(mode is SectorsMode)
|
|
{
|
|
if(General.Map.Map.GetSelectedSectors(true).Count == 0) return SetupFailed("This action requires selection...");
|
|
activetabs = new[] { sectors };
|
|
}
|
|
|
|
if(activetabs == null) return SetupFailed("This action doesn't support current editing mode...");
|
|
|
|
//fill flags
|
|
showntabs = new List<TabPage>();
|
|
foreach(TabPage page in activetabs)
|
|
{
|
|
CheckboxArrayControl curControl = page.Controls[0] as CheckboxArrayControl;
|
|
if(curControl == null) continue; //just a piece of boilerplate...
|
|
|
|
FieldInfo[] props = typecontrols[curControl].GetType().GetFields(BindingFlags.Public | BindingFlags.Instance);
|
|
foreach(var prop in props)
|
|
{
|
|
foreach(Attribute attr in Attribute.GetCustomAttributes(prop))
|
|
{
|
|
if(attr.GetType() == typeof(FieldDescription))
|
|
{
|
|
FieldDescription fd = (FieldDescription)attr;
|
|
if(fd.SupportsCurrentMapFormat)
|
|
curControl.Add(fd.Description, prop.Name).Checked = (bool)prop.GetValue(typecontrols[curControl]);
|
|
}
|
|
}
|
|
}
|
|
|
|
if(curControl.Checkboxes.Count > 0)
|
|
{
|
|
curControl.PositionCheckboxes();
|
|
showntabs.Add(page);
|
|
}
|
|
}
|
|
|
|
// Got anything to show?
|
|
if(showntabs.Count == 0) return SetupFailed("This action doesn't support current editing mode...");
|
|
|
|
// Hide unused tab pages
|
|
tabControl.TabPages.Clear();
|
|
tabControl.TabPages.AddRange(showntabs.ToArray());
|
|
tabControl.SelectTab(showntabs[0]);
|
|
|
|
return true;
|
|
}
|
|
|
|
private static bool SetupFailed(string message)
|
|
{
|
|
General.Interface.DisplayStatus(StatusType.Warning, message);
|
|
return false;
|
|
}
|
|
|
|
private void SelectSimilarElementOptionsPanel_FormClosing(object sender, FormClosingEventArgs e)
|
|
{
|
|
size = this.Size;
|
|
location = this.Location;
|
|
}
|
|
|
|
private void enableall_Click(object sender, EventArgs e)
|
|
{
|
|
CheckboxArrayControl curControl = tabControl.SelectedTab.Controls[0] as CheckboxArrayControl;
|
|
if(curControl == null) return; //just a piece of boilerplate...
|
|
bool enable = !curControl.Checkboxes[0].Checked;
|
|
foreach(var cb in curControl.Checkboxes) cb.Checked = enable;
|
|
}
|
|
|
|
private void cancel_Click(object sender, EventArgs e)
|
|
{
|
|
this.Close();
|
|
}
|
|
|
|
private void apply_Click(object sender, EventArgs e)
|
|
{
|
|
//save flags states
|
|
foreach(TabPage page in showntabs)
|
|
{
|
|
CheckboxArrayControl curControl = page.Controls[0] as CheckboxArrayControl;
|
|
if(curControl == null) continue; //just a piece of boilerplate...
|
|
|
|
FieldInfo[] props = typecontrols[curControl].GetType().GetFields(BindingFlags.Public | BindingFlags.Instance);
|
|
var fields = new Dictionary<string, FieldInfo>(props.Length);
|
|
for(int i = 0; i < props.Length; i++) fields[props[i].Name] = props[i];
|
|
foreach(CheckBox cb in curControl.Checkboxes) fields[cb.Tag.ToString()].SetValue(typecontrols[curControl], cb.Checked);
|
|
}
|
|
|
|
//perform selection
|
|
if(mode is ThingsMode)
|
|
{
|
|
ICollection<Thing> selected = General.Map.Map.GetSelectedThings(true);
|
|
ICollection<Thing> unselected = General.Map.Map.GetSelectedThings(false);
|
|
|
|
foreach(Thing target in unselected)
|
|
{
|
|
foreach(Thing source in selected)
|
|
{
|
|
if(PropertiesComparer.PropertiesMatch((ThingPropertiesCopySettings) typecontrols[thingflags], source, target))
|
|
mode.SelectMapElement(target);
|
|
}
|
|
}
|
|
}
|
|
else if(mode is LinedefsMode)
|
|
{
|
|
ICollection<Linedef> selected = General.Map.Map.GetSelectedLinedefs(true);
|
|
ICollection<Linedef> unselected = General.Map.Map.GetSelectedLinedefs(false);
|
|
|
|
foreach(Linedef target in unselected)
|
|
{
|
|
foreach(Linedef source in selected)
|
|
{
|
|
if(PropertiesComparer.PropertiesMatch((LinedefPropertiesCopySettings)typecontrols[lineflags], (SidedefPropertiesCopySettings)typecontrols[sideflags], source, target))
|
|
mode.SelectMapElement(target);
|
|
}
|
|
}
|
|
}
|
|
else if(mode is SectorsMode)
|
|
{
|
|
ICollection<Sector> selected = General.Map.Map.GetSelectedSectors(true);
|
|
ICollection<Sector> unselected = General.Map.Map.GetSelectedSectors(false);
|
|
|
|
foreach(Sector target in unselected)
|
|
{
|
|
foreach(Sector source in selected)
|
|
{
|
|
if(PropertiesComparer.PropertiesMatch((SectorPropertiesCopySettings)typecontrols[sectorflags], source, target))
|
|
mode.SelectMapElement(target);
|
|
}
|
|
}
|
|
}
|
|
else if(mode is VerticesMode)
|
|
{
|
|
ICollection<Vertex> selected = General.Map.Map.GetSelectedVertices(true);
|
|
ICollection<Vertex> unselected = General.Map.Map.GetSelectedVertices(false);
|
|
|
|
foreach(Vertex target in unselected)
|
|
{
|
|
foreach(Vertex source in selected)
|
|
{
|
|
if(PropertiesComparer.PropertiesMatch((VertexPropertiesCopySettings)typecontrols[vertexflags], source, target))
|
|
mode.SelectMapElement(target);
|
|
}
|
|
}
|
|
|
|
}
|
|
|
|
mode.UpdateSelectionInfo();
|
|
General.Interface.RedrawDisplay();
|
|
this.Close();
|
|
}
|
|
}
|
|
}
|