1895 lines
51 KiB
C#
1895 lines
51 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.ComponentModel;
|
|
using System.Drawing;
|
|
using System.Drawing.Design;
|
|
using System.Globalization;
|
|
using System.Windows.Forms;
|
|
using DevComponents.Instrumentation.Primitives;
|
|
|
|
namespace DevComponents.Instrumentation
|
|
{
|
|
public class GaugeScaleCollection : GenericCollection<GaugeScale>
|
|
{
|
|
}
|
|
|
|
public class GaugeScale : GaugeItem
|
|
{
|
|
#region Private variables
|
|
|
|
private GaugeScaleStyle _Style;
|
|
|
|
private float _Width;
|
|
|
|
private double _MinValue;
|
|
private double _MaxValue;
|
|
|
|
private double _MaxLimit;
|
|
private double _MinLimit;
|
|
|
|
private Color _BorderColor;
|
|
private int _BorderWidth;
|
|
|
|
private GaugeIntervalLabel _Labels;
|
|
private GaugeCustomLabelCollection _CustomLabels;
|
|
private GaugePointerCollection _Pointers;
|
|
private GaugeRangeCollection _Ranges;
|
|
private GaugeSectionCollection _Sections;
|
|
|
|
private GaugeTickMark _MajorTickMarks;
|
|
private GaugeTickMark _MinorTickMarks;
|
|
|
|
private List<TickPoint> _TickMarkList;
|
|
|
|
private GaugePin _MaxPin;
|
|
private GaugePin _MinPin;
|
|
|
|
private bool _Reversed;
|
|
|
|
private GaugeControl _GaugeControl;
|
|
|
|
private Rectangle _Bounds;
|
|
private Point _Center;
|
|
|
|
#endregion
|
|
|
|
public GaugeScale(GaugeControl gaugeControl)
|
|
: this()
|
|
{
|
|
_GaugeControl = gaugeControl;
|
|
}
|
|
|
|
public GaugeScale()
|
|
{
|
|
_Style = GaugeScaleStyle.Circular;
|
|
|
|
InitGaugeScale();
|
|
|
|
HookEvents(true);
|
|
}
|
|
|
|
#region InitGaugeScale
|
|
|
|
private void InitGaugeScale()
|
|
{
|
|
_Labels = new GaugeIntervalLabel(this);
|
|
|
|
_MajorTickMarks = new GaugeTickMark(this,
|
|
GaugeTickMarkRank.Major, GaugeMarkerStyle.Trapezoid, .09f, .14f, 10);
|
|
|
|
_MinorTickMarks = new GaugeTickMark(this,
|
|
GaugeTickMarkRank.Minor, GaugeMarkerStyle.Rectangle, .045f, .1f, 2);
|
|
|
|
_MaxPin = new GaugePin(this, true, "MaxPin");
|
|
_MinPin = new GaugePin(this, false, "MinPin");
|
|
|
|
_BorderColor = Color.Black;
|
|
_BorderWidth = 0;
|
|
|
|
_MinValue = 0;
|
|
_MaxValue = 100;
|
|
|
|
_MinLimit = double.NaN;
|
|
_MaxLimit = double.NaN;
|
|
|
|
_Width = .065f;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Hidden properties
|
|
|
|
#region Tooltip
|
|
|
|
[Browsable(false), EditorBrowsable(EditorBrowsableState.Never)]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
|
|
public new string Tooltip
|
|
{
|
|
get { return (base.Tooltip); }
|
|
set { base.Tooltip = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region Public properties
|
|
|
|
#region BorderColor
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Color of the Border
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance"), DefaultValue(typeof(Color), "Black")]
|
|
[Description("Indicates the Color of the Border.")]
|
|
public Color BorderColor
|
|
{
|
|
get { return (_BorderColor); }
|
|
|
|
set
|
|
{
|
|
if (_BorderColor != value)
|
|
{
|
|
_BorderColor = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region BorderWidth
|
|
|
|
/// <summary>
|
|
/// Gets or sets the width of the Border, specified as pixels
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance"), DefaultValue(0)]
|
|
[Description("Indicates the width of the Border, specified as pixels.")]
|
|
public int BorderWidth
|
|
{
|
|
get { return (_BorderWidth); }
|
|
|
|
set
|
|
{
|
|
if (value < 0)
|
|
throw new ArgumentException("Value can not be less than zero.");
|
|
|
|
if (_BorderWidth != value)
|
|
{
|
|
_BorderWidth = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Bounds
|
|
|
|
/// <summary>
|
|
/// Gets the Bounds of the scale
|
|
/// </summary>
|
|
[Browsable(false), EditorBrowsable(EditorBrowsableState.Never)]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
|
|
public Rectangle Bounds
|
|
{
|
|
get { return (_Bounds); }
|
|
internal set { _Bounds = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region CustomLabels
|
|
|
|
/// <summary>
|
|
/// Gets or sets the collection of Custom Labels
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the collection of Custom Labels associated with the Scale.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
[Editor("DevComponents.Instrumentation.Design.GaugeCollectionEditor, DevComponents.Instrumentation.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=76cb4c6eb576bca5", typeof(UITypeEditor))]
|
|
public GaugeCustomLabelCollection CustomLabels
|
|
{
|
|
get
|
|
{
|
|
if (_CustomLabels == null)
|
|
{
|
|
_CustomLabels = new GaugeCustomLabelCollection();
|
|
_CustomLabels.CollectionChanged += CustomLabels_CollectionChanged;
|
|
}
|
|
|
|
return (_CustomLabels);
|
|
}
|
|
|
|
set
|
|
{
|
|
if (_CustomLabels != null)
|
|
_CustomLabels.CollectionChanged -= CustomLabels_CollectionChanged;
|
|
|
|
_CustomLabels = value;
|
|
|
|
if (_CustomLabels != null)
|
|
_CustomLabels.CollectionChanged += CustomLabels_CollectionChanged;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GaugeControl
|
|
|
|
/// <summary>
|
|
/// Gets the associated GaugeControl
|
|
/// </summary>
|
|
[Browsable(false)]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
|
|
public GaugeControl GaugeControl
|
|
{
|
|
get { return (_GaugeControl); }
|
|
internal set { _GaugeControl = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Labels
|
|
|
|
/// <summary>
|
|
/// Gets the default Scale Label properties
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the default Scale Label properties.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public GaugeIntervalLabel Labels
|
|
{
|
|
get { return (_Labels); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MajorTickMarks
|
|
|
|
/// <summary>
|
|
/// Gets the Scale MajorTickMarks
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the Scale MajorTickMarks.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public GaugeTickMark MajorTickMarks
|
|
{
|
|
get { return (_MajorTickMarks); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MinorTickMarks
|
|
|
|
/// <summary>
|
|
/// Gets the Scale MinorTickMarks
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the Scale MinorTickMarks.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public GaugeTickMark MinorTickMarks
|
|
{
|
|
get { return (_MinorTickMarks); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MaxPin
|
|
|
|
/// <summary>
|
|
/// Gets the properties for the Scale Maximum Pin
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout")]
|
|
[Description("Specifies properties for the Scale Maximum Pin.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public GaugePin MaxPin
|
|
{
|
|
get { return (_MaxPin); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MinPin
|
|
|
|
/// <summary>
|
|
/// Gets the properties for the Scale Minimum Pin
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout")]
|
|
[Description("Specifies properties for the Scale Minimum Pin.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public GaugePin MinPin
|
|
{
|
|
get { return (_MinPin); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MinLimit
|
|
|
|
/// <summary>
|
|
/// Gets or sets the absolute minimum value for the scale.
|
|
/// Setting this values will permit the scale to scroll beyond the
|
|
/// current MinValue range.
|
|
///
|
|
/// Both MinLimit and MaxLimit values must both be set to
|
|
/// valid min/max values, or both reset to their defaults (double.NaN)
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout"), DefaultValue(double.NaN)]
|
|
[Description("Indicates the absolute minimum value for the scale. Setting this values will permit the scale to scroll beyond the current MinValue range.")]
|
|
|
|
public double MinLimit
|
|
{
|
|
get { return (_MinLimit); }
|
|
|
|
set
|
|
{
|
|
if (_MinLimit != value)
|
|
{
|
|
if (value.Equals(double.NaN) == false)
|
|
{
|
|
if (_MaxLimit.Equals(double.NaN) && value >= _MaxLimit)
|
|
throw new ArgumentException("MinLimit must be less than MaxLimit.");
|
|
|
|
if (value > _MinValue)
|
|
throw new ArgumentException("MinLimit must be less or equal to MinValue.");
|
|
}
|
|
|
|
_MinLimit = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MaxLimit
|
|
|
|
/// <summary>
|
|
/// Gets or sets the absolute maximum value for the scale.
|
|
/// Setting this values will permit the scale to scroll beyond the
|
|
/// current MaxValue range.
|
|
///
|
|
/// Both MinLimit and MaxLimit values must both be set to
|
|
/// valid min/max values, or both reset to their defaults (double.NaN)
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout"), DefaultValue(double.NaN)]
|
|
[Description("Indicates the absolute minimum value for the scale. Setting this values will permit the scale to scroll beyond the current MinValue range.")]
|
|
|
|
public double MaxLimit
|
|
{
|
|
get { return (_MaxLimit); }
|
|
|
|
set
|
|
{
|
|
if (_MaxLimit != value)
|
|
{
|
|
if (value.Equals(double.NaN) == false)
|
|
{
|
|
if (_MinLimit.Equals(double.NaN) && value <= _MinLimit)
|
|
throw new ArgumentException("MaxLimit must be greater than MinLimit.");
|
|
|
|
if (value < _MaxValue)
|
|
throw new ArgumentException("MaxLimit must be greater or equal to MaxValue.");
|
|
}
|
|
|
|
_MaxLimit = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MaxValue
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Maximum value for the Scale
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout"), DefaultValue(100d)]
|
|
[Description("Indicates the Maximum value for the Scale.")]
|
|
public double MaxValue
|
|
{
|
|
get { return (_MaxValue); }
|
|
|
|
set
|
|
{
|
|
if (_MaxValue != value)
|
|
{
|
|
if (_MaxLimit.Equals(double.NaN) == false && value > _MaxLimit)
|
|
throw new ArgumentException("Value must be less than or equal to MaxLimit.");
|
|
|
|
_MaxValue = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MinValue
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Minimum value for the Scale
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout"), DefaultValue(0d)]
|
|
[Description("Indicates the Minimum value for the Scale.")]
|
|
public double MinValue
|
|
{
|
|
get { return (_MinValue); }
|
|
|
|
set
|
|
{
|
|
if (_MinValue != value)
|
|
{
|
|
if (_MinLimit.Equals(double.NaN) == false && value < _MinLimit)
|
|
throw new ArgumentException("Value must be less than or equal to MinLimit.");
|
|
|
|
_MinValue = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Pointers
|
|
|
|
/// <summary>
|
|
/// Gets the collection of Pointers associated with the Scale
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the collection of Pointers associated with the Scale.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
[Editor("DevComponents.Instrumentation.Design.GaugeCollectionEditor, DevComponents.Instrumentation.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=76cb4c6eb576bca5", typeof(UITypeEditor))]
|
|
public GaugePointerCollection Pointers
|
|
{
|
|
get
|
|
{
|
|
if (_Pointers == null)
|
|
{
|
|
_Pointers = new GaugePointerCollection();
|
|
_Pointers.CollectionChanged += Pointers_CollectionChanged;
|
|
}
|
|
|
|
return (_Pointers);
|
|
}
|
|
|
|
set
|
|
{
|
|
if (_Pointers != null)
|
|
_Pointers.CollectionChanged -= Pointers_CollectionChanged;
|
|
|
|
_Pointers = value;
|
|
|
|
if (_Pointers != null)
|
|
_Pointers.CollectionChanged += Pointers_CollectionChanged;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Ranges
|
|
|
|
/// <summary>
|
|
/// Gets the collection of Ranges associated with the Scale
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the collection of Ranges associated with the Scale.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
[Editor("DevComponents.Instrumentation.Design.GaugeCollectionEditor, DevComponents.Instrumentation.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=76cb4c6eb576bca5", typeof(UITypeEditor))]
|
|
public GaugeRangeCollection Ranges
|
|
{
|
|
get
|
|
{
|
|
if (_Ranges == null)
|
|
{
|
|
_Ranges = new GaugeRangeCollection();
|
|
_Ranges.CollectionChanged += Ranges_CollectionChanged;
|
|
}
|
|
|
|
return (_Ranges);
|
|
}
|
|
|
|
set
|
|
{
|
|
if (_Ranges != null)
|
|
_Ranges.CollectionChanged -= Ranges_CollectionChanged;
|
|
|
|
_Ranges = value;
|
|
|
|
if (_Ranges != null)
|
|
_Ranges.CollectionChanged += Ranges_CollectionChanged;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Reversed
|
|
|
|
/// <summary>
|
|
/// Gets or sets whether the Scale min/max direction is reversed
|
|
/// </summary>
|
|
[Browsable(true), Category("Layout"), DefaultValue(false)]
|
|
[Description("Indicates that the Scale min/max direction is reversed.")]
|
|
public bool Reversed
|
|
{
|
|
get { return (_Reversed); }
|
|
|
|
set
|
|
{
|
|
if (_Reversed != value)
|
|
{
|
|
_Reversed = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Sections
|
|
|
|
/// <summary>
|
|
/// Gets the collection of Sections associated with the Scale
|
|
/// </summary>
|
|
[Browsable(true), Category("Appearance")]
|
|
[Description("Indicates the collection of Sections associated with the Scale.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
[Editor("DevComponents.Instrumentation.Design.GaugeCollectionEditor, DevComponents.Instrumentation.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=76cb4c6eb576bca5", typeof(UITypeEditor))]
|
|
[NotifyParentProperty(true)]
|
|
public GaugeSectionCollection Sections
|
|
{
|
|
get
|
|
{
|
|
if (_Sections == null)
|
|
{
|
|
_Sections = new GaugeSectionCollection();
|
|
_Sections.CollectionChanged += Sections_CollectionChanged;
|
|
}
|
|
|
|
return (_Sections);
|
|
}
|
|
|
|
set
|
|
{
|
|
if (_Sections != null)
|
|
_Sections.CollectionChanged -= Sections_CollectionChanged;
|
|
|
|
_Sections = value;
|
|
|
|
if (_Sections != null)
|
|
_Sections.CollectionChanged += Sections_CollectionChanged;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Width
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Width of the Scale, specified as a percentage
|
|
/// </summary>
|
|
[Browsable(true)]
|
|
[Category("Layout"), DefaultValue(.065f)]
|
|
[Editor("DevComponents.Instrumentation.Design.WidthRangeValueEditor, DevComponents.Instrumentation.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=76cb4c6eb576bca5", typeof(UITypeEditor))]
|
|
[Description("Indicates the Width of the Scale, specified as a percentage.")]
|
|
public float Width
|
|
{
|
|
get { return (_Width); }
|
|
|
|
set
|
|
{
|
|
if (value < 0)
|
|
throw new ArgumentException("Value can not be less than zero.");
|
|
|
|
if (_Width != value)
|
|
{
|
|
_Width = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region Internal properties
|
|
|
|
#region AbsMaxLimit
|
|
|
|
internal double AbsMaxLimit
|
|
{
|
|
get { return (_MaxLimit.Equals(double.NaN) ? _MaxValue : _MaxLimit); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region AbsMinLimit
|
|
|
|
internal double AbsMinLimit
|
|
{
|
|
get { return (_MinLimit.Equals(double.NaN) ? _MinValue : _MinLimit); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Center
|
|
|
|
internal Point Center
|
|
{
|
|
get { return (_Center); }
|
|
set { _Center = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region HasCustomLabels
|
|
|
|
internal bool HasCustomLabels
|
|
{
|
|
get { return (_CustomLabels != null); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region HasPointers
|
|
|
|
internal bool HasPointers
|
|
{
|
|
get { return (_Pointers != null); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region HasRanges
|
|
|
|
internal bool HasRanges
|
|
{
|
|
get { return (_Ranges != null); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region HasSections
|
|
|
|
internal bool HasSections
|
|
{
|
|
get { return (_Sections != null); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MaxPinEndOffset
|
|
|
|
internal float MaxPinEndOffset
|
|
{
|
|
get
|
|
{
|
|
if (_MaxPin != null && _MaxPin.Visible == true)
|
|
return (_MaxPin.EndOffset);
|
|
|
|
return (0);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MinPinEndOffset
|
|
|
|
internal float MinPinEndOffset
|
|
{
|
|
get
|
|
{
|
|
if (_MinPin != null && _MinPin.Visible == true)
|
|
return (_MinPin.EndOffset);
|
|
|
|
return (0);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedLabelRecalcLayout
|
|
|
|
internal bool NeedLabelRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
_Labels.NeedRecalcLayout = true;
|
|
|
|
if (_CustomLabels != null)
|
|
{
|
|
for (int i = 0; i < _CustomLabels.Count; i++)
|
|
{
|
|
GaugeCustomLabel label = _CustomLabels[i];
|
|
|
|
if (label.Visible == true)
|
|
label.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedPinRecalcLayout
|
|
|
|
internal bool NeedPinRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
if (_MinPin != null)
|
|
_MinPin.NeedRecalcLayout = true;
|
|
|
|
if (_MaxPin != null)
|
|
_MaxPin.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedPointerRecalcLayout
|
|
|
|
internal bool NeedPointerRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
if (_Pointers != null)
|
|
{
|
|
for (int i = 0; i < _Pointers.Count; i++)
|
|
{
|
|
GaugePointer pointer = _Pointers[i];
|
|
|
|
if (pointer.Visible == true)
|
|
pointer.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedRangeRecalcLayout
|
|
|
|
internal bool NeedRangeRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
if (_Ranges != null)
|
|
{
|
|
for (int i = 0; i < _Ranges.Count; i++)
|
|
{
|
|
GaugeRange range = _Ranges[i];
|
|
|
|
if (range.Visible == true)
|
|
range.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedSectionRecalcLayout
|
|
|
|
internal bool NeedSectionRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
if (_Sections != null)
|
|
{
|
|
for (int i = 0; i < _Sections.Count; i++)
|
|
{
|
|
GaugeSection section = _Sections[i];
|
|
|
|
if (section.Visible == true)
|
|
section.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region NeedTickMarkRecalcLayout
|
|
|
|
internal bool NeedTickMarkRecalcLayout
|
|
{
|
|
set
|
|
{
|
|
if (value == true)
|
|
{
|
|
_MajorTickMarks.NeedRecalcLayout = true;
|
|
_MinorTickMarks.NeedRecalcLayout = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Spread
|
|
|
|
internal double Spread
|
|
{
|
|
get { return (_MaxValue - _MinValue); }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Style
|
|
|
|
internal GaugeScaleStyle Style
|
|
{
|
|
get { return (_Style); }
|
|
|
|
set
|
|
{
|
|
if (_Style != value)
|
|
{
|
|
_Style = value;
|
|
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region HookEvents
|
|
|
|
private void HookEvents(bool hook)
|
|
{
|
|
if (hook == true)
|
|
{
|
|
_MajorTickMarks.GaugeItemChanged += MajorTickMarks_GaugeItemChanged;
|
|
_MinorTickMarks.GaugeItemChanged += MinorTickMarks_GaugeItemChanged;
|
|
|
|
_MinPin.GaugeItemChanged += MinPin_GaugeItemChanged;
|
|
_MaxPin.GaugeItemChanged += MaxPin_GaugeItemChanged;
|
|
|
|
_Labels.GaugeItemChanged += Labels_GaugeItemChanged;
|
|
}
|
|
else
|
|
{
|
|
_MajorTickMarks.GaugeItemChanged -= MajorTickMarks_GaugeItemChanged;
|
|
_MinorTickMarks.GaugeItemChanged -= MinorTickMarks_GaugeItemChanged;
|
|
|
|
if (_Sections != null)
|
|
{
|
|
foreach (GaugeSection section in _Sections)
|
|
section.GaugeItemChanged -= Section_GaugeItemChanged;
|
|
|
|
_Sections.CollectionChanged -= Sections_CollectionChanged;
|
|
}
|
|
|
|
if (_Ranges != null)
|
|
_Ranges.CollectionChanged -= Ranges_CollectionChanged;
|
|
|
|
if (_Pointers != null)
|
|
_Pointers.CollectionChanged -= Pointers_CollectionChanged;
|
|
|
|
_Labels.GaugeItemChanged -= Labels_GaugeItemChanged;
|
|
|
|
if (_CustomLabels != null)
|
|
_CustomLabels.CollectionChanged -= CustomLabels_CollectionChanged;
|
|
|
|
_MinPin.GaugeItemChanged -= MinPin_GaugeItemChanged;
|
|
_MaxPin.GaugeItemChanged -= MaxPin_GaugeItemChanged;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Event processing
|
|
|
|
#region Section processing
|
|
|
|
void Sections_CollectionChanged(object sender, EventArgs e)
|
|
{
|
|
foreach (GaugeSection section in _Sections)
|
|
{
|
|
section.Scale = this;
|
|
section.NeedRecalcLayout = true;
|
|
|
|
if (section.FillColor.IsEmpty)
|
|
section.FillColor = new GradientFillColor(Color.Lime);
|
|
|
|
section.GaugeItemChanged -= Section_GaugeItemChanged;
|
|
section.GaugeItemChanged += Section_GaugeItemChanged;
|
|
|
|
section.StripCoverChanged -= StripCoverChanged;
|
|
section.StripCoverChanged += StripCoverChanged;
|
|
}
|
|
|
|
OnStripCoverChanged();
|
|
}
|
|
|
|
void Section_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Range processing
|
|
|
|
void Ranges_CollectionChanged(object sender, EventArgs e)
|
|
{
|
|
foreach (GaugeRange range in _Ranges)
|
|
{
|
|
range.Scale = this;
|
|
range.NeedRecalcLayout = true;
|
|
|
|
if (range.FillColor.IsEmpty)
|
|
{
|
|
range.FillColor = new GradientFillColor(Color.Lime, Color.Red);
|
|
range.FillColor.BorderColor = Color.Black;
|
|
range.FillColor.BorderWidth = 1;
|
|
}
|
|
|
|
range.GaugeItemChanged -= Range_GaugeItemChanged;
|
|
range.GaugeItemChanged += Range_GaugeItemChanged;
|
|
|
|
range.StripCoverChanged -= StripCoverChanged;
|
|
range.StripCoverChanged += StripCoverChanged;
|
|
}
|
|
|
|
OnStripCoverChanged();
|
|
}
|
|
|
|
void Range_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region StripCoverChanged
|
|
|
|
void StripCoverChanged(object sender, EventArgs e)
|
|
{
|
|
OnStripCoverChanged();
|
|
}
|
|
|
|
private void OnStripCoverChanged()
|
|
{
|
|
if (_GaugeControl != null && _GaugeControl.InitComplete == true)
|
|
{
|
|
UpdateValueData();
|
|
OnGaugeItemChanged();
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Pointer processing
|
|
|
|
void Pointers_CollectionChanged(object sender, EventArgs e)
|
|
{
|
|
foreach (GaugePointer pointer in _Pointers)
|
|
{
|
|
pointer.Scale = this;
|
|
pointer.NeedRecalcLayout = true;
|
|
|
|
if (pointer.FillColor.IsEmpty)
|
|
{
|
|
pointer.FillColor = new GradientFillColor(Color.WhiteSmoke, Color.Red);
|
|
pointer.FillColor.BorderColor = Color.Black;
|
|
pointer.FillColor.BorderWidth = 1;
|
|
}
|
|
|
|
pointer.GaugeItemChanged -= Pointer_GaugeItemChanged;
|
|
pointer.GaugeItemChanged += Pointer_GaugeItemChanged;
|
|
}
|
|
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
void Pointer_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Label processing
|
|
|
|
void Labels_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
void CustomLabels_CollectionChanged(object sender, EventArgs e)
|
|
{
|
|
if (_CustomLabels != null)
|
|
{
|
|
foreach (GaugeCustomLabel label in _CustomLabels)
|
|
{
|
|
label.Scale = this;
|
|
label.NeedRecalcLayout = true;
|
|
|
|
label.GaugeItemChanged -= CustomLabel_GaugeItemChanged;
|
|
label.GaugeItemChanged += CustomLabel_GaugeItemChanged;
|
|
}
|
|
|
|
OnGaugeItemChanged();
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region TickMark processing
|
|
|
|
void CustomLabel_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
void MajorTickMarks_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
void MinorTickMarks_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Pin processing
|
|
|
|
void MaxPin_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
|
|
void MinPin_GaugeItemChanged(object sender, EventArgs e)
|
|
{
|
|
OnGaugeItemChanged(true);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RecalcLayout
|
|
|
|
public override void RecalcLayout()
|
|
{
|
|
if (NeedRecalcLayout == true)
|
|
{
|
|
base.RecalcLayout();
|
|
|
|
NeedLabelRecalcLayout = true;
|
|
NeedSectionRecalcLayout = true;
|
|
NeedRangeRecalcLayout = true;
|
|
NeedTickMarkRecalcLayout = true;
|
|
NeedPointerRecalcLayout = true;
|
|
NeedPinRecalcLayout = true;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetIntervalValue
|
|
|
|
internal double GetIntervalValue(double interval)
|
|
{
|
|
return (Math.Round(_MinValue + interval, 10));
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSectionFillColor
|
|
|
|
internal GradientFillColor GetSectionFillColor(double interval, ColorSourceFillEntry entry)
|
|
{
|
|
if (_Sections != null)
|
|
{
|
|
if (interval.Equals(double.NaN) == true)
|
|
interval = 0;
|
|
|
|
double value = GetIntervalValue(interval);
|
|
|
|
for (int i = _Sections.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeSection section = _Sections[i];
|
|
|
|
if (section.Visible == true)
|
|
{
|
|
GradientFillColor fillColor = GetStripFillColor(value, entry, section);
|
|
|
|
if (fillColor != null)
|
|
return (fillColor);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRangeFillColor
|
|
|
|
internal GradientFillColor GetRangeFillColor(double interval, ColorSourceFillEntry entry)
|
|
{
|
|
if (_Ranges != null)
|
|
{
|
|
if (interval.Equals(double.NaN) == true)
|
|
interval = 0;
|
|
|
|
double value = _MinValue + interval;
|
|
|
|
for (int i = _Ranges.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeRange range = _Ranges[i];
|
|
|
|
if (range.Visible == true)
|
|
{
|
|
GradientFillColor fillColor = GetStripFillColor(value, entry, range);
|
|
|
|
if (fillColor != null)
|
|
return (fillColor);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetStripFillColor
|
|
|
|
internal GradientFillColor GetStripFillColor(
|
|
double value, ColorSourceFillEntry entry, GaugeStrip strip)
|
|
{
|
|
if (strip.ValueInRange(value) == true)
|
|
{
|
|
switch (entry)
|
|
{
|
|
case ColorSourceFillEntry.MajorTickMark:
|
|
if (strip.HasMajorTickMarkFillColor)
|
|
return (strip.MajorTickMarkFillColor);
|
|
break;
|
|
|
|
case ColorSourceFillEntry.MinorTickMark:
|
|
if (strip.HasMinorTickMarkFillColor)
|
|
return (strip.MinorTickMarkFillColor);
|
|
break;
|
|
|
|
case ColorSourceFillEntry.Pointer:
|
|
if (strip.HasPointerFillColor)
|
|
return (strip.PointerFillColor);
|
|
break;
|
|
|
|
case ColorSourceFillEntry.Cap:
|
|
if (strip.HasCapFillColor)
|
|
return (strip.CapFillColor);
|
|
break;
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSectionLabelColor
|
|
|
|
internal Color GetSectionLabelColor(double interval)
|
|
{
|
|
if (_Sections != null)
|
|
{
|
|
double value = _MinValue + interval;
|
|
|
|
for (int i = _Sections.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeSection section = _Sections[i];
|
|
|
|
if (section.Visible == true)
|
|
{
|
|
Color labelColor = GetStripLabelColor(value, section);
|
|
|
|
if (labelColor != Color.Empty)
|
|
return (labelColor);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (Color.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRangeLabelColor
|
|
|
|
internal Color GetRangeLabelColor(double interval)
|
|
{
|
|
if (_Ranges != null)
|
|
{
|
|
double value = _MinValue + interval;
|
|
|
|
for (int i = _Ranges.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeRange range = _Ranges[i];
|
|
|
|
if (range.Visible == true)
|
|
{
|
|
Color labelColor = GetStripLabelColor(value, range);
|
|
|
|
if (labelColor != Color.Empty)
|
|
return (labelColor);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (Color.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetStripLabelColor
|
|
|
|
internal Color GetStripLabelColor(double value, GaugeStrip strip)
|
|
{
|
|
if (strip.ValueInRange(value) == true)
|
|
return (strip.LabelColor);
|
|
|
|
return (Color.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FindItem
|
|
|
|
internal override GaugeItem FindItem(Point pt)
|
|
{
|
|
GaugeItem item;
|
|
|
|
if ((item = FindPointerItem(pt)) != null)
|
|
return (item);
|
|
|
|
if ((item = FindRangeItem(pt)) != null)
|
|
return (item);
|
|
|
|
if ((item = FindSectionItem(pt)) != null)
|
|
return (item);
|
|
|
|
if (_MinPin.Visible == true)
|
|
{
|
|
if (_MinPin.Bounds.Contains(pt))
|
|
return (_MinPin);
|
|
}
|
|
|
|
if (_MaxPin.Visible == true)
|
|
{
|
|
if (_MaxPin.Bounds.Contains(pt))
|
|
return (_MaxPin);
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#region FindPointerItem
|
|
|
|
internal GaugeItem FindPointerItem(Point pt)
|
|
{
|
|
if (HasPointers == true)
|
|
{
|
|
for (int i = Pointers.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugePointer pointer = Pointers[i];
|
|
|
|
if (pointer.Visible == true)
|
|
{
|
|
if (pointer.UnderTickMarks == false)
|
|
{
|
|
if (pointer.FindItem(pt) != null)
|
|
return (pointer);
|
|
}
|
|
}
|
|
}
|
|
|
|
for (int i = Pointers.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugePointer pointer = Pointers[i];
|
|
|
|
if (pointer.Visible == true)
|
|
{
|
|
if (pointer.UnderTickMarks == true)
|
|
{
|
|
if (pointer.FindItem(pt) != null)
|
|
return (pointer);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FindRangeItem
|
|
|
|
internal GaugeItem FindRangeItem(Point pt)
|
|
{
|
|
if (HasRanges == true)
|
|
{
|
|
for (int i = Ranges.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeRange range = Ranges[i];
|
|
|
|
if (range.Visible == true)
|
|
{
|
|
if (range.FindItem(pt) != null)
|
|
return (range);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FindSectionItem
|
|
|
|
internal GaugeItem FindSectionItem(Point pt)
|
|
{
|
|
if (HasSections == true)
|
|
{
|
|
for (int i = Sections.Count - 1; i >= 0; i--)
|
|
{
|
|
GaugeSection section = Sections[i];
|
|
|
|
if (section.Visible == true)
|
|
{
|
|
if (section.FindItem(pt) != null)
|
|
return (section);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region UpdateValueData
|
|
|
|
internal void UpdateValueData()
|
|
{
|
|
bool minNan = _MinLimit.Equals(double.NaN);
|
|
bool maxNan = _MaxLimit.Equals(double.NaN);
|
|
|
|
if (minNan != maxNan)
|
|
{
|
|
throw new Exception("MinLimit and MaxLimit must both either be set to " +
|
|
"valid min/max values, or both reset to their default values (double.NaN).");
|
|
}
|
|
|
|
if (_Pointers != null)
|
|
{
|
|
for (int i = 0; i < _Pointers.Count; i++)
|
|
{
|
|
GaugePointer pointer = _Pointers[i];
|
|
|
|
if (pointer.Visible == true)
|
|
pointer.UpdateStripData();
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region OnPaint
|
|
|
|
public override void OnPaint(PaintEventArgs e)
|
|
{
|
|
if (_MaxValue > _MinValue)
|
|
{
|
|
RecalcLayout();
|
|
|
|
if (GaugeControl.OnPreRenderScale(e, this) == false)
|
|
{
|
|
PaintRanges(e);
|
|
PaintSections(e);
|
|
PaintPointers(e, true);
|
|
PaintTickMarks(e);
|
|
PaintPins(e);
|
|
PaintLabels(e);
|
|
|
|
GaugeControl.OnPostRenderScale(e, this);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region PaintRanges
|
|
|
|
private void PaintRanges(PaintEventArgs e)
|
|
{
|
|
if (GaugeControl.OnPreRenderScaleRanges(e, this) == false)
|
|
{
|
|
if (_Ranges != null)
|
|
{
|
|
for (int i = 0; i < _Ranges.Count; i++)
|
|
{
|
|
GaugeRange range = _Ranges[i];
|
|
|
|
if (range.Visible == true)
|
|
range.OnPaint(e);
|
|
}
|
|
}
|
|
|
|
GaugeControl.OnPostRenderScaleRanges(e, this);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region PaintSections
|
|
|
|
private void PaintSections(PaintEventArgs e)
|
|
{
|
|
if (GaugeControl.OnPreRenderScaleSections(e, this) == false)
|
|
{
|
|
if (_Sections != null)
|
|
{
|
|
for (int i = 0; i < _Sections.Count; i++)
|
|
{
|
|
GaugeSection section = _Sections[i];
|
|
|
|
if (section.Visible == true)
|
|
section.OnPaint(e);
|
|
}
|
|
}
|
|
|
|
GaugeControl.OnPostRenderScaleSections(e, this);
|
|
}
|
|
|
|
PaintBorder(e);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region PaintBorder
|
|
|
|
protected virtual void PaintBorder(PaintEventArgs e)
|
|
{
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region PaintTickMarks
|
|
|
|
private void PaintTickMarks(PaintEventArgs e)
|
|
{
|
|
Graphics g = e.Graphics;
|
|
|
|
if (GaugeControl.OnPreRenderScaleTickMarks(e, this) == false)
|
|
{
|
|
BuildTickMarkList();
|
|
|
|
if (_TickMarkList != null)
|
|
{
|
|
foreach (TickPoint tp in _TickMarkList)
|
|
{
|
|
if (tp.TickMark.Visible == true)
|
|
tp.TickMark.PaintTickPoint(g, tp);
|
|
}
|
|
}
|
|
|
|
GaugeControl.OnPostRenderScaleTickMarks(e, this);
|
|
}
|
|
}
|
|
|
|
#region BuildTickMarkList
|
|
|
|
private void BuildTickMarkList()
|
|
{
|
|
if (TickMarkListIsValid() == false)
|
|
{
|
|
if (_TickMarkList != null)
|
|
_TickMarkList.Clear();
|
|
else
|
|
_TickMarkList = new List<TickPoint>();
|
|
|
|
AddMinorTickMarks();
|
|
AddMajorTickMarks();
|
|
AddCustomLabelTickMarks();
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region AddMinorTickMarks
|
|
|
|
private void AddMinorTickMarks()
|
|
{
|
|
if (_MinorTickMarks.Visible == true)
|
|
_MinorTickMarks.RecalcLayout();
|
|
|
|
if (_MinorTickMarks.TickPoints != null)
|
|
_TickMarkList.AddRange(_MinorTickMarks.TickPoints);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region AddMajorTickMarks
|
|
|
|
private void AddMajorTickMarks()
|
|
{
|
|
if (_MajorTickMarks.Visible == true)
|
|
{
|
|
_MajorTickMarks.RecalcLayout();
|
|
|
|
if (_MajorTickMarks.TickPoints != null)
|
|
{
|
|
if (_MajorTickMarks.Layout.Overlap == GaugeTickMarkOverlap.ReplaceNone)
|
|
{
|
|
_TickMarkList.AddRange(_MajorTickMarks.TickPoints);
|
|
}
|
|
else
|
|
{
|
|
foreach (TickPoint tp in _MajorTickMarks.TickPoints)
|
|
{
|
|
if (tp.Visible == true)
|
|
{
|
|
int n = GetTickPointIndex(tp, _MajorTickMarks.Layout.Overlap);
|
|
|
|
if (n >= 0)
|
|
_TickMarkList[n] = tp;
|
|
else
|
|
_TickMarkList.Add(tp);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region AddCustomLabelTickMarks
|
|
|
|
private void AddCustomLabelTickMarks()
|
|
{
|
|
if (_CustomLabels != null)
|
|
{
|
|
foreach (GaugeCustomLabel label in _CustomLabels)
|
|
{
|
|
label.RecalcLayout();
|
|
|
|
if (label.Visible == true)
|
|
{
|
|
TickPoint tp = label.TickMark.TickPoint;
|
|
|
|
if (tp != null && label.TickMark.Visible == true)
|
|
{
|
|
int n = -1;
|
|
|
|
if (tp.TickMark.Layout.Overlap != GaugeTickMarkOverlap.ReplaceNone)
|
|
n = GetTickPointIndex(tp, tp.TickMark.Layout.Overlap);
|
|
|
|
if (n >= 0)
|
|
_TickMarkList[n] = tp;
|
|
else
|
|
_TickMarkList.Add(tp);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetTickPointIndex
|
|
|
|
private int GetTickPointIndex(TickPoint tp, GaugeTickMarkOverlap overlap)
|
|
{
|
|
int n = -1;
|
|
double interval = GetIntervalValue(tp.Interval);
|
|
|
|
for (int i = _TickMarkList.Count - 1; i >= 0; i--)
|
|
{
|
|
if (GetIntervalValue(_TickMarkList[i].Interval) == interval)
|
|
{
|
|
if (overlap == GaugeTickMarkOverlap.ReplaceLast)
|
|
return (i);
|
|
|
|
if (n == -1)
|
|
{
|
|
n = i;
|
|
}
|
|
else
|
|
{
|
|
_TickMarkList.RemoveAt(n);
|
|
n = i;
|
|
}
|
|
}
|
|
}
|
|
|
|
return (n);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region TickMarkListIsValid
|
|
|
|
private bool TickMarkListIsValid()
|
|
{
|
|
if (_TickMarkList == null)
|
|
return (false);
|
|
|
|
if ((_MajorTickMarks.Visible == true && _MajorTickMarks.NeedRecalcLayout) ||
|
|
(_MinorTickMarks.Visible == true && _MinorTickMarks.NeedRecalcLayout))
|
|
{
|
|
return (false);
|
|
}
|
|
|
|
if (_CustomLabels != null)
|
|
{
|
|
for (int i = 0; i < _CustomLabels.Count; i++)
|
|
{
|
|
GaugeCustomLabel label = _CustomLabels[i];
|
|
|
|
if (label.NeedRecalcLayout)
|
|
return (false);
|
|
}
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region PaintPointers
|
|
|
|
internal void PaintPointers(PaintEventArgs e, bool under)
|
|
{
|
|
if (_MaxValue > _MinValue)
|
|
{
|
|
if (GaugeControl.OnPreRenderScalePointers(e, this) == false)
|
|
{
|
|
if (_Pointers != null)
|
|
{
|
|
for (int i = 0; i < _Pointers.Count; i++)
|
|
{
|
|
GaugePointer pointer = _Pointers[i];
|
|
|
|
if (pointer.Visible == true)
|
|
{
|
|
if (pointer.UnderTickMarks == under)
|
|
pointer.OnPaint(e);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
GaugeControl.OnPostRenderScalePointers(e, this);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region PaintPins
|
|
|
|
private void PaintPins(PaintEventArgs e)
|
|
{
|
|
if (_MinPin.Visible == true)
|
|
_MinPin.OnPaint(e);
|
|
|
|
if (_MaxPin.Visible == true)
|
|
_MaxPin.OnPaint(e);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region PaintLabels
|
|
|
|
private void PaintLabels(PaintEventArgs e)
|
|
{
|
|
if (_Labels.Visible == true)
|
|
_Labels.OnPaint(e);
|
|
|
|
if (_CustomLabels != null)
|
|
{
|
|
for (int i = 0; i < _CustomLabels.Count; i++)
|
|
{
|
|
GaugeCustomLabel label = _CustomLabels[i];
|
|
|
|
if (label.Visible == true)
|
|
label.OnPaint(e);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region OnDispose
|
|
|
|
protected override void OnDispose()
|
|
{
|
|
HookEvents(false);
|
|
|
|
base.OnDispose();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ICloneable Members
|
|
|
|
public override object Clone()
|
|
{
|
|
GaugeScale copy = new GaugeScale();
|
|
|
|
CopyToItem(copy);
|
|
|
|
return (copy);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region CopyToItem
|
|
|
|
public override void CopyToItem(GaugeItem copy)
|
|
{
|
|
GaugeScale c = copy as GaugeScale;
|
|
|
|
if (c != null)
|
|
{
|
|
base.CopyToItem(c);
|
|
|
|
c.BorderColor = _BorderColor;
|
|
c.BorderWidth = _BorderWidth;
|
|
|
|
c.MaxLimit = _MaxLimit;
|
|
c.MinLimit = _MinLimit;
|
|
c.MaxValue = _MaxValue;
|
|
c.MinValue = _MinValue;
|
|
|
|
c.Reversed = _Reversed;
|
|
c.Width = _Width;
|
|
|
|
_Labels.CopyToItem(c.Labels);
|
|
c.Labels.Scale = c;
|
|
|
|
_MajorTickMarks.CopyToItem(c.MajorTickMarks);
|
|
c.MajorTickMarks.Scale = c;
|
|
|
|
_MinorTickMarks.CopyToItem(c.MinorTickMarks);
|
|
c.MinorTickMarks.Scale = c;
|
|
|
|
_MaxPin.CopyToItem(c.MaxPin);
|
|
c.MaxPin.Scale = c;
|
|
|
|
_MinPin.CopyToItem(c.MinPin);
|
|
c.MinPin.Scale = c;
|
|
|
|
if (_CustomLabels != null)
|
|
{
|
|
c.CustomLabels = new GaugeCustomLabelCollection();
|
|
c.CustomLabels.CollectionChanged += CustomLabels_CollectionChanged;
|
|
|
|
_CustomLabels.CopyToItem(c.CustomLabels);
|
|
}
|
|
|
|
if (_Pointers != null)
|
|
{
|
|
c.Pointers = new GaugePointerCollection();
|
|
c.Pointers.CollectionChanged += Pointers_CollectionChanged;
|
|
|
|
_Pointers.CopyToItem(c.Pointers);
|
|
}
|
|
|
|
if (_Ranges != null)
|
|
{
|
|
c.Ranges = new GaugeRangeCollection();
|
|
c.Ranges.CollectionChanged += Ranges_CollectionChanged;
|
|
|
|
_Ranges.CopyToItem(c.Ranges);
|
|
}
|
|
|
|
if (_Sections != null)
|
|
{
|
|
c.Sections = new GaugeSectionCollection();
|
|
c.Sections.CollectionChanged += Sections_CollectionChanged;
|
|
|
|
_Sections.CopyToItem(c.Sections);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
}
|
|
|
|
#region Enums
|
|
|
|
public enum GaugeScaleStyle
|
|
{
|
|
Circular,
|
|
Linear
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GaugeScaleConvertor
|
|
|
|
public class GaugeScaleConvertor : ExpandableObjectConverter
|
|
{
|
|
public override object ConvertTo(
|
|
ITypeDescriptorContext context, CultureInfo culture, object value, Type destinationType)
|
|
{
|
|
if (destinationType == typeof(string))
|
|
{
|
|
GaugeScale scale = value as GaugeScale;
|
|
|
|
if (scale != null)
|
|
{
|
|
//ColorConverter cvt = new ColorConverter();
|
|
|
|
//if (lct.Start != Color.Empty)
|
|
// return (cvt.ConvertToString(lct.Start));
|
|
|
|
//if (lct.End != Color.Empty)
|
|
// return (cvt.ConvertToString(lct.End));
|
|
|
|
//if (lct.GradientAngle != 90)
|
|
// return (lct.GradientAngle.ToString());
|
|
|
|
return (String.Empty);
|
|
}
|
|
}
|
|
|
|
return (base.ConvertTo(context, culture, value, destinationType));
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
}
|