2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
#region ================== Copyright (c) 2007 Pascal vd Heiden
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Copyright (c) 2007 Pascal vd Heiden, www.codeimp.com
|
|
|
|
* This program is released under GNU General Public License
|
|
|
|
*
|
|
|
|
* This program is distributed in the hope that it will be useful,
|
|
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
|
|
* GNU General Public License for more details.
|
|
|
|
*
|
|
|
|
*/
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region ================== Namespaces
|
|
|
|
|
|
|
|
using System;
|
|
|
|
using System.ComponentModel;
|
|
|
|
using System.Windows.Forms;
|
|
|
|
using CodeImp.DoomBuilder.Config;
|
2013-08-13 09:49:29 +00:00
|
|
|
using CodeImp.DoomBuilder.Geometry;
|
2009-04-19 18:07:22 +00:00
|
|
|
using CodeImp.DoomBuilder.Types;
|
|
|
|
using System.Globalization;
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
namespace CodeImp.DoomBuilder.Controls
|
|
|
|
{
|
2009-05-21 08:18:34 +00:00
|
|
|
/// <summary>
|
|
|
|
/// Control to accept a linedef action argument.
|
|
|
|
/// </summary>
|
2009-04-19 18:07:22 +00:00
|
|
|
public partial class ArgumentBox : UserControl
|
|
|
|
{
|
|
|
|
#region ================== Variables
|
2010-09-01 14:36:31 +00:00
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
private TypeHandler typehandler;
|
2013-07-23 14:25:03 +00:00
|
|
|
private bool ignorebuttonchange;
|
2020-11-19 21:14:19 +00:00
|
|
|
private bool forcevalidate;
|
2009-07-10 19:15:22 +00:00
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region ================== Properties
|
|
|
|
|
2013-08-08 11:04:13 +00:00
|
|
|
public override string Text { get { return combobox.Text; } } //mxd
|
|
|
|
|
2022-02-19 10:21:28 +00:00
|
|
|
[Browsable(true)]
|
|
|
|
[Category("Action")]
|
|
|
|
[Description("Invoked when user clicks button")]
|
|
|
|
public event EventHandler ValueChanged;
|
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region ================== Constructor
|
|
|
|
|
|
|
|
// Constructor
|
|
|
|
public ArgumentBox()
|
|
|
|
{
|
|
|
|
// Initialize
|
|
|
|
InitializeComponent();
|
2009-07-10 19:15:22 +00:00
|
|
|
scrollbuttons.Value = 0;
|
2010-08-14 08:26:55 +00:00
|
|
|
combobox.MouseWheel += combobox_MouseWheel;
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region ================== Events
|
|
|
|
|
|
|
|
// When control resizes
|
|
|
|
private void ArgumentBox_Resize(object sender, EventArgs e)
|
|
|
|
{
|
|
|
|
if(button.Visible)
|
|
|
|
combobox.Width = ClientRectangle.Width - button.Width - 2;
|
2009-07-10 19:15:22 +00:00
|
|
|
else if(scrollbuttons.Visible)
|
|
|
|
combobox.Width = ClientRectangle.Width - scrollbuttons.Width - 2;
|
2009-04-19 18:07:22 +00:00
|
|
|
else
|
|
|
|
combobox.Width = ClientRectangle.Width;
|
|
|
|
|
|
|
|
button.Left = ClientRectangle.Width - button.Width;
|
2009-07-10 19:15:22 +00:00
|
|
|
scrollbuttons.Left = ClientRectangle.Width - scrollbuttons.Width;
|
2009-04-19 18:07:22 +00:00
|
|
|
Height = button.Height;
|
|
|
|
}
|
|
|
|
|
|
|
|
// When control layout is aplied
|
|
|
|
private void ArgumentBox_Layout(object sender, LayoutEventArgs e)
|
|
|
|
{
|
|
|
|
ArgumentBox_Resize(sender, e);
|
|
|
|
}
|
|
|
|
|
|
|
|
// When the entered value needs to be validated
|
|
|
|
private void combobox_Validating(object sender, CancelEventArgs e)
|
|
|
|
{
|
|
|
|
string str = combobox.Text.Trim().ToLowerInvariant();
|
2016-08-29 11:32:31 +00:00
|
|
|
str = str.TrimStart('+', '-', '<', '>');
|
2014-12-08 21:06:08 +00:00
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
// Anything in the box?
|
|
|
|
if(combobox.Text.Trim().Length > 0)
|
|
|
|
{
|
|
|
|
// Prefixed?
|
2009-07-10 19:15:22 +00:00
|
|
|
if(CheckIsRelative())
|
2009-04-19 18:07:22 +00:00
|
|
|
{
|
|
|
|
// Try parsing to number
|
2014-12-08 21:06:08 +00:00
|
|
|
int num;
|
2009-04-19 18:07:22 +00:00
|
|
|
if(!int.TryParse(str, NumberStyles.Integer, CultureInfo.CurrentCulture, out num))
|
|
|
|
{
|
|
|
|
// Invalid relative number
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = "";
|
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Set the value. The type handler will validate it
|
|
|
|
// and make the best possible choice.
|
|
|
|
typehandler.SetValue(combobox.Text);
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = typehandler.GetStringValue();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
// When browse button is clicked
|
|
|
|
private void button_Click(object sender, EventArgs e)
|
|
|
|
{
|
|
|
|
// Browse for a value
|
|
|
|
typehandler.Browse(this);
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = typehandler.GetStringValue();
|
|
|
|
combobox.Focus();
|
|
|
|
combobox.SelectAll();
|
|
|
|
}
|
2009-07-10 19:15:22 +00:00
|
|
|
|
|
|
|
// Text changes
|
|
|
|
private void combobox_TextChanged(object sender, EventArgs e)
|
|
|
|
{
|
|
|
|
scrollbuttons.Enabled = !CheckIsRelative();
|
2016-05-16 13:04:31 +00:00
|
|
|
|
|
|
|
//mxd. Update button image?
|
|
|
|
if(typehandler.DynamicImage)
|
|
|
|
{
|
|
|
|
combobox_Validating(sender, new CancelEventArgs());
|
|
|
|
button.Image = typehandler.BrowseImage;
|
|
|
|
}
|
2020-11-19 21:14:19 +00:00
|
|
|
else if(forcevalidate)
|
|
|
|
{
|
|
|
|
forcevalidate = false;
|
|
|
|
combobox_Validating(sender, new CancelEventArgs());
|
|
|
|
}
|
2022-02-19 10:21:28 +00:00
|
|
|
|
|
|
|
ValueChanged?.Invoke(sender, EventArgs.Empty);
|
2009-07-10 19:15:22 +00:00
|
|
|
}
|
2010-08-14 08:26:55 +00:00
|
|
|
|
|
|
|
// Mouse wheel used
|
|
|
|
private void combobox_MouseWheel(object sender, MouseEventArgs e)
|
|
|
|
{
|
|
|
|
if(scrollbuttons.Visible)
|
|
|
|
{
|
|
|
|
if(e.Delta < 0)
|
|
|
|
scrollbuttons.Value += 1;
|
|
|
|
else if(e.Delta > 0)
|
|
|
|
scrollbuttons.Value -= 1;
|
|
|
|
}
|
2020-11-19 21:14:19 +00:00
|
|
|
else
|
|
|
|
{
|
|
|
|
forcevalidate = true; // Make sure that the value is validated
|
|
|
|
}
|
2010-08-14 08:26:55 +00:00
|
|
|
}
|
2009-07-10 19:15:22 +00:00
|
|
|
|
|
|
|
// Scroll buttons clicked
|
|
|
|
private void scrollbuttons_ValueChanged(object sender, EventArgs e)
|
|
|
|
{
|
|
|
|
if(!ignorebuttonchange)
|
|
|
|
{
|
|
|
|
ignorebuttonchange = true;
|
|
|
|
if(!CheckIsRelative())
|
|
|
|
{
|
|
|
|
typehandler.SetValue(combobox.Text);
|
|
|
|
int newvalue = GetResult(0) - scrollbuttons.Value;
|
|
|
|
if(newvalue < 0) newvalue = 0;
|
|
|
|
combobox.Text = newvalue.ToString();
|
2009-07-23 09:43:51 +00:00
|
|
|
combobox_Validating(sender, new CancelEventArgs());
|
2009-07-10 19:15:22 +00:00
|
|
|
}
|
|
|
|
scrollbuttons.Value = 0;
|
|
|
|
ignorebuttonchange = false;
|
|
|
|
}
|
|
|
|
}
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
#endregion
|
|
|
|
|
|
|
|
#region ================== Methods
|
|
|
|
|
|
|
|
// This sets up the control for a specific argument
|
|
|
|
public void Setup(ArgumentInfo arginfo)
|
|
|
|
{
|
2013-09-11 09:47:53 +00:00
|
|
|
int oldvalue = 0;
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
// Get the original value
|
|
|
|
if(typehandler != null) oldvalue = typehandler.GetIntValue();
|
|
|
|
|
|
|
|
// Get the type handler
|
|
|
|
typehandler = General.Types.GetArgumentHandler(arginfo);
|
|
|
|
|
|
|
|
// Clear combobox
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Items.Clear();
|
|
|
|
|
2013-03-18 13:52:27 +00:00
|
|
|
// Check if this supports enumerated options
|
2014-12-08 21:06:08 +00:00
|
|
|
if(typehandler.IsEnumerable)
|
2014-12-03 23:15:26 +00:00
|
|
|
{
|
2013-03-18 13:52:27 +00:00
|
|
|
// Show the combobox
|
|
|
|
button.Visible = false;
|
|
|
|
scrollbuttons.Visible = false;
|
|
|
|
combobox.DropDownStyle = ComboBoxStyle.DropDown;
|
2009-04-19 18:07:22 +00:00
|
|
|
combobox.Items.AddRange(typehandler.GetEnumList().ToArray());
|
2013-08-13 09:49:29 +00:00
|
|
|
combobox.DropDownWidth = Tools.GetDropDownWidth(combobox); //mxd
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
// Check if browsable
|
|
|
|
else if(typehandler.IsBrowseable)
|
|
|
|
{
|
|
|
|
// Show the button
|
|
|
|
button.Visible = true;
|
2010-08-22 11:36:09 +00:00
|
|
|
button.Image = typehandler.BrowseImage;
|
2009-07-10 19:15:22 +00:00
|
|
|
scrollbuttons.Visible = false;
|
2009-04-19 18:07:22 +00:00
|
|
|
combobox.DropDownStyle = ComboBoxStyle.Simple;
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2009-07-10 19:15:22 +00:00
|
|
|
// Show textbox with scroll buttons
|
2009-04-19 18:07:22 +00:00
|
|
|
button.Visible = false;
|
2009-07-10 19:15:22 +00:00
|
|
|
scrollbuttons.Visible = true;
|
2009-04-19 18:07:22 +00:00
|
|
|
combobox.DropDownStyle = ComboBoxStyle.Simple;
|
|
|
|
}
|
2013-03-18 13:52:27 +00:00
|
|
|
|
|
|
|
//mxd
|
2014-12-08 21:06:08 +00:00
|
|
|
if(typehandler.IsEnumerable)
|
2014-12-03 23:15:26 +00:00
|
|
|
{
|
2013-03-18 13:52:27 +00:00
|
|
|
combobox.AutoCompleteMode = AutoCompleteMode.Suggest;
|
|
|
|
combobox.AutoCompleteSource = AutoCompleteSource.ListItems;
|
2014-12-03 23:15:26 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
2013-03-18 13:52:27 +00:00
|
|
|
combobox.AutoCompleteMode = AutoCompleteMode.None;
|
|
|
|
combobox.AutoCompleteSource = AutoCompleteSource.None;
|
|
|
|
}
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
// Setup layout
|
|
|
|
ArgumentBox_Resize(this, EventArgs.Empty);
|
|
|
|
|
2015-07-27 09:02:28 +00:00
|
|
|
//mxd. If not mixed values, re-apply the old value
|
|
|
|
if(!string.IsNullOrEmpty(combobox.Text)) SetValue(oldvalue);
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
// This sets the value
|
|
|
|
public void SetValue(int value)
|
|
|
|
{
|
|
|
|
typehandler.SetValue(value);
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = typehandler.GetStringValue();
|
|
|
|
combobox_Validating(this, new CancelEventArgs());
|
|
|
|
}
|
|
|
|
|
2013-09-11 09:47:53 +00:00
|
|
|
//mxd. this sets default value
|
2014-12-03 23:15:26 +00:00
|
|
|
public void SetDefaultValue()
|
|
|
|
{
|
2016-02-08 21:51:03 +00:00
|
|
|
typehandler.ApplyDefaultValue();
|
2013-09-11 09:47:53 +00:00
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = typehandler.GetStringValue();
|
|
|
|
combobox_Validating(this, new CancelEventArgs());
|
|
|
|
}
|
2012-07-10 10:20:45 +00:00
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
// This clears the value
|
|
|
|
public void ClearValue()
|
|
|
|
{
|
|
|
|
typehandler.SetValue("");
|
|
|
|
combobox.SelectedItem = null;
|
|
|
|
combobox.Text = "";
|
|
|
|
}
|
2009-07-10 19:15:22 +00:00
|
|
|
|
|
|
|
// This checks if the number is relative
|
|
|
|
public bool CheckIsRelative()
|
|
|
|
{
|
2016-08-29 11:32:31 +00:00
|
|
|
// Prefixed with +++, ---, <, >, ++ or --?
|
2016-08-29 10:06:16 +00:00
|
|
|
string str = combobox.Text.Trim();
|
2016-08-29 11:32:31 +00:00
|
|
|
return (str.StartsWith("+++") || str.StartsWith("---")
|
|
|
|
|| str.StartsWith("++") || str.StartsWith("--")
|
|
|
|
|| str.StartsWith("<") || str.StartsWith(">"));
|
2009-07-10 19:15:22 +00:00
|
|
|
}
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
// This returns the selected value
|
2016-08-29 10:06:16 +00:00
|
|
|
public int GetResult(int original) { return GetResult(original, 0); } //mxd
|
2016-08-29 11:32:31 +00:00
|
|
|
public int GetResult(int original, int step)
|
2009-04-19 18:07:22 +00:00
|
|
|
{
|
2014-02-21 14:42:12 +00:00
|
|
|
int result;
|
2010-08-14 10:21:38 +00:00
|
|
|
|
2009-04-19 18:07:22 +00:00
|
|
|
// Strip prefixes
|
|
|
|
string str = combobox.Text.Trim().ToLowerInvariant();
|
2016-08-29 11:32:31 +00:00
|
|
|
string numstr = str.TrimStart('+', '-', '<', '>'); //mxd
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
// Anything in the box?
|
2016-08-29 10:06:16 +00:00
|
|
|
if(numstr.Length > 0)
|
2009-04-19 18:07:22 +00:00
|
|
|
{
|
2016-08-29 10:06:16 +00:00
|
|
|
//mxd. Prefixed with +++?
|
|
|
|
if(str.StartsWith("+++"))
|
|
|
|
{
|
|
|
|
// Add offset to number
|
|
|
|
int num;
|
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
2016-08-29 11:32:31 +00:00
|
|
|
result = original + num * step;
|
2016-08-29 10:06:16 +00:00
|
|
|
}
|
|
|
|
//mxd. Prefixed with ---?
|
|
|
|
else if(str.StartsWith("---"))
|
|
|
|
{
|
|
|
|
// Subtract offset from number
|
|
|
|
int num;
|
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
2016-08-29 11:32:31 +00:00
|
|
|
result = original - num * step;
|
|
|
|
}
|
|
|
|
// mxd. Prefixed with <?
|
|
|
|
else if(str.StartsWith("<"))
|
|
|
|
{
|
|
|
|
// Incremental decrease
|
|
|
|
int num;
|
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
|
|
|
result = num - step;
|
|
|
|
}
|
|
|
|
// mxd. Prefixed with >?
|
|
|
|
else if(str.StartsWith(">"))
|
|
|
|
{
|
|
|
|
// Incremental increase
|
|
|
|
int num;
|
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
|
|
|
result = num + step;
|
2016-08-29 10:06:16 +00:00
|
|
|
}
|
2009-04-19 18:07:22 +00:00
|
|
|
// Prefixed with ++?
|
2016-08-29 10:06:16 +00:00
|
|
|
else if(str.StartsWith("++"))
|
2009-04-19 18:07:22 +00:00
|
|
|
{
|
|
|
|
// Add number to original
|
2015-12-28 15:01:53 +00:00
|
|
|
int num;
|
2016-08-29 10:06:16 +00:00
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
2010-08-14 10:21:38 +00:00
|
|
|
result = original + num;
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
// Prefixed with --?
|
2016-08-29 10:06:16 +00:00
|
|
|
else if(str.StartsWith("--"))
|
2009-04-19 18:07:22 +00:00
|
|
|
{
|
|
|
|
// Subtract number from original
|
2015-12-28 15:01:53 +00:00
|
|
|
int num;
|
2016-08-29 10:06:16 +00:00
|
|
|
if(!int.TryParse(numstr, out num)) num = 0;
|
2010-08-14 10:21:38 +00:00
|
|
|
result = original - num;
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Return the value
|
2010-08-14 10:21:38 +00:00
|
|
|
result = typehandler.GetIntValue();
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
else
|
|
|
|
{
|
|
|
|
// Just return the original
|
2010-08-14 10:21:38 +00:00
|
|
|
result = original;
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
2010-08-14 10:21:38 +00:00
|
|
|
|
|
|
|
return General.Clamp(result, General.Map.FormatInterface.MinArgument, General.Map.FormatInterface.MaxArgument);
|
2009-04-19 18:07:22 +00:00
|
|
|
}
|
2013-03-18 13:52:27 +00:00
|
|
|
|
|
|
|
//mxd. Very tricky way to close parent control by pressing ENTER or ESCAPE key when combobox.DropDownStyle == ComboBoxStyle.Simple
|
2014-12-03 23:15:26 +00:00
|
|
|
protected override bool ProcessCmdKey(ref Message msg, Keys keyData)
|
|
|
|
{
|
|
|
|
if(this.ActiveControl == combobox && combobox.DropDownStyle == ComboBoxStyle.Simple
|
|
|
|
&& (keyData == Keys.Return || keyData == Keys.Escape))
|
|
|
|
{
|
2013-03-18 13:52:27 +00:00
|
|
|
combobox.DropDownStyle = ComboBoxStyle.DropDown;
|
|
|
|
return false;
|
|
|
|
}
|
|
|
|
|
|
|
|
return base.ProcessCmdKey(ref msg, keyData);
|
|
|
|
}
|
2009-04-19 18:07:22 +00:00
|
|
|
|
|
|
|
#endregion
|
|
|
|
}
|
|
|
|
}
|