6532 lines
189 KiB
C#
6532 lines
189 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.ComponentModel;
|
|
using System.Drawing;
|
|
using System.Drawing.Design;
|
|
using System.Drawing.Drawing2D;
|
|
using System.Windows.Forms;
|
|
using DevComponents.DotNetBar.SuperGrid.Primitives;
|
|
using DevComponents.DotNetBar.SuperGrid.Style;
|
|
using DevComponents.SuperGrid.TextMarkup;
|
|
|
|
namespace DevComponents.DotNetBar.SuperGrid
|
|
{
|
|
/// <summary>
|
|
/// Represents a layout of column headers
|
|
/// </summary>
|
|
[TypeConverter(typeof(BlankExpandableObjectConverter))]
|
|
public class GridColumnHeader : GridElement
|
|
{
|
|
#region Constants
|
|
|
|
private const int SeparatorWidth = 2;
|
|
private const int ImageCacheSize = 8;
|
|
|
|
#endregion
|
|
|
|
#region Static data
|
|
|
|
private static object _lastSelectedItem;
|
|
|
|
#endregion
|
|
|
|
#region Private variables
|
|
|
|
private GridColumnCollection _Columns;
|
|
private ColumnGroupHeaderCollection _GroupHeaders;
|
|
|
|
private HeaderArea _HitArea;
|
|
private object _HitItem;
|
|
|
|
private HeaderArea _LastHitArea;
|
|
private object _LastHitItem;
|
|
|
|
private GridColumn _ResizeColumn;
|
|
|
|
private int _MouseDownDelta;
|
|
private HeaderArea _MouseDownHitArea;
|
|
private object _MouseDownHitItem;
|
|
|
|
private Point _MouseDownPoint;
|
|
private MouseButtons _MouseDownButtons;
|
|
|
|
private bool _DragSelection;
|
|
private bool _DragStarted;
|
|
|
|
private bool _Reordering;
|
|
private bool _Resizing;
|
|
private int _ResizeWidth;
|
|
|
|
private int _MinRowHeight;
|
|
private int _RowHeight;
|
|
|
|
private GridColumn _SeparatorColumn;
|
|
private bool _SeparatorIsRight;
|
|
|
|
private FloatWindow _HeaderFw;
|
|
private FloatWindow _SeparatorFw;
|
|
|
|
private int _OrderTextOffset;
|
|
private int _SelectAllCount;
|
|
|
|
private ColumnHeaderRowVisualStyles _EffectiveRowHeaderStyles;
|
|
private int _StyleUpdateCount;
|
|
|
|
private bool _ShowHeaderImages = true;
|
|
|
|
private Image _AscendingSortImage;
|
|
private int _AscendingSortImageIndex = -1;
|
|
private Image[] _AscendingSortCacheImages = new Image[ImageCacheSize];
|
|
|
|
private Image _DescendingSortImage;
|
|
private int _DescendingSortImageIndex = -1;
|
|
private Image[] _DescendingSortCacheImages = new Image[ImageCacheSize];
|
|
|
|
private Alignment _SortImageAlignment = Alignment.NotSet;
|
|
|
|
private Image _FilterImage;
|
|
private int _FilterImageIndex = -1;
|
|
private Image[] _FilterCacheImages = new Image[ImageCacheSize * 2];
|
|
|
|
private ImageVisibility _FilterImageVisibility = ImageVisibility.Auto;
|
|
private Alignment _FilterImageAlignment = Alignment.NotSet;
|
|
|
|
private FilterPopup _FilterMenu;
|
|
|
|
private bool _LockedColumn;
|
|
private bool _ShowFilterToolTips = true;
|
|
private bool _ShowToolTips = true;
|
|
private bool _ShowGroupColumnHeaders = true;
|
|
private bool _AutoApplyGroupColors = true;
|
|
|
|
private string _RowHeaderText;
|
|
|
|
#endregion
|
|
|
|
#region Internal properties
|
|
|
|
#region Columns
|
|
|
|
internal GridColumnCollection Columns
|
|
{
|
|
get { return (_Columns); }
|
|
set { _Columns = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RowHeaderBounds
|
|
|
|
internal Rectangle RowHeaderBounds
|
|
{
|
|
get
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
Rectangle r = Bounds;
|
|
r.Width = panel.RowHeaderWidthEx;
|
|
|
|
return (r);
|
|
}
|
|
|
|
return (Rectangle.Empty);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region SelectAllCount
|
|
|
|
internal int SelectAllCount
|
|
{
|
|
get { return (_SelectAllCount); }
|
|
set { _SelectAllCount = value; }
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region Public properties
|
|
|
|
#region AscendingSortImage
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Ascending sort image
|
|
/// </summary>
|
|
[DefaultValue(null), Category("Appearance")]
|
|
[Description("Indicates the Ascending sort image.")]
|
|
public Image AscendingSortImage
|
|
{
|
|
get { return (_AscendingSortImage); }
|
|
|
|
set
|
|
{
|
|
if (_AscendingSortImage != value)
|
|
{
|
|
_AscendingSortImage = value;
|
|
|
|
OnPropertyChangedEx("AscendingSortImage", VisualChangeType.Render);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetAscendingSortImage
|
|
|
|
internal Image GetAscendingSortImage(GridColumn column)
|
|
{
|
|
if (_AscendingSortImage != null)
|
|
return (_AscendingSortImage);
|
|
|
|
if (_AscendingSortImageIndex >= 0)
|
|
{
|
|
ImageList imageList = GridPanel.ImageList;
|
|
|
|
if (imageList != null && _AscendingSortImageIndex < imageList.Images.Count)
|
|
return (imageList.Images[_AscendingSortImageIndex]);
|
|
}
|
|
|
|
return (GetAscendingSortImageEx(column));
|
|
}
|
|
|
|
#region GetAscendingSortImageEx
|
|
|
|
internal Image GetAscendingSortImageEx(GridColumn column)
|
|
{
|
|
StyleState state = GetStyleState(column, column.IsSelected);
|
|
|
|
Image cacheImage = _AscendingSortCacheImages[(int)state];
|
|
|
|
if (cacheImage == null)
|
|
{
|
|
int width = Dpi.Width5;
|
|
int height = Dpi.Height3;
|
|
|
|
if ((width % 2) == 0)
|
|
width++;
|
|
|
|
Rectangle r = new Rectangle(0, 0, width, height);
|
|
Image image = new Bitmap(width, height);
|
|
|
|
using (Graphics g = Graphics.FromImage(image))
|
|
{
|
|
g.SmoothingMode = SmoothingMode.AntiAlias;
|
|
|
|
using (GraphicsPath path = new GraphicsPath())
|
|
{
|
|
Point pt = new Point(r.X + r.Width / 2, r.Top);
|
|
|
|
Point[] pts =
|
|
{
|
|
pt,
|
|
new Point(r.Right - 1, r.Bottom - 1),
|
|
new Point(r.Left, r.Bottom - 1),
|
|
pt
|
|
};
|
|
|
|
path.AddLines(pts);
|
|
|
|
ColumnHeaderRowVisualStyle style = GetEffectiveRowHeaderStyleEx(state);
|
|
|
|
Color color = style.SortIndicatorColor;
|
|
|
|
if (color.IsEmpty)
|
|
color = Color.Black;
|
|
|
|
using (Brush br = new SolidBrush(color))
|
|
g.FillPath(br, path);
|
|
|
|
using (Pen pen = new Pen(color))
|
|
g.DrawPath(pen, path);
|
|
}
|
|
}
|
|
|
|
_AscendingSortCacheImages[(int)state] = image;
|
|
|
|
cacheImage = image;
|
|
}
|
|
|
|
return (cacheImage);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region AscendingSortImageIndex
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Ascending Sort Image index
|
|
/// </summary>
|
|
[Browsable(true), DefaultValue(-1)]
|
|
[Category("Appearance"), Description("Indicates the Ascending Sort Image index.")]
|
|
[Editor("DevComponents.SuperGrid.Design.ImageIndexEditor, DevComponents.SuperGrid.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=26d81176cfa2b486", typeof(UITypeEditor))]
|
|
[TypeConverter(typeof(ImageIndexConverter))]
|
|
public int AscendingSortImageIndex
|
|
{
|
|
get { return (_AscendingSortImageIndex); }
|
|
|
|
set
|
|
{
|
|
if (_AscendingSortImageIndex != value)
|
|
{
|
|
_AscendingSortImageIndex = value;
|
|
|
|
OnPropertyChangedEx("AscendingSortImageIndex", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
[Browsable(false)]
|
|
[EditorBrowsable(EditorBrowsableState.Never)]
|
|
private void ResetAscendingSortImageIndex()
|
|
{
|
|
_AscendingSortImageIndex = -1;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region AutoApplyGroupColors
|
|
|
|
/// <summary>
|
|
/// Gets or sets whether Group Header color properties
|
|
/// (ie. Background and TextColor) are automatically
|
|
/// applied to group Column Headers.
|
|
/// </summary>
|
|
[DefaultValue(true), Category("Appearance")]
|
|
[Description("Indicates whether Group Header color properties (ie. Background and TextColor) are automatically applied to group Column Headers.")]
|
|
public bool AutoApplyGroupColors
|
|
{
|
|
get { return (_AutoApplyGroupColors); }
|
|
|
|
set
|
|
{
|
|
if (_AutoApplyGroupColors != value)
|
|
{
|
|
_AutoApplyGroupColors = value;
|
|
|
|
OnPropertyChangedEx("AutoApplyGroupColors", VisualChangeType.Render);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Bounds
|
|
|
|
///<summary>
|
|
/// Gets the scroll adjusted bounds
|
|
///</summary>
|
|
[Browsable(false)]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Hidden)]
|
|
public override Rectangle Bounds
|
|
{
|
|
get
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
Rectangle r = BoundsRelative;
|
|
|
|
if (panel.IsSubPanel == true)
|
|
{
|
|
r.X -= HScrollOffset;
|
|
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
return (Rectangle.Empty);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region DescendingSortImage
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Descending sort image
|
|
/// </summary>
|
|
[DefaultValue(null), Category("Appearance")]
|
|
[Description("Indicates the Descending sort image.")]
|
|
public Image DescendingSortImage
|
|
{
|
|
get { return (_DescendingSortImage); }
|
|
|
|
set
|
|
{
|
|
if (_DescendingSortImage != value)
|
|
{
|
|
_DescendingSortImage = value;
|
|
|
|
OnPropertyChangedEx("DescendingSortImage", VisualChangeType.Render);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetDescendingSortImage
|
|
|
|
internal Image GetDescendingSortImage(GridColumn column)
|
|
{
|
|
if (_DescendingSortImage != null)
|
|
return (_DescendingSortImage);
|
|
|
|
if (_DescendingSortImageIndex >= 0)
|
|
{
|
|
ImageList imageList = GridPanel.ImageList;
|
|
|
|
if (imageList != null && _DescendingSortImageIndex < imageList.Images.Count)
|
|
return (imageList.Images[_DescendingSortImageIndex]);
|
|
}
|
|
|
|
return (GetDescendingSortImageEx(column));
|
|
}
|
|
|
|
#region GetDescendingSortImageEx
|
|
|
|
internal Image GetDescendingSortImageEx(GridColumn column)
|
|
{
|
|
StyleState state = GetStyleState(column, column.IsSelected);
|
|
|
|
Image cacheImage = _DescendingSortCacheImages[(int)state];
|
|
|
|
if (cacheImage == null)
|
|
{
|
|
int width = Dpi.Width5;
|
|
int height = Dpi.Height3;
|
|
|
|
if ((width % 2) == 0)
|
|
width++;
|
|
|
|
Rectangle r = new Rectangle(0, 0, width, height);
|
|
Image image = new Bitmap(width, height);
|
|
|
|
using (Graphics g = Graphics.FromImage(image))
|
|
{
|
|
g.SmoothingMode = SmoothingMode.AntiAlias;
|
|
|
|
using (GraphicsPath path = new GraphicsPath())
|
|
{
|
|
Point pt = new Point(r.X + width / 2, r.Bottom - 1);
|
|
|
|
Point[] pts =
|
|
{
|
|
pt,
|
|
new Point(r.Right - 1, r.Top),
|
|
new Point(r.Left, r.Top),
|
|
pt
|
|
};
|
|
|
|
path.AddLines(pts);
|
|
|
|
ColumnHeaderRowVisualStyle style = GetEffectiveRowHeaderStyleEx(state);
|
|
|
|
Color color = style.SortIndicatorColor;
|
|
|
|
if (color.IsEmpty)
|
|
color = Color.Black;
|
|
|
|
using (Brush br = new SolidBrush(color))
|
|
g.FillPath(br, path);
|
|
|
|
using (Pen pen = new Pen(color))
|
|
g.DrawPath(pen, path);
|
|
}
|
|
}
|
|
|
|
_DescendingSortCacheImages[(int)state] = image;
|
|
|
|
cacheImage = image;
|
|
}
|
|
|
|
return (cacheImage);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region DescendingSortImageIndex
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Descending Sort Image index
|
|
/// </summary>
|
|
[Browsable(true), DefaultValue(-1)]
|
|
[Category("Appearance"), Description("Indicates the Descending Sort Image index.")]
|
|
[Editor("DevComponents.SuperGrid.Design.ImageIndexEditor, DevComponents.SuperGrid.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=26d81176cfa2b486", typeof(UITypeEditor))]
|
|
[TypeConverter(typeof(ImageIndexConverter))]
|
|
public int DescendingSortImageIndex
|
|
{
|
|
get { return (_DescendingSortImageIndex); }
|
|
|
|
set
|
|
{
|
|
if (_DescendingSortImageIndex != value)
|
|
{
|
|
_DescendingSortImageIndex = value;
|
|
|
|
OnPropertyChangedEx("DescendingSortImageIndex", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
[Browsable(false)]
|
|
[EditorBrowsable(EditorBrowsableState.Never)]
|
|
private void ResetDescendingSortImageIndex()
|
|
{
|
|
_DescendingSortImageIndex = -1;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FilterImage
|
|
|
|
/// <summary>
|
|
/// Gets or sets the default
|
|
/// image to display in the column header.
|
|
/// </summary>
|
|
[DefaultValue(null), Category("Filtering")]
|
|
[Description("Indicates the default image to display in the column header.")]
|
|
public Image FilterImage
|
|
{
|
|
get { return (_FilterImage); }
|
|
|
|
set
|
|
{
|
|
if (_FilterImage != value)
|
|
{
|
|
_FilterImage = value;
|
|
|
|
NeedsMeasured = true;
|
|
|
|
OnPropertyChangedEx("FilterImage", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetFilterImage
|
|
|
|
internal Image GetFilterImage(GridColumn column)
|
|
{
|
|
bool inFilter;
|
|
StyleState state = GetFilterImageState(column, out inFilter);
|
|
|
|
return (GetFilterImage(column, state, inFilter));
|
|
}
|
|
|
|
internal Image GetFilterImage(
|
|
GridColumn column, StyleState state, bool inFilter)
|
|
{
|
|
if (_FilterImage != null)
|
|
return (_FilterImage);
|
|
|
|
if (_FilterImageIndex >= 0)
|
|
{
|
|
ImageList imageList = GridPanel.ImageList;
|
|
|
|
if (imageList != null && _FilterImageIndex < imageList.Images.Count)
|
|
return (imageList.Images[_FilterImageIndex]);
|
|
}
|
|
|
|
return (GetFilterImageEx(state, inFilter));
|
|
}
|
|
|
|
#region GetFilterImageEx
|
|
|
|
private Image GetFilterImageEx(StyleState state, bool inFilter)
|
|
{
|
|
int n = (int)state;
|
|
|
|
if (inFilter == true)
|
|
n += ImageCacheSize;
|
|
|
|
Image cacheImage = _FilterCacheImages[n];
|
|
|
|
if (cacheImage == null)
|
|
{
|
|
Image image = new Bitmap(Dpi.Width8, Dpi.Height8);
|
|
|
|
using (Graphics g = Graphics.FromImage(image))
|
|
{
|
|
g.SmoothingMode = SmoothingMode.AntiAlias;
|
|
|
|
using (GraphicsPath path = new GraphicsPath())
|
|
{
|
|
Point[] pts =
|
|
{
|
|
new Point(0, 0),
|
|
new Point(Dpi.Width7, 0),
|
|
new Point(Dpi.Width7, Dpi.Height1),
|
|
new Point(Dpi.Width4, Dpi.Height4),
|
|
new Point(Dpi.Width4, Dpi.Height7),
|
|
new Point(Dpi.Width3, Dpi.Height6),
|
|
new Point(Dpi.Width3, Dpi.Height4),
|
|
new Point(0, Dpi.Height1),
|
|
new Point(0, 0),
|
|
};
|
|
|
|
path.AddLines(pts);
|
|
|
|
Rectangle r = new Rectangle(Dpi.Width1, Dpi.Height1, Dpi.Width6, Dpi.Height3);
|
|
|
|
ColumnHeaderRowVisualStyle style = GetEffectiveRowHeaderStyleEx(state);
|
|
|
|
Color color = style.FilterBorderColor;
|
|
|
|
if (color.IsEmpty)
|
|
color = Color.DimGray;
|
|
|
|
if (inFilter == false)
|
|
style = GetEffectiveRowHeaderStyleEx(state & ~StyleState.MouseOver);
|
|
|
|
Background back = (style.FilterBackground != null && style.FilterBackground.IsEmpty == false)
|
|
? style.FilterBackground : new Background(Color.White);
|
|
|
|
using (Brush br = back.GetBrush(r))
|
|
g.FillPath(br, path);
|
|
|
|
using (Pen pen = new Pen(color))
|
|
g.DrawPath(pen, path);
|
|
}
|
|
}
|
|
|
|
_FilterCacheImages[n] = image;
|
|
|
|
cacheImage = image;
|
|
}
|
|
|
|
return (cacheImage);
|
|
}
|
|
|
|
#region GetFilterImageState
|
|
|
|
private StyleState GetFilterImageState(GridColumn column, out bool inFilter)
|
|
{
|
|
inFilter = false;
|
|
|
|
StyleState state = GetRowHeaderState();
|
|
|
|
state &= ~(StyleState.MouseOver | StyleState.Selected);
|
|
|
|
GridColumn hitColumn = _HitItem as GridColumn;
|
|
|
|
if (column == hitColumn)
|
|
{
|
|
state |= StyleState.MouseOver;
|
|
|
|
if (_HitArea == HeaderArea.InFilterMenu)
|
|
inFilter = true;
|
|
}
|
|
|
|
if (column != null && string.IsNullOrEmpty(column.FilterExpr) == false)
|
|
state |= StyleState.Selected;
|
|
|
|
return (state);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region FilterImageAlignment
|
|
|
|
/// <summary>
|
|
/// Gets or sets the alignment of the filter Image
|
|
/// </summary>
|
|
[DefaultValue(Alignment.NotSet), Category("Appearance")]
|
|
[Description("Indicates the alignment of the filter Image.")]
|
|
public Alignment FilterImageAlignment
|
|
{
|
|
get { return (_FilterImageAlignment); }
|
|
|
|
set
|
|
{
|
|
if (_FilterImageAlignment != value)
|
|
{
|
|
_FilterImageAlignment = value;
|
|
|
|
OnPropertyChangedEx("FilterImageAlignment", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FilterImageIndex
|
|
|
|
/// <summary>
|
|
/// Gets or sets the Filter image index
|
|
/// </summary>
|
|
[Browsable(true), DefaultValue(-1)]
|
|
[Category("Appearance"), Description("Indicates the Filter Row image index.")]
|
|
[Editor("DevComponents.SuperGrid.Design.ImageIndexEditor, DevComponents.SuperGrid.Design, Version=14.1.0.37, Culture=neutral, PublicKeyToken=26d81176cfa2b486", typeof(UITypeEditor))]
|
|
[TypeConverter(typeof(ImageIndexConverter))]
|
|
public int FilterImageIndex
|
|
{
|
|
get { return (_FilterImageIndex); }
|
|
|
|
set
|
|
{
|
|
if (_FilterImageIndex != value)
|
|
{
|
|
_FilterImageIndex = value;
|
|
|
|
OnPropertyChangedEx("FilterImageIndex", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
[Browsable(false)]
|
|
[EditorBrowsable(EditorBrowsableState.Never)]
|
|
private void ResetFilterImageIndex()
|
|
{
|
|
_FilterImageIndex = -1;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FilterImageVisibility
|
|
|
|
/// <summary>
|
|
/// Gets or sets the visibility of the header filter image
|
|
/// </summary>
|
|
[DefaultValue(ImageVisibility.Auto), Category("Filtering")]
|
|
[Description("Indicates the visibility of the header filter image.")]
|
|
public ImageVisibility FilterImageVisibility
|
|
{
|
|
get { return (_FilterImageVisibility); }
|
|
|
|
set
|
|
{
|
|
if (_FilterImageVisibility != value)
|
|
{
|
|
_FilterImageVisibility = value;
|
|
|
|
OnPropertyChangedEx("FilterImageVisibility", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GroupHeaders
|
|
|
|
/// <summary>
|
|
/// Gets a reference to the collection of grid columns
|
|
/// </summary>
|
|
[Category("Appearance")]
|
|
[Description("Indicates the collection of grid columns.")]
|
|
[DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
|
|
public ColumnGroupHeaderCollection GroupHeaders
|
|
{
|
|
get
|
|
{
|
|
if (_GroupHeaders == null)
|
|
{
|
|
_GroupHeaders = new ColumnGroupHeaderCollection();
|
|
|
|
_GroupHeaders.Parent = this;
|
|
|
|
_GroupHeaders.CollectionChanged += GroupHeadersCollectionChanged;
|
|
_GroupHeaders.PropertyChanged += GroupHeadersPropertyChanged;
|
|
_GroupHeaders.GroupHeaderMarkupLinkClick += GroupHeaderMarkupLinkClick;
|
|
}
|
|
|
|
return (_GroupHeaders);
|
|
}
|
|
}
|
|
|
|
#region GroupHeadersCollectionChanged
|
|
|
|
void GroupHeadersCollectionChanged(object sender, NotifyCollectionChangedEventArgs e)
|
|
{
|
|
NeedsMeasured = true;
|
|
SuperGrid.StyleUpdateCount++;
|
|
|
|
InvalidateLayout();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GroupHeadersPropertyChanged
|
|
|
|
void GroupHeadersPropertyChanged(object sender, PropertyChangedEventArgs e)
|
|
{
|
|
NeedsMeasured = true;
|
|
|
|
InvalidateStyle();
|
|
InvalidateLayout();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GroupHeadersMarkupLinkClick
|
|
|
|
void GroupHeaderMarkupLinkClick(object sender, GroupHeaderMarkupLinkClickEventArgs e)
|
|
{
|
|
SuperGrid.DoColumnGroupHeaderMarkupLinkClickEvent(
|
|
GridPanel, this, e.GroupHeader, e.HyperLink);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region MinRowHeight
|
|
|
|
///<summary>
|
|
/// Gets or sets the minimum height of the ColumnHeader row
|
|
///</summary>
|
|
[DefaultValue(0), Category("Style")]
|
|
[Description("Indicates the minimum height of the ColumnHeader row")]
|
|
public int MinRowHeight
|
|
{
|
|
get { return (_MinRowHeight); }
|
|
|
|
set
|
|
{
|
|
if (_MinRowHeight != value)
|
|
{
|
|
if (value < 0)
|
|
throw new Exception("MinRowHeight cannot be negative");
|
|
|
|
_MinRowHeight = value;
|
|
|
|
NeedsMeasured = true;
|
|
|
|
OnPropertyChangedEx("MinRowHeight", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RowHeaderText
|
|
|
|
///<summary>
|
|
/// Gets or sets the associated row header text (only
|
|
/// displayed if TopLeftHeaderSelectBehavior is set to NoSelection).
|
|
///</summary>
|
|
[DefaultValue(null), Category("Appearance")]
|
|
[Description("Indicates the associated row header text (only displayed if TopLeftHeaderSelectBehavior is set to NoSelection).")]
|
|
public string RowHeaderText
|
|
{
|
|
get { return (_RowHeaderText); }
|
|
|
|
set
|
|
{
|
|
if (_RowHeaderText != value)
|
|
{
|
|
_RowHeaderText = value;
|
|
|
|
NeedsMeasured = true;
|
|
|
|
OnPropertyChangedEx("RowHeaderText", VisualChangeType.Render);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RowHeight
|
|
|
|
///<summary>
|
|
/// Gets or sets the height of the ColumnHeader row
|
|
///</summary>
|
|
[DefaultValue(0), Category("Style")]
|
|
[Description("Indicates the height of the ColumnHeader row")]
|
|
public int RowHeight
|
|
{
|
|
get { return (_RowHeight); }
|
|
|
|
set
|
|
{
|
|
if (_RowHeight != value)
|
|
{
|
|
if (value < 0)
|
|
throw new Exception("RowHeight cannot be negative");
|
|
|
|
_RowHeight = value;
|
|
|
|
NeedsMeasured = true;
|
|
|
|
OnPropertyChangedEx("RowHeight", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ShowFilterToolTips
|
|
|
|
/// <summary>
|
|
/// Gets or sets whether tooltips are shown when over the filter image
|
|
/// </summary>
|
|
[DefaultValue(true), Category("Filtering")]
|
|
[Description("Indicates whether tooltips are shown when over the filter image.")]
|
|
public bool ShowFilterToolTips
|
|
{
|
|
get { return (_ShowFilterToolTips); }
|
|
|
|
set
|
|
{
|
|
if (value != _ShowFilterToolTips)
|
|
{
|
|
_ShowFilterToolTips = value;
|
|
|
|
OnPropertyChanged("ShowFilterToolTips");
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ShowHeaderImages
|
|
|
|
/// <summary>
|
|
/// Gets or sets whether Column Header images are displayed
|
|
/// </summary>
|
|
[DefaultValue(true), Category("Appearance")]
|
|
[Description("Indicates whether Column Header images are displayed.")]
|
|
public bool ShowHeaderImages
|
|
{
|
|
get { return (_ShowHeaderImages); }
|
|
|
|
set
|
|
{
|
|
if (_ShowHeaderImages != value)
|
|
{
|
|
_ShowHeaderImages = value;
|
|
|
|
NeedsMeasured = true;
|
|
|
|
OnPropertyChangedEx("ShowHeaderImages", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ShowGroupColumnHeaders
|
|
|
|
///<summary>
|
|
/// Gets or sets whether column headers are shown
|
|
/// by default when the columns are within a grouped header
|
|
///</summary>
|
|
[DefaultValue(true), Category("Appearance")]
|
|
[Description("Indicates whether column headers are shown by default when the columns are within a grouped header.")]
|
|
public bool ShowGroupColumnHeaders
|
|
{
|
|
get { return (_ShowGroupColumnHeaders); }
|
|
|
|
set
|
|
{
|
|
if (_ShowGroupColumnHeaders != value)
|
|
{
|
|
_ShowGroupColumnHeaders = value;
|
|
|
|
OnPropertyChangedEx("ShowGroupColumnHeaders", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ShowToolTips
|
|
|
|
/// <summary>
|
|
/// Gets or sets whether tooltips are shown for the column header
|
|
/// </summary>
|
|
[DefaultValue(true), Category("Filtering")]
|
|
[Description("Indicates whether tooltips are shown for the column header.")]
|
|
public bool ShowToolTips
|
|
{
|
|
get { return (_ShowToolTips); }
|
|
|
|
set
|
|
{
|
|
if (value != _ShowToolTips)
|
|
{
|
|
_ShowToolTips = value;
|
|
|
|
OnPropertyChanged("ShowToolTips");
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region SortImageAlignment
|
|
|
|
/// <summary>
|
|
/// Gets or sets the alignment of the Sort Images
|
|
/// </summary>
|
|
[DefaultValue(Alignment.NotSet), Category("Appearance")]
|
|
[Description("Indicates the alignment of the Sort Images.")]
|
|
public Alignment SortImageAlignment
|
|
{
|
|
get { return (_SortImageAlignment); }
|
|
|
|
set
|
|
{
|
|
if (_SortImageAlignment != value)
|
|
{
|
|
_SortImageAlignment = value;
|
|
|
|
OnPropertyChangedEx("SortImageAlignment", VisualChangeType.Layout);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region MeasureOverride
|
|
|
|
/// <summary>
|
|
/// Performs the layout of the item and sets
|
|
/// the Size property to size that item will take.
|
|
/// </summary>
|
|
/// <param name="layoutInfo">Layout information.</param>
|
|
/// <param name="stateInfo"></param>
|
|
/// <param name="constraintSize"></param>
|
|
protected override void MeasureOverride(
|
|
GridLayoutInfo layoutInfo, GridLayoutStateInfo stateInfo, Size constraintSize)
|
|
{
|
|
GridPanel panel = stateInfo.GridPanel;
|
|
|
|
ResetProcessStates(panel);
|
|
|
|
Size sizeNeeded = MeasureGroupHeaders(layoutInfo, constraintSize, panel);
|
|
MeasureColumnHeaders(layoutInfo, constraintSize, panel, ref sizeNeeded);
|
|
|
|
if (panel.ShowRowHeaders == true)
|
|
sizeNeeded.Width += panel.RowHeaderWidthEx;
|
|
|
|
Size = sizeNeeded;
|
|
}
|
|
|
|
#region MeasureGroupHeaders
|
|
|
|
private Size MeasureGroupHeaders(
|
|
GridLayoutInfo layoutInfo, Size constraintSize, GridPanel panel)
|
|
{
|
|
Size sizeNeeded = Size.Empty;
|
|
|
|
if (_GroupHeaders != null)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in _GroupHeaders)
|
|
{
|
|
if (cgh.Visible == true)
|
|
{
|
|
Size size = MeasureGroupHeader(layoutInfo, constraintSize, panel, cgh);
|
|
|
|
sizeNeeded.Width += size.Width;
|
|
sizeNeeded.Height = Math.Max(size.Height, sizeNeeded.Height);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (sizeNeeded);
|
|
}
|
|
|
|
#region MeasureGroupHeader
|
|
|
|
private Size MeasureGroupHeader(GridLayoutInfo layoutInfo,
|
|
Size constraintSize, GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
Size sizeNeeded = MeasureGroupHeaderColumn(layoutInfo, constraintSize, panel, cgh);
|
|
|
|
if (cgh.RowHeight > 0)
|
|
{
|
|
sizeNeeded.Height = Dpi.Height(cgh.RowHeight);
|
|
}
|
|
else
|
|
{
|
|
int mrh = Dpi.Height(cgh.MinRowHeight);
|
|
|
|
if (sizeNeeded.Height < mrh)
|
|
sizeNeeded.Height = mrh;
|
|
}
|
|
|
|
cgh.ContentSize = sizeNeeded;
|
|
|
|
if (cgh.GroupHeaders.Count > 0)
|
|
{
|
|
Size subSize = Size.Empty;
|
|
|
|
foreach (ColumnGroupHeader gh in cgh.GroupHeaders)
|
|
{
|
|
Size size = MeasureGroupHeader(layoutInfo, constraintSize, panel, gh);
|
|
|
|
subSize.Height = Math.Max(subSize.Height, size.Height);
|
|
subSize.Width += size.Width;
|
|
}
|
|
|
|
sizeNeeded.Height += subSize.Height;
|
|
sizeNeeded.Width = Math.Max(sizeNeeded.Width, subSize.Width);
|
|
}
|
|
else
|
|
{
|
|
Size baseSize = Size.Empty;
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
bool showColumnHeaders = GetShowRootColumnHeaders(cgh);
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint)i >= map.Length)
|
|
break;
|
|
|
|
int index = map[i];
|
|
|
|
GridColumn column = columns[index];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
if (showColumnHeaders == true)
|
|
{
|
|
Size size = MeasureHeader(layoutInfo, constraintSize, panel, column);
|
|
|
|
baseSize.Width += size.Width;
|
|
baseSize.Height = Math.Max(baseSize.Height, size.Height);
|
|
}
|
|
}
|
|
}
|
|
|
|
sizeNeeded.Height += baseSize.Height;
|
|
|
|
if (constraintSize.Width > 0)
|
|
sizeNeeded.Width = baseSize.Width;
|
|
else
|
|
sizeNeeded.Width = Math.Max(sizeNeeded.Width, baseSize.Width);
|
|
}
|
|
|
|
cgh.Size = sizeNeeded;
|
|
|
|
return (sizeNeeded);
|
|
}
|
|
|
|
#region MeasureGroupHeaderColumn
|
|
|
|
private Size MeasureGroupHeaderColumn(GridLayoutInfo layoutInfo,
|
|
Size constraintSize, GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
ColumnHeaderVisualStyle style = GetSizingStyle(panel, cgh);
|
|
|
|
Size sizeNeeded = MeasureGroupHeaderTextAndImage(layoutInfo, constraintSize, panel, cgh, style);
|
|
|
|
sizeNeeded.Width += Dpi.Width8;
|
|
sizeNeeded.Height += Dpi.Height4;
|
|
|
|
return (sizeNeeded);
|
|
}
|
|
|
|
#region MeasureGroupHeaderTextAndImage
|
|
|
|
private Size MeasureGroupHeaderTextAndImage(GridLayoutInfo layoutInfo, Size constraintSize,
|
|
GridPanel panel, ColumnGroupHeader cgh, ColumnHeaderVisualStyle style)
|
|
{
|
|
Size sizeNeeded = Size.Empty;
|
|
|
|
object figure = (_ShowHeaderImages == true) ? style.GetFigure(panel) : null;
|
|
Size figureSize = style.GetFigureSize(panel);
|
|
|
|
Alignment imageAlignment = style.ImageAlignment;
|
|
|
|
if (style.IsOverlayImage == true)
|
|
imageAlignment = Alignment.MiddleCenter;
|
|
|
|
Size borderSize = style.GetBorderSize(true);
|
|
|
|
int bwidth = (borderSize.Width * 2);
|
|
int bheight = (borderSize.Height * 2);
|
|
|
|
int width = constraintSize.Width > 0 ? GetDefaultGroupHeaderWidth(panel, cgh) : 0;
|
|
|
|
if (width > 0)
|
|
{
|
|
width -= bwidth;
|
|
|
|
switch (imageAlignment)
|
|
{
|
|
case Alignment.TopCenter:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.BottomCenter:
|
|
break;
|
|
|
|
default:
|
|
width -= figureSize.Width;
|
|
break;
|
|
}
|
|
}
|
|
|
|
Size contentSize =
|
|
MeasureGroupHeaderText(layoutInfo.Graphics, cgh, style, new Size(width, 0));
|
|
|
|
switch (imageAlignment)
|
|
{
|
|
case Alignment.MiddleCenter:
|
|
sizeNeeded.Height = Math.Max(figureSize.Height, contentSize.Height) + bheight;
|
|
sizeNeeded.Width = Math.Max(figureSize.Width, contentSize.Width) + bwidth;
|
|
break;
|
|
|
|
case Alignment.TopCenter:
|
|
case Alignment.BottomCenter:
|
|
sizeNeeded.Width = Math.Max(figureSize.Width, contentSize.Width) + bwidth;
|
|
sizeNeeded.Height = contentSize.Height + figureSize.Height + bheight;
|
|
break;
|
|
|
|
default:
|
|
sizeNeeded.Width = contentSize.Width + figureSize.Width + bwidth;
|
|
sizeNeeded.Height = Math.Max(figureSize.Height, contentSize.Height) + bheight;
|
|
break;
|
|
}
|
|
|
|
return (sizeNeeded);
|
|
}
|
|
|
|
#region GetDefaultGroupHeaderWidth
|
|
|
|
private int GetDefaultGroupHeaderWidth(
|
|
GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
int width = 0;
|
|
|
|
GridColumnCollection columns = panel.Columns;
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint)i >= map.Length)
|
|
break;
|
|
|
|
int index = map[i];
|
|
|
|
GridColumn column = columns[index];
|
|
|
|
if (column.Visible == true)
|
|
width += column.Size.Width;
|
|
}
|
|
|
|
return (width);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MeasureGroupHeaderText
|
|
|
|
private Size MeasureGroupHeaderText(Graphics g,
|
|
ColumnGroupHeader cgh, CellVisualStyle style, Size constraintSize)
|
|
{
|
|
Size size = Size.Empty;
|
|
|
|
string s = GetHeaderText(cgh);
|
|
|
|
if (string.IsNullOrEmpty(s) == false)
|
|
{
|
|
if (cgh.HeaderTextMarkup != null)
|
|
{
|
|
size = GetMarkupTextSize(g,
|
|
cgh.HeaderTextMarkup, style, constraintSize.Width);
|
|
|
|
cgh.HeaderTextSize = size;
|
|
}
|
|
else
|
|
{
|
|
eTextFormat tf = style.GetTextFormatFlags();
|
|
|
|
size = (constraintSize.IsEmpty == true)
|
|
? TextHelper.MeasureText(g, s, style.Font)
|
|
: TextHelper.MeasureText(g, s, style.Font, constraintSize, tf);
|
|
}
|
|
}
|
|
|
|
return (size);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region MeasureColumnHeaders
|
|
|
|
private void MeasureColumnHeaders(
|
|
GridLayoutInfo layoutInfo, Size constraintSize, GridPanel panel, ref Size sizeNeeded)
|
|
{
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
for (int i = 0; i < columns.Count; i++)
|
|
{
|
|
GridColumn column = columns[i];
|
|
|
|
if (column.Processed == false)
|
|
{
|
|
Size size = MeasureHeader(layoutInfo, constraintSize, panel, column);
|
|
|
|
sizeNeeded.Width += size.Width;
|
|
sizeNeeded.Height = Math.Max(size.Height, sizeNeeded.Height);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region MeasureHeader
|
|
|
|
internal Size MeasureHeader(GridLayoutInfo layoutInfo,
|
|
Size constraintSize, GridPanel panel, GridColumn column)
|
|
{
|
|
Size sizeNeeded = Size.Empty;
|
|
|
|
ColumnHeaderVisualStyle style = GetSizingStyle(panel, column);
|
|
|
|
MeasureTextAndImage(layoutInfo, constraintSize, panel, column, style, ref sizeNeeded);
|
|
MeasureSortAndFilter(panel, column, style, ref sizeNeeded);
|
|
|
|
sizeNeeded.Width += Dpi.Width8;
|
|
sizeNeeded.Height += Dpi.Height4;
|
|
|
|
if (Dpi.Height(_RowHeight) > 0)
|
|
sizeNeeded.Height = Dpi.Height(_RowHeight);
|
|
|
|
else if (sizeNeeded.Height < Dpi.Height(_MinRowHeight))
|
|
sizeNeeded.Height = Dpi.Height(_MinRowHeight);
|
|
|
|
column.HeaderSize = sizeNeeded;
|
|
|
|
column.Processed = true;
|
|
|
|
return (sizeNeeded);
|
|
}
|
|
|
|
#region MeasureTextAndImage
|
|
|
|
private void MeasureTextAndImage(GridLayoutInfo layoutInfo, Size constraintSize,
|
|
GridPanel panel, GridColumn column, ColumnHeaderVisualStyle style, ref Size sizeNeeded)
|
|
{
|
|
Size figureSize = (_ShowHeaderImages == true)
|
|
? style.GetFigureSize(panel) : Size.Empty;
|
|
|
|
Alignment imageAlignment = style.ImageAlignment;
|
|
|
|
if (style.IsOverlayImage == true)
|
|
imageAlignment = Alignment.MiddleCenter;
|
|
|
|
Size borderSize = style.GetBorderSize(true);
|
|
|
|
int bwidth = (borderSize.Width * 2);
|
|
int bheight = (borderSize.Height * 2);
|
|
|
|
int width = constraintSize.Width > 0 ? column.Size.Width : 0;
|
|
|
|
if (width > 0)
|
|
{
|
|
width -= bwidth;
|
|
|
|
switch (imageAlignment)
|
|
{
|
|
case Alignment.TopCenter:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.BottomCenter:
|
|
break;
|
|
|
|
default:
|
|
width -= figureSize.Width;
|
|
break;
|
|
}
|
|
}
|
|
|
|
Size contentSize =
|
|
MeasureHeaderText(layoutInfo.Graphics, column, style, new Size(width, 0));
|
|
|
|
if (width == 0)
|
|
column.HeaderTextSize = contentSize;
|
|
|
|
switch (imageAlignment)
|
|
{
|
|
case Alignment.MiddleCenter:
|
|
sizeNeeded.Height = Math.Max(figureSize.Height, contentSize.Height) + bheight;
|
|
sizeNeeded.Width = Math.Max(figureSize.Width, contentSize.Width) + bwidth;
|
|
break;
|
|
|
|
case Alignment.TopCenter:
|
|
case Alignment.BottomCenter:
|
|
sizeNeeded.Width = Math.Max(figureSize.Width, contentSize.Width) + bwidth;
|
|
sizeNeeded.Height = contentSize.Height + figureSize.Height + bheight;
|
|
break;
|
|
|
|
default:
|
|
sizeNeeded.Width = contentSize.Width + figureSize.Width + bwidth;
|
|
sizeNeeded.Height = Math.Max(figureSize.Height, contentSize.Height) + bheight;
|
|
break;
|
|
}
|
|
}
|
|
|
|
#region MeasureHeaderText
|
|
|
|
private Size MeasureHeaderText(Graphics g,
|
|
GridColumn column, CellVisualStyle style, Size constraintSize)
|
|
{
|
|
Size size = Size.Empty;
|
|
|
|
string s = column.GetHeaderText();
|
|
|
|
if (string.IsNullOrEmpty(s) == false)
|
|
{
|
|
if (column.HeaderTextMarkup != null)
|
|
{
|
|
size = GetMarkupTextSize(g,
|
|
column.HeaderTextMarkup, style, constraintSize.Width > 0 ? constraintSize.Width : 10000);
|
|
|
|
column.HeaderTextSize = size;
|
|
}
|
|
else
|
|
{
|
|
eTextFormat tf = style.GetTextFormatFlags();
|
|
|
|
size = (constraintSize.IsEmpty == true)
|
|
? TextHelper.MeasureText(g, s, style.Font)
|
|
: TextHelper.MeasureText(g, s, style.Font, constraintSize, tf);
|
|
}
|
|
}
|
|
|
|
return (size);
|
|
}
|
|
|
|
#region GetMarkupTextSize
|
|
|
|
private Size GetMarkupTextSize(Graphics g,
|
|
BodyElement textMarkup, CellVisualStyle style, int width)
|
|
{
|
|
MarkupDrawContext d =
|
|
new MarkupDrawContext(g, style.Font, style.TextColor, false);
|
|
|
|
textMarkup.InvalidateElementsSize();
|
|
textMarkup.Measure(new Size(width, 0), d);
|
|
|
|
return (textMarkup.Bounds.Size);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region MeasureSortAndFilter
|
|
|
|
private void MeasureSortAndFilter(GridPanel panel,
|
|
GridColumn column, ColumnHeaderVisualStyle style, ref Size sizeNeeded)
|
|
{
|
|
Alignment sortAlignment = (_SortImageAlignment == Alignment.NotSet)
|
|
? Alignment.TopCenter : _SortImageAlignment;
|
|
|
|
Alignment filterAlignment = (_FilterImageAlignment == Alignment.NotSet)
|
|
? Alignment.MiddleLeft : _FilterImageAlignment;
|
|
|
|
int imsHeight = 0;
|
|
|
|
if (panel.SortLevel != SortLevel.None)
|
|
{
|
|
imsHeight = GetPartSizeNeeded(
|
|
GetAscendingSortImage(column), style, sortAlignment, ref sizeNeeded);
|
|
}
|
|
|
|
int imfHeight = 0;
|
|
|
|
if (FilterCanBeVisible(panel) == true)
|
|
{
|
|
imfHeight = GetPartSizeNeeded(
|
|
GetFilterImage(column), style, filterAlignment, ref sizeNeeded);
|
|
}
|
|
|
|
if (imsHeight > 0 && imfHeight > 0)
|
|
{
|
|
if (VAlignment(sortAlignment) == VAlignment(filterAlignment))
|
|
{
|
|
int n = Math.Max(imsHeight, imfHeight);
|
|
|
|
sizeNeeded.Height += n;
|
|
|
|
if (VAlignment(style.Alignment) == 1)
|
|
sizeNeeded.Height += n;
|
|
}
|
|
else
|
|
sizeNeeded.Height += (imsHeight + imfHeight);
|
|
}
|
|
else
|
|
{
|
|
int n = imsHeight + imfHeight;
|
|
|
|
sizeNeeded.Height += n;
|
|
|
|
if (VAlignment(style.Alignment) == 1)
|
|
sizeNeeded.Height += n;
|
|
}
|
|
}
|
|
|
|
#region GetPartSizeNeeded
|
|
|
|
private int GetPartSizeNeeded(Image image,
|
|
ColumnHeaderVisualStyle style, Alignment alignment, ref Size sizeNeeded)
|
|
{
|
|
int height = 0;
|
|
|
|
if (image != null)
|
|
{
|
|
if (alignment != Alignment.TopCenter &&
|
|
alignment != Alignment.MiddleCenter &&
|
|
alignment != Alignment.BottomCenter)
|
|
{
|
|
sizeNeeded.Width += (image.Width + 4);
|
|
}
|
|
|
|
if (alignment == Alignment.MiddleLeft ||
|
|
alignment == Alignment.MiddleCenter ||
|
|
alignment == Alignment.MiddleRight ||
|
|
VAlignment(alignment) == VAlignment(style.Alignment))
|
|
{
|
|
sizeNeeded.Height = Math.Max(sizeNeeded.Height, image.Height);
|
|
}
|
|
else
|
|
{
|
|
height = (image.Height + 2);
|
|
}
|
|
}
|
|
|
|
return (height);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region FilterCanBeVisible
|
|
|
|
private bool FilterCanBeVisible(GridPanel panel)
|
|
{
|
|
if (panel.EnableFiltering == true && panel.EnableColumnFiltering == true)
|
|
{
|
|
if (FilterImageVisibility != ImageVisibility.Never)
|
|
return (true);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ArrangeOverride
|
|
|
|
/// <summary>
|
|
/// Performs the arrange pass layout of the item
|
|
/// when final position and size of the item has been set.
|
|
/// </summary>
|
|
/// <param name="layoutInfo">Layout information.</param>
|
|
/// <param name="stateInfo"></param>
|
|
/// <param name="layoutBounds">Layout bounds</param>
|
|
protected override void ArrangeOverride(GridLayoutInfo layoutInfo,
|
|
GridLayoutStateInfo stateInfo, Rectangle layoutBounds)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
ArrangeGroupHeader(panel, GroupHeaders, 0);
|
|
|
|
foreach (GridColumn col in panel.Columns)
|
|
{
|
|
if (col.Visible == true)
|
|
UpdateImageBounds(panel, col);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region ArrangeGroupHeader
|
|
|
|
private void ArrangeGroupHeader(
|
|
GridPanel panel, IEnumerable<ColumnGroupHeader> csc, int dy)
|
|
{
|
|
if (csc != null)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in csc)
|
|
{
|
|
if (cgh.Visible == true)
|
|
{
|
|
Size oldSize = cgh.BoundsRelative.Size;
|
|
|
|
cgh.BoundsRelative = GetGroupHeaderBounds(panel, cgh, dy);
|
|
cgh.Size = new Size(cgh.Size.Width, Bounds.Height - dy);
|
|
|
|
ArrangeGroupHeader(panel, cgh.GroupHeaders, dy + cgh.BoundsRelative.Height);
|
|
|
|
if (oldSize != cgh.BoundsRelative.Size)
|
|
SuperGrid.DoColumnGroupHeaderResizedEvent(panel, cgh, oldSize);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetGroupHeaderBounds
|
|
|
|
private Rectangle GetGroupHeaderBounds(
|
|
GridPanel panel, ColumnGroupHeader cgh, int dy)
|
|
{
|
|
GridColumnCollection columns = panel.Columns;
|
|
|
|
Rectangle r = Rectangle.Empty;
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
bool showColHeaders = GetShowRootColumnHeaders(cgh) && cgh.GroupHeaders.Count == 0;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint)i < columns.Count)
|
|
{
|
|
GridColumn column = columns[map[i]];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
Rectangle q = GetRelativeBounds(panel, column);
|
|
|
|
r = (r.IsEmpty == true) ? q : Rectangle.Union(r, q);
|
|
|
|
r.Height = (showColHeaders == true) ? column.HeaderSize.Height : 0;
|
|
}
|
|
}
|
|
}
|
|
|
|
r.Y += dy;
|
|
|
|
if (cgh.GroupHeaders.Count > 0)
|
|
{
|
|
r.Height = cgh.ContentSize.Height;
|
|
}
|
|
else
|
|
{
|
|
if (showColHeaders == true && cgh.RowHeight > 0)
|
|
r.Height = Dpi.Height(cgh.RowHeight);
|
|
else
|
|
r.Height = (Bounds.Bottom - r.Bottom);
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RenderOverride
|
|
|
|
/// <summary>
|
|
/// Performs drawing of the item and its children.
|
|
/// </summary>
|
|
/// <param name="renderInfo">Holds contextual rendering information.</param>
|
|
protected override void RenderOverride(GridRenderInfo renderInfo)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
ResetProcessStates(panel);
|
|
|
|
Graphics g = renderInfo.Graphics;
|
|
Rectangle bounds = Bounds;
|
|
|
|
ColumnHeaderRowVisualStyle style = GetEffectiveRowHeaderStyle();
|
|
GridPanelVisualStyle pstyle = panel.GetEffectiveStyle();
|
|
|
|
if (SuperGrid.DoPreRenderColumnHeaderEvent(g,
|
|
this, null, RenderParts.Background, bounds) == false)
|
|
{
|
|
RenderRowBackground(g, style, bounds);
|
|
|
|
SuperGrid.DoPostRenderColumnHeaderEvent(g,
|
|
this, null, RenderParts.Background, bounds);
|
|
}
|
|
|
|
RenderColumnBorder(g, panel, bounds);
|
|
|
|
if (HScrollOffset == 0 || panel.IsSubPanel || panel.FrozenColumnCount <= 0)
|
|
{
|
|
RenderHeaders(panel, renderInfo, false, false);
|
|
}
|
|
else
|
|
{
|
|
RenderHeaders(panel, renderInfo, true, false);
|
|
RenderHeaders(panel, renderInfo, true, true);
|
|
}
|
|
|
|
if (panel.FrozenColumnCount > 0)
|
|
RenderFrozenColumnMarker(g, panel, pstyle);
|
|
|
|
RenderRowHeader(g, panel, style, pstyle);
|
|
}
|
|
}
|
|
|
|
#region RenderRowBackground
|
|
|
|
private void RenderRowBackground(
|
|
Graphics g, ColumnHeaderRowVisualStyle style, Rectangle bounds)
|
|
{
|
|
using (Brush br = style.WhiteSpaceBackground.GetBrush(bounds))
|
|
g.FillRectangle(br, bounds);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderColumnBorder
|
|
|
|
private void RenderColumnBorder(
|
|
Graphics g, GridPanel panel, Rectangle bounds)
|
|
{
|
|
Rectangle r = bounds;
|
|
|
|
SmoothingMode sm = g.SmoothingMode;
|
|
g.SmoothingMode = SmoothingMode.None;
|
|
|
|
GridPanelVisualStyle pstyle = panel.GetEffectiveStyle();
|
|
|
|
if (pstyle.HeaderHLinePattern != LinePattern.None &&
|
|
pstyle.HeaderHLinePattern != LinePattern.NotSet)
|
|
{
|
|
using (Pen pen = new Pen(pstyle.HeaderLineColor, Dpi.Height1))
|
|
{
|
|
pen.DashStyle = (DashStyle)pstyle.HeaderHLinePattern;
|
|
|
|
g.DrawLine(pen, r.X, r.Bottom - 1, r.Right - 1, r.Bottom - 1);
|
|
g.DrawLine(pen, r.X, r.Top - 1, r.Right - 1, r.Top - 1);
|
|
}
|
|
}
|
|
|
|
if (pstyle.HeaderVLinePattern != LinePattern.None &&
|
|
pstyle.HeaderVLinePattern != LinePattern.NotSet)
|
|
{
|
|
using (Pen pen = new Pen(pstyle.HeaderLineColor, Dpi.Width1))
|
|
{
|
|
pen.DashStyle = (DashStyle)pstyle.HeaderVLinePattern;
|
|
|
|
g.DrawLine(pen, r.Right - 1, r.Top - 1, r.Right - 1, r.Bottom - 1);
|
|
}
|
|
}
|
|
|
|
g.SmoothingMode = sm;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderHeaders
|
|
|
|
private void RenderHeaders(GridPanel panel,
|
|
GridRenderInfo renderInfo, bool chkFrozen, bool frozen)
|
|
{
|
|
Graphics g = renderInfo.Graphics;
|
|
Rectangle clip = renderInfo.ClipRectangle;
|
|
|
|
RenderGroupHeaders(g, panel, clip, GroupHeaders, chkFrozen, frozen);
|
|
RenderColumnHeaders(g, panel, clip, chkFrozen, frozen);
|
|
}
|
|
|
|
#region RenderGroupHeaders
|
|
|
|
private void RenderGroupHeaders(Graphics g, GridPanel panel,
|
|
Rectangle clip, IEnumerable<ColumnGroupHeader> csc, bool chkFrozen, bool frozen)
|
|
{
|
|
if (csc != null)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in csc)
|
|
{
|
|
if (cgh.Visible == true)
|
|
{
|
|
if (chkFrozen == false || (IsGroupHeaderHFrozen(panel, cgh) == frozen))
|
|
{
|
|
Rectangle r = GetSubContScrollBounds(panel, cgh);
|
|
|
|
if (clip.IsEmpty == true || r.IntersectsWith(clip) == true)
|
|
{
|
|
Rectangle bounds = GetSubScrollBounds(panel, cgh);
|
|
|
|
RenderGroupHeader(g, panel, cgh, bounds);
|
|
|
|
if (cgh.GroupHeaders.Count > 0)
|
|
RenderGroupHeaders(g, panel, Rectangle.Empty, cgh.GroupHeaders, chkFrozen, frozen);
|
|
|
|
RenderBaseHeaders(g, panel, cgh);
|
|
}
|
|
else
|
|
{
|
|
if (cgh.GroupHeaders.Count > 0)
|
|
RenderGroupHeaders(g, panel, Rectangle.Empty, cgh.GroupHeaders, chkFrozen, frozen);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region RenderGroupHeader
|
|
|
|
private void RenderGroupHeader(
|
|
Graphics g, GridPanel panel, ColumnGroupHeader cgh, Rectangle bounds)
|
|
{
|
|
if (bounds.IsEmpty == false)
|
|
{
|
|
ColumnHeaderVisualStyle style = GetEffectiveStyle(cgh);
|
|
|
|
if (bounds.Width > 0 && bounds.Height > 0)
|
|
{
|
|
if (SuperGrid.DoPreRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Background, bounds) == false)
|
|
{
|
|
RenderBackground(g, style, bounds);
|
|
|
|
SuperGrid.DoPostRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Background, bounds);
|
|
}
|
|
|
|
RenderColumnBorder(g, panel, bounds);
|
|
|
|
Rectangle r = bounds;
|
|
Rectangle t = GetContentBounds(panel, style, r);
|
|
|
|
t = GetAdjustedBounds(style, t);
|
|
|
|
if (style.ImageOverlay == ImageOverlay.None ||
|
|
style.ImageOverlay == ImageOverlay.Bottom)
|
|
{
|
|
RenderHeaderImage(g, panel, style, bounds, t);
|
|
}
|
|
|
|
if (SuperGrid.DoPreRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Content, t) == false)
|
|
{
|
|
RenderGroupHeaderText(g, style, cgh, t);
|
|
|
|
SuperGrid.DoPostRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Content, t);
|
|
}
|
|
|
|
if (style.ImageOverlay == ImageOverlay.Top)
|
|
RenderHeaderImage(g, panel, style, bounds, t);
|
|
|
|
r = GetBorderRect(style, r);
|
|
|
|
if (SuperGrid.DoPreRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Border, r) == false)
|
|
{
|
|
if (r.Width > 0 && r.Height > 0)
|
|
style.RenderBorder(g, r);
|
|
|
|
SuperGrid.DoPostRenderColumnGroupHeaderEvent(g,
|
|
this, cgh, RenderParts.Border, r);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region RenderGroupHeaderText
|
|
|
|
private void RenderGroupHeaderText(Graphics g,
|
|
ColumnHeaderVisualStyle style, ColumnGroupHeader cgh, Rectangle r)
|
|
{
|
|
if (_MouseDownButtons == MouseButtons.Left)
|
|
r = AdjustTextHeaderBounds(cgh, r, GridPanel.ColumnGroupHeaderClickBehavior);
|
|
|
|
if (cgh.HeaderTextMarkup != null)
|
|
{
|
|
RenderTextMarkup(g, cgh.HeaderTextMarkup, style, r);
|
|
}
|
|
else
|
|
{
|
|
string s = GetHeaderText(cgh);
|
|
|
|
if (string.IsNullOrEmpty(s) == false)
|
|
{
|
|
TextDrawing.DrawString(g, s,
|
|
style.Font, style.TextColor, r, style.GetTextFormatFlags());
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetHeaderText
|
|
|
|
private string GetHeaderText(ColumnGroupHeader cgh)
|
|
{
|
|
return (cgh.HeaderText ?? cgh.Name);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RenderBaseHeaders
|
|
|
|
private void RenderBaseHeaders(Graphics g, GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
int[] map = panel.Columns.DisplayIndexMap;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint)i >= map.Length)
|
|
break;
|
|
|
|
RenderBaseHeader(g, panel, cgh, map[i]);
|
|
}
|
|
}
|
|
|
|
#region RenderBaseHeader
|
|
|
|
private void RenderBaseHeader(Graphics g,
|
|
GridPanel panel, ColumnGroupHeader cgh, int i)
|
|
{
|
|
GridColumn col = panel.Columns[i];
|
|
|
|
if (col.Visible == true && col.Processed == false)
|
|
{
|
|
Rectangle r = GetBounds(panel, col);
|
|
|
|
int n = cgh.Size.Height - cgh.BoundsRelative.Height;
|
|
|
|
r.Y = r.Bottom - n;
|
|
r.Height = n;
|
|
|
|
if (GetShowRootColumnHeaders(cgh) == true || cgh.GroupHeaders.Count > 0)
|
|
{
|
|
RenderColumnHeader(g, panel, col, r, true);
|
|
}
|
|
else
|
|
{
|
|
RenderColumnBorder(g, panel, r);
|
|
col.Processed = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RenderColumnHeaders
|
|
|
|
private void RenderColumnHeaders(Graphics g,
|
|
GridPanel panel, Rectangle clip, bool chkFrozen, bool frozen)
|
|
{
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
for (int i = 0; i < map.Length; i++)
|
|
{
|
|
int index = map[i];
|
|
|
|
GridColumn column = columns[index];
|
|
|
|
if (column.Visible == true && column.Processed == false)
|
|
{
|
|
if ((chkFrozen == false) || (frozen == column.IsHFrozen))
|
|
{
|
|
Rectangle r = GetBounds(panel, column);
|
|
|
|
if (r.IntersectsWith(clip) == true)
|
|
RenderColumnHeader(g, panel, column, r, true);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region RenderColumnHeader
|
|
|
|
private void RenderColumnHeader(Graphics g,
|
|
GridPanel panel, GridColumn column, Rectangle bounds, bool fullRender)
|
|
{
|
|
ColumnHeaderVisualStyle style = GetEffectiveStyle(column);
|
|
|
|
if (bounds.Width > 0 && bounds.Height > 0)
|
|
{
|
|
if (SuperGrid.DoPreRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Background, bounds) == false)
|
|
{
|
|
RenderBackground(g, style, bounds);
|
|
|
|
SuperGrid.DoPostRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Background, bounds);
|
|
}
|
|
|
|
RenderColumnBorder(g, panel, bounds);
|
|
|
|
Rectangle r = bounds;
|
|
Rectangle t = GetContentBounds(panel, style, r);
|
|
|
|
t = GetAdjustedBounds(style, t);
|
|
|
|
if (style.ImageOverlay == ImageOverlay.None ||
|
|
style.ImageOverlay == ImageOverlay.Bottom)
|
|
{
|
|
RenderHeaderImage(g, panel, style, bounds, t);
|
|
}
|
|
|
|
if (fullRender == true)
|
|
t = RenderSortAndFilterImage(g, column, style, t);
|
|
|
|
if (SuperGrid.DoPreRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Content, t) == false)
|
|
{
|
|
RenderText(g, panel, column, style, t);
|
|
|
|
SuperGrid.DoPostRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Content, t);
|
|
}
|
|
|
|
if (style.ImageOverlay == ImageOverlay.Top)
|
|
RenderHeaderImage(g, panel, style, bounds, t);
|
|
|
|
r = GetBorderRect(style, r);
|
|
|
|
if (SuperGrid.DoPreRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Border, r) == false)
|
|
{
|
|
if (r.Width > 0 && r.Height > 0)
|
|
style.RenderBorder(g, r);
|
|
|
|
SuperGrid.DoPostRenderColumnHeaderEvent(g,
|
|
this, column, RenderParts.Border, r);
|
|
}
|
|
|
|
column.Processed = true;
|
|
}
|
|
}
|
|
|
|
#region GetBorderRect
|
|
|
|
private Rectangle GetBorderRect(
|
|
ColumnHeaderVisualStyle style, Rectangle r)
|
|
{
|
|
r.X += style.Margin.Left;
|
|
r.Width -= style.Margin.Horizontal;
|
|
|
|
r.Y += style.Margin.Top;
|
|
r.Height -= style.Margin.Vertical;
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderBackground
|
|
|
|
private void RenderBackground(Graphics g,
|
|
VisualStyle style, Rectangle r)
|
|
{
|
|
using (Brush br = style.Background.GetBrush(r))
|
|
g.FillRectangle(br, r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderSortAndFilterImage
|
|
|
|
private Rectangle RenderSortAndFilterImage(
|
|
Graphics g, GridColumn column, ColumnHeaderVisualStyle style, Rectangle t)
|
|
{
|
|
GridPanel panel = column.Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
Alignment falign = (_FilterImageAlignment == Alignment.NotSet)
|
|
? Alignment.MiddleLeft : _FilterImageAlignment;
|
|
|
|
Alignment salign = (_SortImageAlignment == Alignment.NotSet)
|
|
? Alignment.TopCenter : _SortImageAlignment;
|
|
|
|
Rectangle rf = GetFilterImageBounds(panel, column);
|
|
|
|
if (rf.IsEmpty == false)
|
|
{
|
|
Image filterImage = GetColumnFilterImage(column);
|
|
|
|
if (filterImage != null)
|
|
g.DrawImageUnscaledAndClipped(filterImage, rf);
|
|
}
|
|
|
|
Rectangle rs = GetSortImageBounds(panel, column, salign, falign, rf);
|
|
|
|
if (rs.IsEmpty == false)
|
|
{
|
|
Image sortImage = GetColumnSortImage(panel, column);
|
|
|
|
if (sortImage != null)
|
|
g.DrawImageUnscaledAndClipped(sortImage, rs);
|
|
}
|
|
|
|
if (rf.IsEmpty == false)
|
|
t = UpdateContentRect(rf, t, falign, style, column);
|
|
|
|
if (rs.IsEmpty == false)
|
|
t = UpdateContentRect(rs, t, salign, style, column);
|
|
}
|
|
|
|
t.X += 2;
|
|
t.Width -= 4;
|
|
|
|
return (t);
|
|
}
|
|
|
|
#region GetFilterImageBounds
|
|
|
|
private Rectangle GetFilterImageBounds(GridPanel panel, GridColumn column)
|
|
{
|
|
if (column != null)
|
|
{
|
|
GridColumn hitColumn = _HitItem as GridColumn;
|
|
|
|
if (_FilterImageVisibility == ImageVisibility.Always ||
|
|
(column == hitColumn) || (string.IsNullOrEmpty(column.FilterExpr) == false))
|
|
{
|
|
return (GetScrollBounds(panel, column, column.FilterImageBounds));
|
|
}
|
|
}
|
|
|
|
return (Rectangle.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSortImageBounds
|
|
|
|
private Rectangle GetSortImageBounds(GridPanel panel,
|
|
GridColumn column, Alignment salign, Alignment falign, Rectangle rf)
|
|
{
|
|
Rectangle r = GetScrollBounds(panel, column, column.SortImageBounds);
|
|
|
|
if (r.IsEmpty == false)
|
|
{
|
|
if (falign == salign && r.IsEmpty == false)
|
|
{
|
|
if (salign == Alignment.TopCenter ||
|
|
salign == Alignment.MiddleCenter ||
|
|
salign == Alignment.BottomCenter)
|
|
{
|
|
r.X = rf.X - (r.Width + 1);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region UpdateContentRect
|
|
|
|
private Rectangle UpdateContentRect(Rectangle r,
|
|
Rectangle t, Alignment alignment, ColumnHeaderVisualStyle style, GridColumn column)
|
|
{
|
|
switch (GetStringAlignment(alignment))
|
|
{
|
|
case StringAlignment.Near:
|
|
int n1 = r.Right - t.Left;
|
|
|
|
switch (GetStringAlignment(style.Alignment))
|
|
{
|
|
case StringAlignment.Center:
|
|
if (n1 + 3 > (t.Width - column.HeaderTextSize.Width) / 2)
|
|
{
|
|
t.X = r.Right;
|
|
t.Width -= n1;
|
|
}
|
|
break;
|
|
|
|
default:
|
|
t.X = r.Right;
|
|
t.Width -= n1;
|
|
break;
|
|
}
|
|
break;
|
|
|
|
case StringAlignment.Far:
|
|
int n2 = t.Right - r.Left;
|
|
|
|
switch (GetStringAlignment(style.Alignment))
|
|
{
|
|
case StringAlignment.Center:
|
|
if (n2 + 3 > (t.Width - column.HeaderTextSize.Width) / 2)
|
|
t.Width -= n2;
|
|
break;
|
|
|
|
default:
|
|
t.Width -= n2;
|
|
break;
|
|
}
|
|
break;
|
|
}
|
|
|
|
return (t);
|
|
}
|
|
|
|
#region GetStringAlignment
|
|
|
|
private StringAlignment GetStringAlignment(Alignment alignment)
|
|
{
|
|
switch (alignment)
|
|
{
|
|
case Alignment.TopLeft:
|
|
case Alignment.MiddleLeft:
|
|
case Alignment.BottomLeft:
|
|
return (StringAlignment.Near);
|
|
|
|
case Alignment.TopCenter:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.BottomCenter:
|
|
return (StringAlignment.Center);
|
|
|
|
default:
|
|
return (StringAlignment.Far);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RenderText
|
|
|
|
private void RenderText(Graphics g, GridPanel panel,
|
|
GridColumn column, CellVisualStyle style, Rectangle r)
|
|
{
|
|
string s = column.GetHeaderText();
|
|
|
|
if (s != null)
|
|
{
|
|
if (_MouseDownButtons == MouseButtons.Left)
|
|
r = AdjustTextHeaderBounds(column, r, panel.ColumnHeaderClickBehavior);
|
|
|
|
if (column.HeaderTextMarkup != null)
|
|
{
|
|
RenderTextMarkup(g, column.HeaderTextMarkup, style, r);
|
|
}
|
|
else
|
|
{
|
|
TextDrawing.DrawString(g, s,
|
|
style.Font, style.TextColor, r, style.GetTextFormatFlags());
|
|
}
|
|
}
|
|
}
|
|
|
|
#region RenderTextMarkup
|
|
|
|
private void RenderTextMarkup(Graphics g,
|
|
BodyElement textMarkup, CellVisualStyle style, Rectangle r)
|
|
{
|
|
MarkupDrawContext d =
|
|
new MarkupDrawContext(g, style.Font, style.TextColor, false);
|
|
|
|
textMarkup.Arrange(new Rectangle(r.Location, r.Size), d);
|
|
|
|
Size size = textMarkup.Bounds.Size;
|
|
|
|
switch (style.Alignment)
|
|
{
|
|
case Alignment.MiddleLeft:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.MiddleRight:
|
|
if (r.Height > size.Height)
|
|
r.Y += (r.Height - size.Height) / 2;
|
|
break;
|
|
|
|
default:
|
|
if (r.Height > size.Height)
|
|
r.Y = r.Bottom - size.Height;
|
|
break;
|
|
}
|
|
|
|
textMarkup.Bounds = new Rectangle(r.Location, size);
|
|
|
|
Region oldClip = g.Clip;
|
|
|
|
try
|
|
{
|
|
g.SetClip(r, CombineMode.Intersect);
|
|
|
|
textMarkup.Render(d);
|
|
}
|
|
finally
|
|
{
|
|
g.Clip = oldClip;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region VAlignment
|
|
|
|
private int VAlignment(Alignment alignment)
|
|
{
|
|
switch (alignment)
|
|
{
|
|
case Alignment.TopLeft:
|
|
case Alignment.TopCenter:
|
|
case Alignment.TopRight:
|
|
return (0);
|
|
|
|
case Alignment.MiddleLeft:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.MiddleRight:
|
|
return (1);
|
|
|
|
default:
|
|
return (2);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetColumnSortImage
|
|
|
|
internal Image GetColumnSortImage(GridPanel panel, GridColumn column)
|
|
{
|
|
SortDirection sortDirection = SortDirection.None;
|
|
|
|
if (panel.GroupColumns != null &&
|
|
panel.GroupColumns.Contains(column) == true)
|
|
{
|
|
sortDirection = column.GroupDirection;
|
|
}
|
|
else if (panel.SortLevel != SortLevel.None)
|
|
{
|
|
sortDirection = column.SortDirection;
|
|
|
|
switch (column.SortIndicator)
|
|
{
|
|
case SortIndicator.None:
|
|
sortDirection = SortDirection.None;
|
|
break;
|
|
|
|
case SortIndicator.Ascending:
|
|
sortDirection = SortDirection.Ascending;
|
|
break;
|
|
|
|
case SortIndicator.Descending:
|
|
sortDirection = SortDirection.Descending;
|
|
break;
|
|
}
|
|
}
|
|
|
|
switch (sortDirection)
|
|
{
|
|
case SortDirection.Ascending:
|
|
return (GetAscendingSortImage(column));
|
|
|
|
case SortDirection.Descending:
|
|
return (GetDescendingSortImage(column));
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetFilterImage
|
|
|
|
internal Image GetColumnFilterImage(GridColumn column)
|
|
{
|
|
if (column.IsFilteringEnabled == true)
|
|
{
|
|
if (_FilterImageVisibility != ImageVisibility.Never)
|
|
return (GetFilterImage(column));
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetImageBounds
|
|
|
|
private Rectangle GetImageBounds(
|
|
Image image1, Alignment alignment, ref Rectangle r)
|
|
{
|
|
Rectangle u = r;
|
|
Rectangle t = r;
|
|
t.Size = image1.Size;
|
|
|
|
switch (alignment)
|
|
{
|
|
case Alignment.TopLeft:
|
|
r.X += t.Width + 2;
|
|
r.Width -= (t.Width + 2);
|
|
break;
|
|
|
|
case Alignment.NotSet:
|
|
case Alignment.TopCenter:
|
|
t.X += (r.Width - t.Width) / 2;
|
|
break;
|
|
|
|
case Alignment.TopRight:
|
|
t.X = r.Right - t.Width;
|
|
r.Width -= (t.Width + 2);
|
|
break;
|
|
|
|
case Alignment.MiddleLeft:
|
|
t.Y += (r.Height - t.Height) / 2;
|
|
|
|
r.X += t.Width + 2;
|
|
r.Width -= (t.Width + 2);
|
|
break;
|
|
|
|
case Alignment.MiddleCenter:
|
|
t.X += (r.Width - t.Width) / 2;
|
|
t.Y += (r.Height - t.Height) / 2;
|
|
break;
|
|
|
|
case Alignment.MiddleRight:
|
|
t.X = r.Right - t.Width;
|
|
t.Y += (r.Height - t.Height) / 2;
|
|
|
|
r.Width -= (t.Width + 2);
|
|
break;
|
|
|
|
case Alignment.BottomLeft:
|
|
r.X += t.Width + 2;
|
|
r.Width -= (t.Width + 2);
|
|
t.Y = r.Bottom - t.Height;
|
|
break;
|
|
|
|
case Alignment.BottomCenter:
|
|
t.X += (r.Width - t.Width) / 2;
|
|
t.Y = r.Bottom - t.Height;
|
|
break;
|
|
|
|
case Alignment.BottomRight:
|
|
t.X = r.Right - t.Width;
|
|
t.Y = r.Bottom - t.Height;
|
|
|
|
r.Width -= (t.Width + 2);
|
|
break;
|
|
}
|
|
|
|
t.Intersect(u);
|
|
|
|
return (t);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region AdjustTextHeaderBounds
|
|
|
|
private Rectangle AdjustTextHeaderBounds(
|
|
object item, Rectangle r, ColumnHeaderClickBehavior cmode)
|
|
{
|
|
if (_Reordering == false && item == _MouseDownHitItem)
|
|
{
|
|
if (_MouseDownHitArea == HeaderArea.InMarkup ||
|
|
(_MouseDownHitArea == HeaderArea.InContent && cmode == ColumnHeaderClickBehavior.SortAndReorder))
|
|
{
|
|
r.X++;
|
|
|
|
r.Y += 2;
|
|
r.Height -= 2;
|
|
}
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderHeaderImage
|
|
|
|
private void RenderHeaderImage(Graphics g, GridPanel panel,
|
|
ColumnHeaderVisualStyle style, Rectangle bounds, Rectangle r)
|
|
{
|
|
if (_ShowHeaderImages == true)
|
|
{
|
|
object figure = style.GetFigure(panel);
|
|
|
|
if (figure != null)
|
|
{
|
|
Rectangle t = style.GetFigureBounds(panel, r);
|
|
|
|
bounds.Inflate(-1, -1);
|
|
t.Intersect(bounds);
|
|
|
|
style.RenderFigure(g, panel, t);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RenderFrozenColumnMarker
|
|
|
|
private void RenderFrozenColumnMarker(
|
|
Graphics g, GridPanel panel, GridPanelVisualStyle pstyle)
|
|
{
|
|
GridColumn col = panel.Columns.GetLastVisibleFrozenColumn();
|
|
|
|
if (col != null)
|
|
{
|
|
Rectangle bounds = GetBounds(panel, col);
|
|
|
|
bounds.Y = Bounds.Y;
|
|
bounds.Height = Bounds.Height;
|
|
|
|
Rectangle r = col.BoundsRelative;
|
|
|
|
r.Y = bounds.Y + Dpi.Width3;
|
|
r.Height = bounds.Height - Dpi.Width5;
|
|
|
|
if (panel.IsSubPanel == true)
|
|
r.X -= HScrollOffset;
|
|
|
|
if (r.Height > 0 && r.Width > 0)
|
|
{
|
|
using (Pen pen = new Pen(pstyle.HeaderLineColor, Dpi.Width1))
|
|
{
|
|
g.DrawLine(pen, r.Right - Dpi.Width3,
|
|
r.Top - 1, r.Right - Dpi.Width3, r.Bottom - 1);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderRowHeader
|
|
|
|
private void RenderRowHeader(Graphics g,
|
|
GridPanel panel, ColumnHeaderRowVisualStyle style, GridPanelVisualStyle pstyle)
|
|
{
|
|
Rectangle r = GetRowHeaderBounds(panel);
|
|
|
|
if (r.Width > 0 && r.Height > 0)
|
|
{
|
|
if (SuperGrid.DoPreRenderColumnHeaderEvent(g,
|
|
this, null, RenderParts.RowHeader, r) == false)
|
|
{
|
|
SmoothingMode sm = g.SmoothingMode;
|
|
g.SmoothingMode = SmoothingMode.None;
|
|
|
|
using (Brush br = style.RowHeader.Background.GetBrush(r))
|
|
g.FillRectangle(br, r);
|
|
|
|
using (Pen pen = new Pen(style.RowHeader.BorderHighlightColor, Dpi.Height1))
|
|
g.DrawLine(pen, r.X, r.Top, r.Right - 1, r.Top);
|
|
|
|
using (Pen pen = new Pen(style.RowHeader.BorderHighlightColor, Dpi.Height1))
|
|
g.DrawLine(pen, r.X + 1, r.Top, r.X + 1, r.Bottom - 1);
|
|
|
|
using (Pen pen = new Pen(pstyle.HeaderLineColor, Dpi.Height1))
|
|
{
|
|
g.DrawLine(pen, r.X, r.Top - 1, r.Right - 1, r.Top - 1);
|
|
g.DrawLine(pen, r.X, r.Bottom - 1, r.Right - 1, r.Bottom - 1);
|
|
}
|
|
|
|
using (Pen pen = new Pen(pstyle.HeaderLineColor, Dpi.Width1))
|
|
g.DrawLine(pen, r.Right - 1, r.Top, r.Right - 1, r.Bottom - 1);
|
|
|
|
if (panel.TopLeftHeaderSelectBehavior != TopLeftHeaderSelectBehavior.NoSelection)
|
|
{
|
|
RenderRowHeaderIndicator(g, panel, style, r);
|
|
}
|
|
else
|
|
{
|
|
if (string.IsNullOrEmpty(_RowHeaderText) == false)
|
|
RenderRowHeaderText(g, _RowHeaderText, style, r);
|
|
}
|
|
|
|
SuperGrid.DoPostRenderColumnHeaderEvent(g,
|
|
this, null, RenderParts.RowHeader, r);
|
|
|
|
g.SmoothingMode = sm;
|
|
}
|
|
}
|
|
}
|
|
|
|
#region RenderRowHeaderIndicator
|
|
|
|
private void RenderRowHeaderIndicator(Graphics g,
|
|
GridPanel panel, ColumnHeaderRowVisualStyle style, Rectangle r)
|
|
{
|
|
r.Inflate(-Dpi.Width3, -Dpi.Height3);
|
|
|
|
if (r.Width > 0 && r.Height > 0)
|
|
{
|
|
using (GraphicsPath path = new GraphicsPath())
|
|
{
|
|
int n = Math.Min(r.Width, r.Height);
|
|
|
|
if (n > Dpi.Width10)
|
|
n = Dpi.Width10;
|
|
|
|
Point[] pts = new Point[3];
|
|
|
|
if (_SelectAllCount != panel.SelectionUpdateCount)
|
|
{
|
|
r.X--;
|
|
r.Y--;
|
|
|
|
pts[0] = new Point(r.Right, r.Bottom - n);
|
|
pts[1] = new Point(r.Right, r.Bottom);
|
|
pts[2] = new Point(r.Right - n, r.Bottom);
|
|
}
|
|
else
|
|
{
|
|
pts[0] = new Point(r.X, r.Y);
|
|
pts[1] = new Point(r.X + n, r.Y);
|
|
pts[2] = new Point(r.X, r.Y + n);
|
|
|
|
r.X++;
|
|
r.Y++;
|
|
}
|
|
|
|
path.AddPolygon(pts);
|
|
path.CloseFigure();
|
|
|
|
if (style.IndicatorBackground.GradientAngle % 45 == 0)
|
|
n /= 2;
|
|
|
|
r.Width = n - 1;
|
|
r.Height = n - 1;
|
|
|
|
if (n > 0)
|
|
{
|
|
g.SmoothingMode = SmoothingMode.AntiAlias;
|
|
|
|
using (Brush br = style.IndicatorBackground.GetBrush(r))
|
|
{
|
|
if (br is LinearGradientBrush)
|
|
((LinearGradientBrush)br).WrapMode = WrapMode.Tile;
|
|
|
|
g.FillPath(br, path);
|
|
}
|
|
|
|
using (Pen pen = new Pen(style.IndicatorBorderColor))
|
|
g.DrawPath(pen, path);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region RenderRowHeaderText
|
|
|
|
private void RenderRowHeaderText(Graphics g,
|
|
string text, ColumnHeaderRowVisualStyle style, Rectangle r)
|
|
{
|
|
Font font = style.RowHeader.Font ?? SystemFonts.DefaultFont;
|
|
|
|
Size tSize = TextHelper.MeasureText(g, text, font);
|
|
|
|
r.Inflate(-Dpi.Width2, -Dpi.Height2);
|
|
|
|
eTextFormat tf = ((r.Width <= tSize.Width)
|
|
? eTextFormat.Left
|
|
: eTextFormat.HorizontalCenter) | eTextFormat.NoPadding;
|
|
|
|
tf |= eTextFormat.WordBreak | eTextFormat.VerticalCenter;
|
|
|
|
TextDrawing.DrawString(g, text,
|
|
font, style.RowHeader.TextColor, r, tf);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ResetProcessStates
|
|
|
|
private void ResetProcessStates(GridPanel panel)
|
|
{
|
|
for (int i = 0; i < panel.Columns.Count; i++)
|
|
panel.Columns[i].Processed = false;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Mouse support
|
|
|
|
#region InternalMouseEnter
|
|
|
|
internal override void InternalMouseEnter(EventArgs e)
|
|
{
|
|
SuperGrid.ToolTipText = "";
|
|
|
|
SuperGrid.DoColumnHeaderMouseEnterEvent(this);
|
|
|
|
base.InternalMouseEnter(e);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InternalMouseLeave
|
|
|
|
internal override void InternalMouseLeave(EventArgs e)
|
|
{
|
|
if (_LockedColumn == false)
|
|
{
|
|
ResetColumnState();
|
|
|
|
_HitArea = HeaderArea.NoWhere;
|
|
_HitItem = null;
|
|
}
|
|
|
|
SuperGrid.ToolTipText = "";
|
|
|
|
SuperGrid.DoColumnHeaderMouseLeaveEvent(this);
|
|
|
|
base.InternalMouseLeave(e);
|
|
}
|
|
|
|
#region ResetColumnState
|
|
|
|
internal void ResetColumnState()
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (_MouseDownHitItem != null)
|
|
InvalidateItem(panel, _MouseDownHitItem);
|
|
|
|
if (_HitItem != null && (_MouseDownHitItem != _HitItem))
|
|
InvalidateItem(panel, _HitItem);
|
|
|
|
if (_HitArea == HeaderArea.InRowHeader)
|
|
InvalidateRowHeader();
|
|
|
|
if (_HitArea == HeaderArea.InWhitespace)
|
|
InvalidateWhitespace();
|
|
|
|
_MouseDownHitItem = null;
|
|
}
|
|
|
|
_LockedColumn = false;
|
|
}
|
|
|
|
internal void ResetColumnStateEx()
|
|
{
|
|
ResetColumnState();
|
|
|
|
_HitItem = null;
|
|
_HitArea = HeaderArea.NoWhere;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region InternalMouseMove
|
|
|
|
internal override void InternalMouseMove(MouseEventArgs e)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (AllowSelection == true)
|
|
{
|
|
if (_Resizing == false)
|
|
{
|
|
_LastHitArea = _HitArea;
|
|
_LastHitItem = _HitItem;
|
|
|
|
_HitArea = GetHitArea(e.Location, ref _HitItem, IsMouseDown);
|
|
|
|
if (_Reordering == false)
|
|
{
|
|
if (_HitItem is GridColumn)
|
|
ProcessColumnMouseMove(e, panel);
|
|
|
|
else if (_HitItem is ColumnGroupHeader)
|
|
ProcessGroupHeaderMouseMove(e, panel);
|
|
|
|
else
|
|
ProcessRowHeaderMouseMove(panel);
|
|
|
|
if (_HitArea != _LastHitArea || _LastHitItem != _HitItem)
|
|
{
|
|
if (_LastHitItem != null)
|
|
InvalidateItem(panel, _LastHitItem);
|
|
|
|
if (_HitItem != null)
|
|
InvalidateItem(panel, _HitItem);
|
|
|
|
if (_HitArea == HeaderArea.InRowHeader || _LastHitArea == HeaderArea.InRowHeader)
|
|
InvalidateRowHeader();
|
|
|
|
if (_HitArea == HeaderArea.InWhitespace || _LastHitArea == HeaderArea.InWhitespace)
|
|
InvalidateWhitespace();
|
|
|
|
}
|
|
}
|
|
}
|
|
|
|
if (IsMouseDown == true)
|
|
{
|
|
if (ProcessMouseDownMove(e) == false)
|
|
{
|
|
if (_MouseDownHitItem != null)
|
|
{
|
|
SuperGrid.EnableAutoScrolling(AutoScrollEnable.Horizontal, ViewRect);
|
|
|
|
StopResize();
|
|
StopReorder();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
SuperGrid.DoColumnHeaderMouseMoveEvent(this, e);
|
|
|
|
base.InternalMouseMove(e);
|
|
}
|
|
}
|
|
|
|
#region ProcessColumnMouseMove
|
|
|
|
private void ProcessColumnMouseMove(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = (GridColumn) _HitItem;
|
|
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
SuperGrid.GridCursor = Cursors.Default;
|
|
|
|
if (hitColumn.HeaderTextMarkup != null)
|
|
{
|
|
hitColumn.HeaderTextMarkup.MouseMove(SuperGrid, e);
|
|
|
|
if (hitColumn.HeaderTextMarkup.MouseOverElement != null)
|
|
_HitArea = HeaderArea.InMarkup;
|
|
}
|
|
|
|
if (_ShowToolTips == true)
|
|
UpdateToolTip(panel, hitColumn.ToolTip);
|
|
break;
|
|
|
|
case HeaderArea.InResize:
|
|
SuperGrid.GridCursor = Cursors.VSplit;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
|
|
case HeaderArea.InFilterMenu:
|
|
SuperGrid.GridCursor = Cursors.Hand;
|
|
|
|
if (_ShowFilterToolTips == true && hitColumn.IsFilteringEnabled == true)
|
|
UpdateToolTip(panel, hitColumn.FilterExpr);
|
|
break;
|
|
|
|
default:
|
|
SuperGrid.GridCursor = Cursors.Default;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessGroupHeaderMouseMove
|
|
|
|
private void ProcessGroupHeaderMouseMove(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
SuperGrid.GridCursor = Cursors.Default;
|
|
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_HitItem;
|
|
|
|
if (cgh.HeaderTextMarkup != null)
|
|
{
|
|
cgh.HeaderTextMarkup.MouseMove(SuperGrid, e);
|
|
|
|
if (cgh.HeaderTextMarkup.MouseOverElement != null)
|
|
_HitArea = HeaderArea.InMarkup;
|
|
}
|
|
|
|
if (_ShowToolTips == true)
|
|
UpdateToolTip(panel, cgh.ToolTip);
|
|
break;
|
|
|
|
case HeaderArea.InResize:
|
|
SuperGrid.GridCursor = Cursors.VSplit;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
|
|
default:
|
|
SuperGrid.GridCursor = Cursors.Default;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessRowHeaderMouseMove
|
|
|
|
private void ProcessRowHeaderMouseMove(GridPanel panel)
|
|
{
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InRowHeaderResize:
|
|
SuperGrid.GridCursor = Cursors.VSplit;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
|
|
case HeaderArea.InRowHeader:
|
|
SuperGrid.GridCursor =
|
|
(panel.TopLeftHeaderSelectBehavior != TopLeftHeaderSelectBehavior.NoSelection)
|
|
? Cursors.Hand
|
|
: Cursors.Default;
|
|
|
|
UpdateToolTip(panel, "");
|
|
break;
|
|
|
|
default:
|
|
SuperGrid.GridCursor = Cursors.Default;
|
|
SuperGrid.ToolTipText = "";
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region UpdateToolTip
|
|
|
|
private void UpdateToolTip(GridPanel panel, string toolTip)
|
|
{
|
|
if (_HitArea != _LastHitArea || _LastHitItem != _HitItem)
|
|
panel.SetHeaderTooltip(this, _HitItem, _HitArea, toolTip);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessMouseDownMove
|
|
|
|
private bool ProcessMouseDownMove(MouseEventArgs e)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (_MouseDownHitArea == HeaderArea.InRowHeaderResize)
|
|
return (InRowHeaderResize(e.Location, e));
|
|
|
|
if (_MouseDownHitItem is GridColumn)
|
|
return (ColumnMouseDownMove(e, panel));
|
|
|
|
if (_MouseDownHitItem is ColumnGroupHeader)
|
|
return (GroupHeaderMouseDownMove(e, panel));
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#region InRowHeaderResize
|
|
|
|
private bool InRowHeaderResize(Point pt, MouseEventArgs e)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (_Resizing == false)
|
|
{
|
|
_Resizing = true;
|
|
_ResizeWidth = panel.RowHeaderWidthEx;
|
|
|
|
if (panel.ImmediateResize == false)
|
|
{
|
|
_SeparatorFw = new FloatWindow();
|
|
_SeparatorFw.Opacity = .5;
|
|
_SeparatorFw.BackColor = Color.Black;
|
|
_SeparatorFw.Owner = SuperGrid.FindForm();
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (panel.ImmediateResize == false)
|
|
ContinueRowHeaderResize(panel, pt);
|
|
else
|
|
ResizeRowHeader(panel, pt.X - MouseDownPoint.X);
|
|
}
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ColumnMouseDownMove
|
|
|
|
private bool ColumnMouseDownMove(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = (GridColumn)_MouseDownHitItem;
|
|
Rectangle r = ViewRect;
|
|
|
|
if ((_MouseDownHitArea == HeaderArea.InResize) ||
|
|
(_MouseDownHitArea == HeaderArea.InRowHeaderResize) ||
|
|
(e.X >= r.X && e.X < r.Right) ||
|
|
(hitColumn.IsHFrozen == true && panel.IsSubPanel == false))
|
|
{
|
|
SuperGrid.DisableAutoScrolling();
|
|
|
|
switch (_MouseDownHitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
hitColumn = _MouseDownHitItem as GridColumn;
|
|
|
|
if (hitColumn != null)
|
|
{
|
|
if (_HitArea == HeaderArea.InGroupBox &&
|
|
hitColumn.GroupBoxEffectsEx != GroupBoxEffects.None)
|
|
{
|
|
if (ColumnInGroupBox(panel, e, hitColumn) == true)
|
|
return (true);
|
|
}
|
|
}
|
|
|
|
if (_HitItem == null)
|
|
return (false);
|
|
|
|
ColumnInContent(e);
|
|
break;
|
|
|
|
case HeaderArea.InResize:
|
|
ColumnInResize(e.Location, e);
|
|
break;
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#region ColumnInGroupBox
|
|
|
|
private bool ColumnInGroupBox(
|
|
GridPanel panel, MouseEventArgs e, GridColumn hitColumn)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
if (hitColumn != null)
|
|
{
|
|
if (panel.VisibleColumnCount > 1)
|
|
{
|
|
if (panel.GroupByRow.DragStart(hitColumn) == true)
|
|
{
|
|
ResetColumnState();
|
|
StopReorder();
|
|
|
|
_MouseDownHitItem = null;
|
|
_HitArea = HeaderArea.NoWhere;
|
|
_HitItem = null;
|
|
|
|
return (true);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ColumnInContent
|
|
|
|
private void ColumnInContent(MouseEventArgs e)
|
|
{
|
|
if (IsDesignerHosted == false)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (DragStarted(panel, e) == false)
|
|
{
|
|
if (panel.ColumnDragBehavior == ColumnDragBehavior.ExtendClickBehavior)
|
|
{
|
|
switch (panel.ColumnHeaderClickBehavior)
|
|
{
|
|
case ColumnHeaderClickBehavior.SortAndReorder:
|
|
ProcessMove(e.Location);
|
|
break;
|
|
|
|
case ColumnHeaderClickBehavior.Select:
|
|
if (_HitItem != _LastHitItem)
|
|
ProcessExtendSelection(panel, true);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region DragStarted
|
|
|
|
private bool DragStarted(GridPanel panel, MouseEventArgs e)
|
|
{
|
|
if (_HitItem is GridColumn)
|
|
{
|
|
if (_DragSelection == true)
|
|
{
|
|
if (_DragStarted == false)
|
|
{
|
|
if (DragDrop.DragStarted(_MouseDownPoint, e.Location) == true)
|
|
{
|
|
_DragStarted = true;
|
|
|
|
if (SuperGrid.DoItemDragEvent((GridColumn)_HitItem, e) == true)
|
|
{
|
|
_DragSelection = false;
|
|
|
|
ExtendSelection(panel, true);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessMove
|
|
|
|
private void ProcessMove(Point pt)
|
|
{
|
|
if (_Reordering == false)
|
|
StartReorder(pt);
|
|
else
|
|
ContinueReorder(pt);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessExtendSelection
|
|
|
|
private void ProcessExtendSelection(GridPanel panel, bool extend)
|
|
{
|
|
bool ckey = (panel.MultiSelect == true) ?
|
|
((Control.ModifierKeys & Keys.Control) == Keys.Control) : false;
|
|
|
|
if (ckey == true)
|
|
ProcessControlExtend(panel);
|
|
else
|
|
ProcessNonControlExtend(panel, extend);
|
|
|
|
_lastSelectedItem = _HitItem;
|
|
}
|
|
|
|
#region ProcessControlExtend
|
|
|
|
private void ProcessControlExtend(GridPanel panel)
|
|
{
|
|
int startIndex = 0;
|
|
int endIndex = 0;
|
|
|
|
if (GetSelectionIndicees(panel,
|
|
_lastSelectedItem, _HitItem, ref startIndex, ref endIndex, false) == true)
|
|
{
|
|
int mdStart = 0;
|
|
int mdEnd = 0;
|
|
|
|
GetSelectionIndicees(panel,
|
|
_MouseDownHitItem, _MouseDownHitItem, ref mdStart, ref mdEnd, true);
|
|
|
|
panel.NormalizeIndices(true, mdStart, ref startIndex, ref endIndex);
|
|
|
|
int[] map = panel.Columns.DisplayIndexMap;
|
|
|
|
for (int j = startIndex; j <= endIndex; j++)
|
|
{
|
|
GridColumn column = panel.Columns[map[j]];
|
|
|
|
if (j < mdStart || j > mdEnd)
|
|
column.IsSelected = !column.IsSelected;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ProcessNonControlExtend
|
|
|
|
private void ProcessNonControlExtend(GridPanel panel, bool extend)
|
|
{
|
|
int startIndex = 0;
|
|
int endIndex = 0;
|
|
|
|
if (GetSelectionIndicees(panel,
|
|
panel.SelectionColumnAnchor, _HitItem, ref startIndex, ref endIndex, true) == true)
|
|
{
|
|
int[] map = panel.Columns.DisplayIndexMap;
|
|
|
|
if (panel.OnlyColumnsSelected(startIndex, endIndex) == false)
|
|
{
|
|
if (extend == false)
|
|
panel.ClearAll();
|
|
|
|
for (int i = 0; i < map.Length; i++)
|
|
{
|
|
int index = map[i];
|
|
|
|
GridColumn column = panel.Columns[index];
|
|
|
|
if (column.Visible == true)
|
|
column.IsSelected = (i >= startIndex && i <= endIndex);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSelectionIndicees
|
|
|
|
private bool GetSelectionIndicees(GridPanel panel,
|
|
object start, object end, ref int startIndex, ref int endIndex, bool reorder)
|
|
{
|
|
if (GetSelectionStartIndex(panel, start, ref startIndex) == false)
|
|
return (false);
|
|
|
|
if (GetSelectionEndIndex(panel, end, ref endIndex) == false)
|
|
return (false);
|
|
|
|
if (startIndex > endIndex)
|
|
{
|
|
if (start is ColumnGroupHeader)
|
|
startIndex = ((ColumnGroupHeader)start).EndDisplayIndex;
|
|
|
|
if (end is ColumnGroupHeader)
|
|
endIndex = ((ColumnGroupHeader)end).StartDisplayIndex;
|
|
|
|
if (reorder == true)
|
|
{
|
|
int tempIndex = startIndex;
|
|
startIndex = endIndex;
|
|
endIndex = tempIndex;
|
|
}
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSelectionStartIndex
|
|
|
|
private bool GetSelectionStartIndex(GridPanel panel, object item, ref int startIndex)
|
|
{
|
|
startIndex = -1;
|
|
|
|
if (item is ColumnGroupHeader)
|
|
startIndex = ((ColumnGroupHeader) item).StartDisplayIndex;
|
|
|
|
else if (item is GridColumn)
|
|
startIndex = panel.Columns.GetDisplayIndex(((GridColumn) item).ColumnIndex);
|
|
|
|
return (startIndex >= 0);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSelectionEndIndex
|
|
|
|
private bool GetSelectionEndIndex(GridPanel panel, object item, ref int endIndex)
|
|
{
|
|
endIndex = -1;
|
|
|
|
if (item is ColumnGroupHeader)
|
|
endIndex = ((ColumnGroupHeader)item).EndDisplayIndex;
|
|
|
|
else if (item is GridColumn)
|
|
endIndex = panel.Columns.GetDisplayIndex(((GridColumn) item).ColumnIndex);
|
|
|
|
return (endIndex >= 0);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ColumnInResize
|
|
|
|
private void ColumnInResize(Point pt, MouseEventArgs e)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
if (_Resizing == false)
|
|
{
|
|
StartResize();
|
|
}
|
|
else
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (panel.ImmediateResize == false)
|
|
ContinueResize(panel, pt);
|
|
else
|
|
ResizeColumn(panel, pt.X - MouseDownPoint.X);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region GroupHeaderMouseDownMove
|
|
|
|
private bool GroupHeaderMouseDownMove(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_MouseDownHitItem;
|
|
|
|
Rectangle r = ViewRect;
|
|
|
|
if ((_MouseDownHitArea == HeaderArea.InResize) ||
|
|
(_MouseDownHitArea == HeaderArea.InRowHeaderResize) || (e.X >= r.X && e.X < r.Right) ||
|
|
(panel.IsSubPanel == false && IsGroupHeaderHFrozen(panel, cgh) == true))
|
|
{
|
|
SuperGrid.DisableAutoScrolling();
|
|
|
|
switch (_MouseDownHitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
GroupHeaderInContent(e);
|
|
break;
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#region GroupHeaderInContent
|
|
|
|
private void GroupHeaderInContent(MouseEventArgs e)
|
|
{
|
|
if (IsDesignerHosted == false)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (DragStarted(panel, e) == false)
|
|
{
|
|
if (panel.ColumnDragBehavior == ColumnDragBehavior.ExtendClickBehavior)
|
|
{
|
|
switch (panel.ColumnGroupHeaderClickBehavior)
|
|
{
|
|
case ColumnHeaderClickBehavior.SortAndReorder:
|
|
ProcessMove(e.Location);
|
|
break;
|
|
|
|
case ColumnHeaderClickBehavior.Select:
|
|
if (_HitItem != _LastHitItem)
|
|
ProcessExtendSelection(panel, true);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region InternalMouseDown
|
|
|
|
internal override void InternalMouseDown(MouseEventArgs e)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (EndCurrentOp() == true)
|
|
{
|
|
_MouseDownPoint = e.Location;
|
|
_MouseDownButtons = e.Button;
|
|
|
|
_MouseDownHitItem = _HitItem;
|
|
_MouseDownHitArea = _HitArea;
|
|
|
|
_DragSelection = false;
|
|
_DragStarted = false;
|
|
|
|
if (_HitItem is GridColumn)
|
|
ColumnMouseDown(e, panel);
|
|
|
|
else if (_HitItem is ColumnGroupHeader)
|
|
GroupHeaderMouseDown(e, panel);
|
|
|
|
else
|
|
RowHeaderMouseDown(e, panel);
|
|
|
|
_lastSelectedItem = _HitItem;
|
|
}
|
|
|
|
SuperGrid.DoColumnHeaderMouseDownEvent(this, e);
|
|
|
|
base.InternalMouseDown(e);
|
|
}
|
|
}
|
|
|
|
#region EndCurrentOp
|
|
|
|
private bool EndCurrentOp()
|
|
{
|
|
GridCell ecell = SuperGrid.EditorCell;
|
|
|
|
if (ecell != null)
|
|
{
|
|
if (ecell.EndEdit() == false)
|
|
{
|
|
_MouseDownHitArea = HeaderArea.NoWhere;
|
|
|
|
return (false);
|
|
}
|
|
}
|
|
|
|
if (_Reordering == true || _Resizing == true)
|
|
{
|
|
StopResize();
|
|
StopReorder();
|
|
|
|
InvalidateRender();
|
|
}
|
|
|
|
return (true);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ColumnMouseDown
|
|
|
|
private void ColumnMouseDown(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = (GridColumn)_HitItem;
|
|
|
|
if (_HitArea == HeaderArea.InContent)
|
|
{
|
|
Capture = true;
|
|
|
|
ColumnInContentMouseDown(e, panel, hitColumn);
|
|
}
|
|
else if (_HitArea == HeaderArea.InMarkup)
|
|
{
|
|
InvalidateHeader(panel, hitColumn);
|
|
}
|
|
else
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
Capture = true;
|
|
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InResize:
|
|
ColumnInResizeMouseDown(e, panel);
|
|
break;
|
|
|
|
case HeaderArea.InFilterMenu:
|
|
ColumnInFilterMouseDown(panel, hitColumn);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region ColumnInContentMouseDown
|
|
|
|
private void ColumnInContentMouseDown(
|
|
MouseEventArgs e, GridPanel panel, GridColumn hitColumn)
|
|
{
|
|
_MouseDownDelta = e.X - hitColumn.BoundsRelative.X;
|
|
|
|
if (panel.IsSubPanel == true || hitColumn.IsHFrozen == false)
|
|
_MouseDownDelta += HScrollOffset;
|
|
|
|
if (hitColumn.AllowSelection == true)
|
|
{
|
|
_LastHitItem = null;
|
|
_Reordering = false;
|
|
|
|
if (panel.ColumnHeaderClickBehavior == ColumnHeaderClickBehavior.Select)
|
|
{
|
|
if (hitColumn.IsSelected == false ||
|
|
((Control.ModifierKeys & (Keys.Control | Keys.Shift)) != Keys.None))
|
|
{
|
|
ExtendSelection(panel, true);
|
|
}
|
|
else
|
|
{
|
|
_DragSelection = true;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
InvalidateItem(panel, _MouseDownHitItem);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region ExtendSelection
|
|
|
|
private void ExtendSelection(GridPanel panel, bool capture)
|
|
{
|
|
if (capture == true)
|
|
Capture = true;
|
|
|
|
if (panel.SelectionColumnAnchor == null ||
|
|
(Control.ModifierKeys & Keys.Shift) != Keys.Shift)
|
|
{
|
|
panel.SelectionColumnAnchor = _MouseDownHitItem;
|
|
}
|
|
|
|
if ((Control.ModifierKeys & Keys.Control) == Keys.Control)
|
|
{
|
|
int startIndex = 0;
|
|
int endIndex = 0;
|
|
|
|
if (GetSelectionIndicees(panel, _MouseDownHitItem,
|
|
_MouseDownHitItem, ref startIndex, ref endIndex, true) == true)
|
|
{
|
|
int[] map = panel.Columns.DisplayIndexMap;
|
|
|
|
for (int i = startIndex; i <= endIndex; i++)
|
|
{
|
|
GridColumn column = panel.Columns[map[i]];
|
|
|
|
column.IsSelected = !column.IsSelected;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
ProcessNonControlExtend(panel, false);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ColumnInResizeMouseDown
|
|
|
|
private void ColumnInResizeMouseDown(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = _HitItem as GridColumn;
|
|
|
|
if (hitColumn != null)
|
|
{
|
|
Capture = true;
|
|
|
|
_MouseDownDelta = e.X - hitColumn.BoundsRelative.X;
|
|
|
|
if (panel.IsSubPanel == true || hitColumn.IsHFrozen == false)
|
|
_MouseDownDelta += HScrollOffset;
|
|
|
|
_Resizing = false;
|
|
_LastHitItem = null;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ColumnInFilterMouseDown
|
|
|
|
private void ColumnInFilterMouseDown(GridPanel panel, GridColumn column)
|
|
{
|
|
ActivateFilterPopup(panel, column);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region GroupHeaderMouseDown
|
|
|
|
private void GroupHeaderMouseDown(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_HitItem;
|
|
|
|
if (_HitArea == HeaderArea.InContent)
|
|
{
|
|
Capture = true;
|
|
|
|
GroupHeaderInContentMouseDown(e, panel, cgh);
|
|
}
|
|
else if (_HitArea == HeaderArea.InMarkup)
|
|
{
|
|
InvalidateHeader(panel, cgh);
|
|
}
|
|
else
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
Capture = true;
|
|
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InResize:
|
|
ColumnInResizeMouseDown(e, panel);
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GroupHeaderInContentMouseDown
|
|
|
|
private void GroupHeaderInContentMouseDown(
|
|
MouseEventArgs e, GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
_MouseDownDelta = e.X - cgh.BoundsRelative.X;
|
|
|
|
if (panel.IsSubPanel == true || IsGroupHeaderHFrozen(panel, cgh) == false)
|
|
_MouseDownDelta += HScrollOffset;
|
|
|
|
if (cgh.AllowSelection == true)
|
|
{
|
|
_LastHitItem = null;
|
|
_Reordering = false;
|
|
|
|
if (panel.ColumnGroupHeaderClickBehavior == ColumnHeaderClickBehavior.Select)
|
|
{
|
|
if (IsGroupHeaderSelected(cgh) == false ||
|
|
((Control.ModifierKeys & (Keys.Control | Keys.Shift)) != Keys.None))
|
|
{
|
|
ExtendSelection(panel, true);
|
|
}
|
|
else
|
|
{
|
|
_DragSelection = true;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
InvalidateItem(panel, _MouseDownHitItem);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RowHeaderMouseDown
|
|
|
|
private void RowHeaderMouseDown(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
Capture = true;
|
|
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InRowHeader:
|
|
InRowHeaderMouseDown(panel);
|
|
break;
|
|
|
|
case HeaderArea.InRowHeaderResize:
|
|
InRowHeaderResizeMouseDown();
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
#region InRowHeaderMouseDown
|
|
|
|
private void InRowHeaderMouseDown(GridPanel panel)
|
|
{
|
|
if (panel.TopLeftHeaderSelectBehavior != TopLeftHeaderSelectBehavior.NoSelection)
|
|
{
|
|
bool select = (_SelectAllCount != panel.SelectionUpdateCount);
|
|
|
|
if (select == true)
|
|
{
|
|
if (panel.MultiSelect == true)
|
|
{
|
|
panel.SelectAll();
|
|
}
|
|
else if (panel.ActiveRow != null)
|
|
{
|
|
panel.ClearAll();
|
|
panel.ActiveRow.IsSelected = true;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
panel.ClearAll();
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InRowHeaderResizeMouseDown
|
|
|
|
private void InRowHeaderResizeMouseDown()
|
|
{
|
|
Capture = true;
|
|
|
|
_Resizing = false;
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region InternalMouseUp
|
|
|
|
internal override void InternalMouseUp(MouseEventArgs e)
|
|
{
|
|
SuperGrid.DisableAutoScrolling();
|
|
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (_Reordering == true)
|
|
{
|
|
StopReorder();
|
|
|
|
if (_SeparatorColumn != null && _HitItem != _MouseDownHitItem)
|
|
ReorderItem(panel);
|
|
}
|
|
else if (_Resizing == true && _ResizeColumn != null)
|
|
{
|
|
StopResize();
|
|
|
|
if (panel.ImmediateResize == false)
|
|
ResizeColumn(panel, e.Location.X - MouseDownPoint.X);
|
|
}
|
|
else
|
|
{
|
|
if (_HitItem is GridColumn)
|
|
ColumnMouseUp(e, panel);
|
|
|
|
else if (_HitItem is ColumnGroupHeader)
|
|
GroupHeaderMouseUp(e, panel);
|
|
|
|
else
|
|
RowHeaderMouseUp(e, panel);
|
|
}
|
|
}
|
|
|
|
_MouseDownHitItem = null;
|
|
|
|
SuperGrid.DoColumnHeaderMouseUpEvent(this, e);
|
|
|
|
base.InternalMouseUp(e);
|
|
}
|
|
|
|
#region ColumnMouseUp
|
|
|
|
private void ColumnMouseUp(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = (GridColumn)_HitItem;
|
|
|
|
switch (_MouseDownHitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
case HeaderArea.InMarkup:
|
|
if (hitColumn != null && hitColumn == _MouseDownHitItem)
|
|
{
|
|
if (SuperGrid.DoColumnHeaderClickEvent(panel, hitColumn, e) == false)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
DoHeaderMouseUp(panel, panel.ColumnHeaderClickBehavior,
|
|
hitColumn.HeaderTextMarkup, hitColumn);
|
|
|
|
InvalidateHeader(panel, hitColumn);
|
|
}
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GroupHeaderMouseUp
|
|
|
|
private void GroupHeaderMouseUp(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_HitItem;
|
|
|
|
switch (_MouseDownHitArea)
|
|
{
|
|
case HeaderArea.InContent:
|
|
case HeaderArea.InMarkup:
|
|
if (_HitItem == _MouseDownHitItem)
|
|
{
|
|
if (SuperGrid.DoColumnGroupHeaderClickEvent(panel, this, cgh, e) == false)
|
|
{
|
|
if (e.Button == MouseButtons.Left)
|
|
{
|
|
DoHeaderMouseUp(panel, panel.ColumnGroupHeaderClickBehavior,
|
|
cgh.HeaderTextMarkup,
|
|
panel.Columns.ColumnAtDisplayIndex(cgh.StartDisplayIndex));
|
|
|
|
InvalidateHeader(panel, cgh);
|
|
}
|
|
}
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region DoHeaderMouseUp
|
|
|
|
private void DoHeaderMouseUp(GridPanel panel,
|
|
ColumnHeaderClickBehavior cmode, BodyElement bodyElement, GridColumn hitColumn)
|
|
{
|
|
if (panel.FlushActiveRow() == true)
|
|
{
|
|
if (DoMarkupClick(bodyElement) == false)
|
|
{
|
|
if (_DragSelection == true)
|
|
ExtendSelection(panel, false);
|
|
|
|
if (cmode == ColumnHeaderClickBehavior.SortAndReorder && panel.IsSortable == true)
|
|
SortColumn(panel, hitColumn);
|
|
}
|
|
}
|
|
}
|
|
|
|
#region DoMarkupClick
|
|
|
|
private bool DoMarkupClick(BodyElement bodyElement)
|
|
{
|
|
if (bodyElement != null)
|
|
{
|
|
if (bodyElement.MouseOverElement != null)
|
|
{
|
|
bodyElement.Click(SuperGrid);
|
|
|
|
SuperGrid.Cursor = Cursors.Default;
|
|
|
|
return (true);
|
|
}
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RowHeaderMouseUp
|
|
|
|
private void RowHeaderMouseUp(MouseEventArgs e, GridPanel panel)
|
|
{
|
|
switch (_MouseDownHitArea)
|
|
{
|
|
case HeaderArea.InRowHeader:
|
|
SuperGrid.DoColumnRowHeaderClickEvent(panel);
|
|
break;
|
|
|
|
case HeaderArea.InRowHeaderResize:
|
|
if (_Resizing == true)
|
|
{
|
|
StopResize();
|
|
|
|
if (panel.ImmediateResize == false)
|
|
ResizeRowHeader(panel, e.Location.X - MouseDownPoint.X);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region InternalMouseDoubleClick
|
|
|
|
internal override void InternalMouseDoubleClick(MouseEventArgs e)
|
|
{
|
|
GridColumn hitColumn = _HitItem as GridColumn;
|
|
|
|
if (hitColumn != null)
|
|
{
|
|
if (SuperGrid.DoColumnHeaderDoubleClickEvent(hitColumn, e) == false)
|
|
{
|
|
switch (_HitArea)
|
|
{
|
|
case HeaderArea.InResize:
|
|
if (hitColumn.GetAutoSizeMode() == ColumnAutoSizeMode.None)
|
|
{
|
|
RowScope scope = (GridPanel.VirtualMode == true || hitColumn.GridPanel.Rows.Count > 1000)
|
|
? RowScope.OnScreenRows
|
|
: RowScope.AllRows;
|
|
|
|
hitColumn.Width = Dpi.DescaleWidth(hitColumn.GetMaximumCellSize(scope, true).Width);
|
|
}
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (_HitArea == HeaderArea.InRowHeader)
|
|
SuperGrid.DoColumnRowHeaderDoubleClickEvent(GridPanel);
|
|
}
|
|
|
|
base.InternalMouseDoubleClick(e);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region Column Reorder
|
|
|
|
#region StartReorder
|
|
|
|
private void StartReorder(Point pt)
|
|
{
|
|
if (_MouseDownHitItem != null && Math.Abs(MouseDownPoint.X - pt.X) > 5)
|
|
{
|
|
Capture = true;
|
|
|
|
_Reordering = true;
|
|
_SeparatorColumn = null;
|
|
|
|
_HeaderFw = new FloatWindow();
|
|
_HeaderFw.Opacity = .3;
|
|
_HeaderFw.Owner = SuperGrid.FindForm();
|
|
_HeaderFw.Paint += ColumnHeaderFwPaint;
|
|
|
|
_SeparatorFw = new FloatWindow();
|
|
_SeparatorFw.Opacity = .5;
|
|
_SeparatorFw.BackColor = Color.Black;
|
|
_SeparatorFw.Owner = SuperGrid.FindForm();
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region StopReorder
|
|
|
|
private void StopReorder()
|
|
{
|
|
_Reordering = false;
|
|
|
|
if (_HeaderFw != null)
|
|
{
|
|
_HeaderFw.Close();
|
|
_HeaderFw.Paint -= ColumnHeaderFwPaint;
|
|
_HeaderFw.Dispose();
|
|
|
|
_HeaderFw = null;
|
|
}
|
|
|
|
if (_SeparatorFw != null)
|
|
{
|
|
HideSeparator();
|
|
|
|
_SeparatorFw.Close();
|
|
_SeparatorFw.Dispose();
|
|
|
|
_SeparatorFw = null;
|
|
}
|
|
|
|
if (_MouseDownHitItem != null)
|
|
InvalidateItem(GridPanel, _MouseDownHitItem);
|
|
|
|
if (_HitItem != null)
|
|
InvalidateItem(GridPanel, _HitItem);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ContinueReorder
|
|
|
|
private void ContinueReorder(Point pt)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (_HitItem != null && _MouseDownHitItem != null)
|
|
{
|
|
ReorderHeader(pt);
|
|
|
|
if (ValidReorder() == true)
|
|
{
|
|
ReorderSeparator(pt);
|
|
}
|
|
else if (_SeparatorFw != null)
|
|
{
|
|
HideSeparator();
|
|
|
|
_SeparatorColumn = null;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#region ValidReorder
|
|
|
|
private bool ValidReorder()
|
|
{
|
|
if (IsItemHFrozen(_HitItem) == IsItemHFrozen(_MouseDownHitItem))
|
|
{
|
|
object o1 = GetParent(_HitItem);
|
|
object o2 = GetParent(_MouseDownHitItem);
|
|
|
|
if (o1 is GridColumnHeader)
|
|
o1 = null;
|
|
|
|
if (o2 is GridColumnHeader)
|
|
o2 = null;
|
|
|
|
return (o1 == o2);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ReorderHeader
|
|
|
|
private void ReorderHeader(Point pt)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
Rectangle r = GetReorderWindowBounds(panel, pt);
|
|
|
|
if (r.Width <= 0 || r.Height <= 0)
|
|
{
|
|
_HeaderFw.Hide();
|
|
}
|
|
else
|
|
{
|
|
r.Location = SuperGrid.PointToScreen(r.Location);
|
|
|
|
Size size = _HeaderFw.Size;
|
|
|
|
_HeaderFw.Bounds = r;
|
|
|
|
if (_HeaderFw.Visible == false)
|
|
_HeaderFw.Show();
|
|
|
|
else if (r.Size.Equals(size) == false)
|
|
_HeaderFw.Refresh();
|
|
}
|
|
}
|
|
}
|
|
|
|
#region GetReorderWindowBounds
|
|
|
|
private Rectangle GetReorderWindowBounds(GridPanel panel, Point pt)
|
|
{
|
|
Rectangle r = GetReorderBounds(panel, _MouseDownHitItem);
|
|
Rectangle t = SViewRect;
|
|
|
|
r.X = (pt.X - _MouseDownDelta);
|
|
|
|
int x = Math.Max(r.X, t.X);
|
|
|
|
if (r.X < x)
|
|
{
|
|
_OrderTextOffset = r.X - x;
|
|
|
|
r.X = x;
|
|
r.Width += _OrderTextOffset;
|
|
}
|
|
else
|
|
{
|
|
_OrderTextOffset = 0;
|
|
}
|
|
|
|
int n = r.Right;
|
|
|
|
x = Math.Min(n, t.Right);
|
|
|
|
if (r.Right > x)
|
|
r.Width -= (r.Right - x);
|
|
|
|
if (r.Bottom > t.Bottom)
|
|
r.Height -= (r.Bottom - t.Bottom);
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ReorderSeparator
|
|
|
|
private void ReorderSeparator(Point pt)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
Rectangle r = GetReorderBounds(panel, _HitItem);
|
|
|
|
Rectangle t = SViewRect;
|
|
|
|
if (r.Right > t.Right)
|
|
r.Width = t.Right - r.X;
|
|
|
|
bool isRight = (pt.X > r.X + r.Width / 2);
|
|
GridColumn column = GetSeparatorColumn(panel, isRight);
|
|
|
|
if (_SeparatorColumn != column || _SeparatorIsRight != isRight)
|
|
{
|
|
_SeparatorColumn = column;
|
|
_SeparatorIsRight = isRight;
|
|
|
|
if (column != null)
|
|
{
|
|
r = GetReorderSeparatorBounds(panel, r, isRight);
|
|
r.Location = SuperGrid.PointToScreen(r.Location);
|
|
|
|
_SeparatorFw.Show();
|
|
|
|
_SeparatorFw.Bounds = r;
|
|
_SeparatorFw.Size = r.Size;
|
|
}
|
|
else
|
|
{
|
|
HideSeparator();
|
|
}
|
|
}
|
|
else
|
|
{
|
|
if (_SeparatorColumn!= null)
|
|
_SeparatorFw.Show();
|
|
}
|
|
}
|
|
|
|
#region HideSeparator
|
|
|
|
private void HideSeparator()
|
|
{
|
|
if (_SeparatorFw != null)
|
|
_SeparatorFw.Hide();
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSeparatorColumn
|
|
|
|
private GridColumn GetSeparatorColumn(GridPanel panel, bool isRight)
|
|
{
|
|
if (_HitItem is GridColumn)
|
|
return ((GridColumn) _HitItem);
|
|
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_HitItem;
|
|
|
|
if (cgh != null)
|
|
{
|
|
GridColumnCollection columns = panel.Columns;
|
|
|
|
int index = (isRight == true)
|
|
? cgh.EndDisplayIndex : cgh.StartDisplayIndex;
|
|
|
|
return (columns[columns.DisplayIndexMap[index]]);
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetReorderSeparatorBounds
|
|
|
|
private Rectangle GetReorderSeparatorBounds(
|
|
GridPanel panel, Rectangle r, bool isRight)
|
|
{
|
|
if (isRight == true)
|
|
r.X = r.Right - (SeparatorWidth >> 1);
|
|
else
|
|
r.X -= (SeparatorWidth >> 1);
|
|
|
|
r.Width = SeparatorWidth;
|
|
|
|
if (r.X >= panel.BoundsRelative.Right - 2)
|
|
r.X = panel.BoundsRelative.Right - 3;
|
|
|
|
Rectangle t = SViewRect;
|
|
|
|
if (r.Bottom > t.Bottom)
|
|
r.Height -= (r.Bottom - t.Bottom);
|
|
|
|
if (r.X < t.X)
|
|
r.X = t.X;
|
|
|
|
else if (r.Right > t.Right)
|
|
r.X = t.Right - SeparatorWidth;
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region GetReorderBounds
|
|
|
|
private Rectangle GetReorderBounds(GridPanel panel, object item)
|
|
{
|
|
Rectangle r = BoundsRelative;
|
|
|
|
if (item is GridColumn)
|
|
{
|
|
GridColumn column = (GridColumn)item;
|
|
int index = panel.Columns.GetDisplayIndex(column);
|
|
|
|
ColumnGroupHeader cgh = GetParentHeader(index);
|
|
|
|
if (cgh != null)
|
|
r.Y = r.Bottom - (cgh.Size.Height - cgh.BoundsRelative.Height);
|
|
|
|
r.Height = (panel.BoundsRelative.Height - (r.Y - panel.BoundsRelative.Y));
|
|
|
|
r.X = column.BoundsRelative.X;
|
|
r.Width = column.BoundsRelative.Width;
|
|
|
|
if (panel.IsSubPanel == true || column.IsHFrozen == false)
|
|
r.X -= HScrollOffset;
|
|
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
|
|
return (r);
|
|
}
|
|
|
|
if (item is ColumnGroupHeader)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)item;
|
|
|
|
r.Y = r.Bottom - cgh.Size.Height;
|
|
r.Height = (panel.BoundsRelative.Height - (r.Y - panel.BoundsRelative.Y));
|
|
|
|
r.X = cgh.BoundsRelative.X;
|
|
r.Width = cgh.BoundsRelative.Width;
|
|
|
|
if (panel.IsSubPanel == true || IsGroupHeaderHFrozen(panel, cgh) == false)
|
|
r.X -= HScrollOffset;
|
|
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ReorderItem
|
|
|
|
private void ReorderItem(GridPanel panel)
|
|
{
|
|
if (_MouseDownHitItem is GridColumn)
|
|
ReorderColumn(panel);
|
|
|
|
if (_MouseDownHitItem is ColumnGroupHeader)
|
|
ReorderGroupHeader(panel);
|
|
}
|
|
|
|
#region ReorderColumn
|
|
|
|
private void ReorderColumn(GridPanel panel)
|
|
{
|
|
GridColumn hitColumn = (GridColumn)_MouseDownHitItem;
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
int curIndex = columns.GetDisplayIndex(hitColumn);
|
|
int sepIndex = columns.GetDisplayIndex(_SeparatorColumn);
|
|
|
|
if (curIndex > sepIndex && _SeparatorIsRight == true && sepIndex < map.Length - 1)
|
|
sepIndex++;
|
|
|
|
else if (curIndex < sepIndex && _SeparatorIsRight == false && sepIndex > 0)
|
|
sepIndex--;
|
|
|
|
if (sepIndex != curIndex)
|
|
{
|
|
ColumnGroupHeader parent = GetParent(hitColumn) as ColumnGroupHeader;
|
|
|
|
int[] dmap = new int[map.Length];
|
|
|
|
if (sepIndex < curIndex)
|
|
{
|
|
for (int i = curIndex; i > sepIndex; i--)
|
|
{
|
|
map[i] = map[i - 1];
|
|
dmap[i - 1] = 1;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
for (int i = curIndex; i < sepIndex; i++)
|
|
{
|
|
map[i] = map[i + 1];
|
|
dmap[i + 1] = -1;
|
|
}
|
|
}
|
|
|
|
map[sepIndex] = hitColumn.ColumnIndex;
|
|
dmap[curIndex] = sepIndex - curIndex;
|
|
|
|
for (int i = 0; i < map.Length; i++)
|
|
columns[map[i]].DisplayIndex = i;
|
|
|
|
UpdateGroupHeaderRanges(parent != null ? parent.GroupHeaders : GroupHeaders, dmap);
|
|
|
|
SuperGrid.UpdateStyleCount();
|
|
SuperGrid.PrimaryGrid.InvalidateRender();
|
|
|
|
SuperGrid.DoColumnMovedEvent(panel, hitColumn);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ReorderGroupHeader
|
|
|
|
private void ReorderGroupHeader(GridPanel panel)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_MouseDownHitItem;
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
int curStartIndex = cgh.StartDisplayIndex;
|
|
int curEndIndex = cgh.EndDisplayIndex;
|
|
|
|
int sepIndex = columns.GetDisplayIndex(_SeparatorColumn);
|
|
|
|
if (curStartIndex > sepIndex && _SeparatorIsRight == true && sepIndex < map.Length - 1)
|
|
sepIndex++;
|
|
|
|
else if (curEndIndex < sepIndex && _SeparatorIsRight == false && sepIndex > 0)
|
|
sepIndex--;
|
|
|
|
if (sepIndex != curStartIndex && sepIndex != curEndIndex)
|
|
{
|
|
ColumnGroupHeader parent = GetParent(cgh) as ColumnGroupHeader;
|
|
|
|
int n = curEndIndex - curStartIndex + 1;
|
|
|
|
int[] temp = new int[n];
|
|
int[] dmap = new int[map.Length];
|
|
|
|
for (int i = 0; i < n; i++)
|
|
temp[i] = map[curStartIndex + i];
|
|
|
|
for (int i = 0; i < dmap.Length; i++)
|
|
dmap[i] = 0;
|
|
|
|
if (sepIndex < curStartIndex)
|
|
{
|
|
for (int i = curStartIndex - 1; i >= sepIndex; i--)
|
|
{
|
|
map[i + n] = map[i];
|
|
dmap[i] = n;
|
|
}
|
|
|
|
for (int i = 0; i < n; i++)
|
|
map[sepIndex + i] = temp[i];
|
|
|
|
for (int i = curStartIndex; i <= curEndIndex; i++)
|
|
dmap[i] = sepIndex - curStartIndex;
|
|
}
|
|
else
|
|
{
|
|
for (int i = curEndIndex + 1; i <= sepIndex; i++)
|
|
{
|
|
map[i - n] = map[i];
|
|
dmap[i] = -n;
|
|
}
|
|
|
|
for (int i = 0; i < n; i++)
|
|
map[sepIndex - n + i + 1] = temp[i];
|
|
|
|
for (int i = curStartIndex; i <= curEndIndex; i++)
|
|
dmap[i] = sepIndex - curEndIndex;
|
|
}
|
|
|
|
for (int i = 0; i < map.Length; i++)
|
|
columns[map[i]].DisplayIndex = i;
|
|
|
|
UpdateGroupHeaderRanges(parent != null ? parent.GroupHeaders : cgh.Collection, dmap);
|
|
|
|
SuperGrid.UpdateStyleCount();
|
|
SuperGrid.PrimaryGrid.InvalidateRender();
|
|
|
|
for (int i = curStartIndex; i <= curEndIndex; i++)
|
|
SuperGrid.DoColumnMovedEvent(panel, columns[map[i]]);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region UpdateGroupHeaderRanges
|
|
|
|
private void UpdateGroupHeaderRanges(ColumnGroupHeaderCollection csc, int[] dmap)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in csc)
|
|
{
|
|
if (cgh.Visible == true)
|
|
{
|
|
UpdateGroupHeaderRanges(cgh.GroupHeaders, dmap);
|
|
|
|
cgh.StartDisplayIndex += dmap[cgh.StartDisplayIndex];
|
|
cgh.EndDisplayIndex += dmap[cgh.EndDisplayIndex];
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ColumnHeaderFwPaint
|
|
|
|
void ColumnHeaderFwPaint(object sender, PaintEventArgs e)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (_MouseDownHitItem is GridColumn)
|
|
{
|
|
GridColumn mouseDownHitColumn = (GridColumn)_MouseDownHitItem;
|
|
Rectangle r = mouseDownHitColumn.BoundsRelative;
|
|
|
|
r.Y = 0;
|
|
r.X = _OrderTextOffset;
|
|
r.Height = e.ClipRectangle.Height;
|
|
|
|
RenderColumnHeader(e.Graphics, panel, mouseDownHitColumn, r, false);
|
|
|
|
r.Width--;
|
|
r.Height--;
|
|
e.Graphics.DrawRectangle(Pens.DimGray, r);
|
|
}
|
|
else if (_MouseDownHitItem is ColumnGroupHeader)
|
|
{
|
|
ColumnGroupHeader cgh = (ColumnGroupHeader)_MouseDownHitItem;
|
|
Rectangle r = cgh.BoundsRelative;
|
|
|
|
r.Y = 0;
|
|
r.X = _OrderTextOffset;
|
|
r.Height = e.ClipRectangle.Height;
|
|
|
|
RenderGroupHeader(e.Graphics, panel, cgh, r);
|
|
|
|
r.Width--;
|
|
r.Height--;
|
|
e.Graphics.DrawRectangle(Pens.DimGray, r);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region SortColumn
|
|
|
|
internal void SortColumn(GridPanel panel, GridColumn column)
|
|
{
|
|
if (panel.IsSortable == true)
|
|
{
|
|
if (column.IsGroupColumn == true)
|
|
{
|
|
column.GroupDirection =
|
|
ToggleSortDirection(panel, column.GroupDirection, column.SortCycle);
|
|
|
|
SuperGrid.DoSortChangedEvent(panel);
|
|
}
|
|
else if (column.ColumnSortMode != ColumnSortMode.None)
|
|
{
|
|
SortDirection sortDirection =
|
|
ToggleSortDirection(panel, column.SortDirection, column.SortCycle);
|
|
|
|
if (column.ColumnSortMode == ColumnSortMode.Multiple &&
|
|
((Control.ModifierKeys & Keys.Shift) == Keys.Shift))
|
|
{
|
|
panel.AddSort(column, sortDirection);
|
|
}
|
|
else
|
|
{
|
|
if (panel.SortColumns.Count > 1)
|
|
sortDirection = SortDirection.Ascending;
|
|
|
|
panel.SetSort(column, sortDirection);
|
|
}
|
|
|
|
SuperGrid.DoSortChangedEvent(panel);
|
|
}
|
|
else
|
|
{
|
|
InvalidateHeader(panel, column);
|
|
}
|
|
}
|
|
else
|
|
{
|
|
InvalidateHeader(panel, column);
|
|
}
|
|
}
|
|
|
|
#region ToggleSortDirection
|
|
|
|
private SortDirection ToggleSortDirection(
|
|
GridPanel panel, SortDirection dir, SortCycle sortCycle)
|
|
{
|
|
if (dir == SortDirection.Ascending)
|
|
return (SortDirection.Descending);
|
|
|
|
if (dir == SortDirection.None)
|
|
return (SortDirection.Ascending);
|
|
|
|
if (sortCycle == SortCycle.NotSet)
|
|
{
|
|
sortCycle = panel.SortCycle;
|
|
|
|
if (sortCycle == SortCycle.NotSet)
|
|
sortCycle = SortCycle.AscDesc;
|
|
}
|
|
|
|
return (sortCycle == SortCycle.AscDescNone ? SortDirection.None : SortDirection.Ascending);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region Column Resize
|
|
|
|
#region StartResize
|
|
|
|
private void StartResize()
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
_ResizeColumn = _MouseDownHitItem as GridColumn;
|
|
|
|
if (_ResizeColumn != null)
|
|
{
|
|
_Resizing = true;
|
|
_ResizeWidth = _ResizeColumn.Size.Width;
|
|
|
|
_HitItem = _ResizeColumn;
|
|
_HitArea = HeaderArea.InResize;
|
|
|
|
if (panel.ImmediateResize == false)
|
|
{
|
|
_SeparatorFw = new FloatWindow();
|
|
_SeparatorFw.Opacity = .5;
|
|
_SeparatorFw.BackColor = Color.Black;
|
|
_SeparatorFw.Owner = SuperGrid.FindForm();
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region StopResize
|
|
|
|
private void StopResize()
|
|
{
|
|
_Resizing = false;
|
|
|
|
if (_SeparatorFw != null)
|
|
{
|
|
HideSeparator();
|
|
|
|
_SeparatorFw.Close();
|
|
_SeparatorFw.Dispose();
|
|
|
|
_SeparatorFw = null;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ContinueResize
|
|
|
|
private void ContinueResize(GridPanel panel, Point pt)
|
|
{
|
|
Rectangle r = panel.BoundsRelative;
|
|
r.Y = BoundsRelative.Y;
|
|
|
|
if (panel.IsSubPanel == true)
|
|
r.Y -= VScrollOffset;
|
|
|
|
r.X -= HScrollOffset;
|
|
|
|
if (pt.X > r.X)
|
|
{
|
|
Rectangle t = _ResizeColumn.BoundsRelative;
|
|
t.X -= HScrollOffset;
|
|
|
|
int width = pt.X - t.X;
|
|
|
|
int n = Dpi.Width(_ResizeColumn.MinimumWidth);
|
|
|
|
if (width < n)
|
|
pt.X = t.X + n;
|
|
|
|
if (pt.X >= SuperGrid.PrimaryGrid.BoundsRelative.Right - Dpi.Width2)
|
|
{
|
|
HideSeparator();
|
|
}
|
|
else
|
|
{
|
|
if (pt.X == panel.BoundsRelative.Right - 1)
|
|
pt.X -= 1;
|
|
|
|
r.X = pt.X;
|
|
|
|
r.Width = Dpi.Width(SeparatorWidth);
|
|
r.Height -= (BoundsRelative.Y - panel.BoundsRelative.Y);
|
|
|
|
t = SViewRect;
|
|
|
|
if (r.Bottom > t.Bottom)
|
|
r.Height -= (r.Bottom - t.Bottom);
|
|
|
|
r.Location = SuperGrid.PointToScreen(r.Location);
|
|
|
|
_SeparatorFw.Show();
|
|
|
|
_SeparatorFw.Bounds = r;
|
|
_SeparatorFw.Size = r.Size;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ResizeColumn
|
|
|
|
#region ResizeColumn
|
|
|
|
private void ResizeColumn(GridPanel panel, int width)
|
|
{
|
|
ColumnAutoSizeMode autoSizeMode = _ResizeColumn.GetAutoSizeMode();
|
|
|
|
if (autoSizeMode == ColumnAutoSizeMode.None)
|
|
ResizeNoneColumn(panel, width);
|
|
|
|
else if (autoSizeMode == ColumnAutoSizeMode.Fill)
|
|
ResizeFillColumn(panel, width);
|
|
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ResizeNoneColumn
|
|
|
|
private void ResizeNoneColumn(GridPanel panel, int width)
|
|
{
|
|
int newWidth = _ResizeWidth + width;
|
|
|
|
int n = Dpi.Width(_ResizeColumn.MinimumWidth);
|
|
|
|
if (newWidth < n)
|
|
newWidth = n;
|
|
|
|
if (_ResizeColumn.ResizeMode == ColumnResizeMode.MoveFollowingElements)
|
|
{
|
|
_ResizeColumn.Width = Dpi.DescaleWidth(newWidth);
|
|
}
|
|
else if (_ResizeColumn.ResizeMode == ColumnResizeMode.MaintainTotalWidth)
|
|
{
|
|
GridColumn ncolumn = panel.Columns.GetNextVisibleColumn(_ResizeColumn);
|
|
|
|
if ((ncolumn == null) || (ncolumn.GetAutoSizeMode() != ColumnAutoSizeMode.None))
|
|
{
|
|
_ResizeColumn.Width = Dpi.DescaleWidth(newWidth);
|
|
}
|
|
else
|
|
{
|
|
int twidth = _ResizeColumn.Size.Width + ncolumn.Size.Width;
|
|
int nwidth = twidth - newWidth;
|
|
|
|
int n2 = Dpi.Width(ncolumn.MinimumWidth);
|
|
|
|
if (nwidth < n2)
|
|
nwidth = n2;
|
|
|
|
newWidth = twidth - nwidth;
|
|
|
|
_ResizeColumn.Width = Dpi.DescaleWidth(newWidth);
|
|
ncolumn.Width = Dpi.DescaleWidth(nwidth);
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ResizeFillColumn
|
|
|
|
private void ResizeFillColumn(GridPanel panel, int width)
|
|
{
|
|
int fillWeight = 0;
|
|
int fillWidth = 0;
|
|
|
|
GridColumnCollection columns = _Columns;
|
|
|
|
int colDisplayIndex = columns.GetDisplayIndex(_ResizeColumn);
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
for (int i = 0; i < map.Length; i++)
|
|
{
|
|
int index = map[i];
|
|
|
|
GridColumn column = columns[index];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
if (column.GetAutoSizeMode() == ColumnAutoSizeMode.Fill)
|
|
{
|
|
fillWidth += column.Size.Width;
|
|
|
|
if (i != colDisplayIndex)
|
|
fillWeight += column.FillWeight;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (fillWidth > 0 && fillWeight > 0)
|
|
{
|
|
int nw = _ResizeWidth + width;
|
|
int newFillWidth = fillWidth - nw;
|
|
|
|
for (int i = 0; i < map.Length; i++)
|
|
{
|
|
int index = map[i];
|
|
|
|
GridColumn column = columns[index];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
if (column.GetAutoSizeMode() == ColumnAutoSizeMode.Fill)
|
|
{
|
|
float colWidth;
|
|
|
|
if (i != colDisplayIndex)
|
|
colWidth = (int)(newFillWidth * (float)column.FillWeight / fillWeight);
|
|
else
|
|
colWidth = nw;
|
|
|
|
int n = Dpi.Width(column.MinimumWidth);
|
|
|
|
if (colWidth < n)
|
|
colWidth = n;
|
|
|
|
column.FillWeight = (int)((colWidth * 1000) / fillWidth);
|
|
}
|
|
}
|
|
}
|
|
|
|
panel.SuperGrid.Invalidate();
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region RowHeader Resize
|
|
|
|
#region ContinueRowHeaderResize
|
|
|
|
private void ContinueRowHeaderResize(GridPanel panel, Point pt)
|
|
{
|
|
Rectangle r = panel.BoundsRelative;
|
|
r.Y = BoundsRelative.Y;
|
|
|
|
if (panel.IsSubPanel == true)
|
|
r.Y -= VScrollOffset;
|
|
|
|
r.X -= HScrollOffset;
|
|
|
|
if (pt.X > r.X)
|
|
{
|
|
int width = pt.X - r.X;
|
|
|
|
if (width < 5)
|
|
pt.X = r.X + 5;
|
|
|
|
if (pt.X >= SuperGrid.PrimaryGrid.BoundsRelative.Right - 2)
|
|
{
|
|
HideSeparator();
|
|
}
|
|
else
|
|
{
|
|
if (pt.X == panel.BoundsRelative.Right - 1)
|
|
pt.X--;
|
|
|
|
r.X = pt.X;
|
|
|
|
r.Width = SeparatorWidth;
|
|
r.Height -= (BoundsRelative.Y - panel.BoundsRelative.Y);
|
|
|
|
Rectangle t = SViewRect;
|
|
|
|
if (r.Bottom > t.Bottom)
|
|
r.Height -= (r.Bottom - t.Bottom);
|
|
|
|
r.Location = SuperGrid.PointToScreen(r.Location);
|
|
|
|
_SeparatorFw.Show();
|
|
|
|
_SeparatorFw.Bounds = r;
|
|
_SeparatorFw.Size = r.Size;
|
|
}
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ResizeRowHeader
|
|
|
|
private void ResizeRowHeader(GridPanel panel, int width)
|
|
{
|
|
Rectangle t = panel.ViewRect;
|
|
|
|
int n = Math.Max(5, _ResizeWidth + width);
|
|
|
|
if (t.Right - 10 < n)
|
|
n = t.Right - 10;
|
|
|
|
n = Dpi.DescaleWidth(n);
|
|
|
|
if (panel.RowHeaderWidth != n)
|
|
{
|
|
panel.RowHeaderWidth = n;
|
|
|
|
panel.SuperGrid.Invalidate();
|
|
|
|
SuperGrid.DoRowHeaderResizedEvent(panel);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ActivateFilterPopup
|
|
|
|
internal void ActivateFilterPopup(GridPanel panel, GridColumn column)
|
|
{
|
|
if (_FilterMenu != null)
|
|
_FilterMenu.Dispose();
|
|
|
|
_FilterMenu = new FilterPopup(panel);
|
|
|
|
_LockedColumn = true;
|
|
_HitArea = HeaderArea.NoWhere;
|
|
|
|
_FilterMenu.ActivatePopup(column, ResetColumnState);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region DeactivateFilterPopup
|
|
|
|
internal void DeactivateFilterPopup(GridPanel panel, GridColumn column)
|
|
{
|
|
FilterPopup fm = _FilterMenu;
|
|
|
|
if (fm != null)
|
|
fm.DeactivatePopup();
|
|
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetHitArea
|
|
|
|
///<summary>
|
|
/// Returns the ColumnHeader hit area
|
|
/// and column for the given Point
|
|
///</summary>
|
|
///<param name="pt"></param>
|
|
///<param name="column"></param>
|
|
///<returns>HeaderArea</returns>
|
|
public HeaderArea GetHitArea(Point pt, ref GridColumn column)
|
|
{
|
|
object hitItem = null;
|
|
|
|
HeaderArea area = GetHitArea(pt, ref hitItem, false);
|
|
|
|
column = hitItem as GridColumn;
|
|
|
|
return (area);
|
|
}
|
|
|
|
///<summary>
|
|
/// Returns the ColumnHeader hit area
|
|
/// and hit object for the given Point
|
|
///</summary>
|
|
///<param name="pt"></param>
|
|
///<param name="hitItem"></param>
|
|
///<returns></returns>
|
|
public HeaderArea GetHitArea(Point pt, ref object hitItem)
|
|
{
|
|
return (GetHitArea(pt, ref hitItem, false));
|
|
}
|
|
|
|
private HeaderArea GetHitArea(
|
|
Point pt, ref object hitItem, bool isMouseDown)
|
|
{
|
|
GridPanel panel = Parent as GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
GridElement hitObject = GetHitObject(panel, pt, isMouseDown);
|
|
|
|
if (hitObject == this)
|
|
return (GetHeaderHitArea(panel, pt, ref hitItem, isMouseDown));
|
|
|
|
if (hitObject == panel.GroupByRow)
|
|
return (HeaderArea.InGroupBox);
|
|
}
|
|
|
|
return (HeaderArea.NoWhere);
|
|
}
|
|
|
|
#region GetHitObject
|
|
|
|
private GridElement GetHitObject(
|
|
GridPanel panel, Point pt, bool isMouseDown)
|
|
{
|
|
if (isMouseDown == true && panel.GroupByRow.Visible == true)
|
|
{
|
|
if (panel.GroupByRow.Bounds.Contains(pt) == true)
|
|
return (panel.GroupByRow);
|
|
}
|
|
|
|
if (Capture == true || Bounds.Contains(pt) == true)
|
|
return (this);
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetHeaderHitArea
|
|
|
|
private HeaderArea GetHeaderHitArea(GridPanel panel,
|
|
Point pt, ref object hitItem, bool isMouseDown)
|
|
{
|
|
hitItem = null;
|
|
|
|
HeaderArea area = GetRowHeaderArea(panel, pt);
|
|
|
|
if (area != HeaderArea.NoWhere)
|
|
return (area);
|
|
|
|
area = GetGroupHeaderArea(panel, pt, ref hitItem);
|
|
|
|
if (area != HeaderArea.NoWhere)
|
|
return (area);
|
|
|
|
GridColumn column = GetHitColumn(panel, pt, isMouseDown, false);
|
|
|
|
area = GetHeaderArea(panel, pt, ref column);
|
|
|
|
hitItem = column;
|
|
|
|
return (area);
|
|
}
|
|
|
|
#region GetGroupHeaderArea
|
|
|
|
private HeaderArea GetGroupHeaderArea(GridPanel panel, Point pt, ref object hitItem)
|
|
{
|
|
ColumnGroupHeader cgh = GetHitGroupHeader(panel, pt, _GroupHeaders);
|
|
|
|
if (cgh != null)
|
|
{
|
|
if (GetShowRootColumnHeaders(cgh) == false)
|
|
{
|
|
GridColumn coll = GetHitColumn(panel, pt, false, true);
|
|
|
|
if (coll != null)
|
|
{
|
|
HeaderArea area = GetHeaderArea(panel, pt, ref coll);
|
|
|
|
if (area == HeaderArea.InResize)
|
|
{
|
|
hitItem = coll;
|
|
|
|
return (area);
|
|
}
|
|
}
|
|
}
|
|
|
|
hitItem = cgh;
|
|
|
|
if (IsMouseDown == false)
|
|
{
|
|
int[] map = panel.Columns.DisplayIndexMap;
|
|
|
|
Rectangle r = GetSubScrollBounds(panel, cgh);
|
|
|
|
if (pt.X < r.Left + 3 && pt.X >= r.Left)
|
|
{
|
|
if ((uint)cgh.StartDisplayIndex < map.Length)
|
|
{
|
|
GridColumn column = panel.Columns[map[cgh.StartDisplayIndex]];
|
|
|
|
if (InLeftResizeArea(ref column, panel) == true)
|
|
{
|
|
hitItem = column;
|
|
|
|
return (HeaderArea.InResize);
|
|
}
|
|
}
|
|
}
|
|
|
|
if ((pt.X > r.Right - 5) && (pt.X < r.Right + 3))
|
|
{
|
|
if ((uint)cgh.EndDisplayIndex < map.Length)
|
|
{
|
|
GridColumn column = panel.Columns[map[cgh.EndDisplayIndex]];
|
|
|
|
if (InRightResizeArea(ref column, panel) == true)
|
|
{
|
|
hitItem = column;
|
|
|
|
return (HeaderArea.InResize);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
if (cgh.AllowSelection == true)
|
|
return (HeaderArea.InContent);
|
|
|
|
return (HeaderArea.NoWhere);
|
|
}
|
|
|
|
return (HeaderArea.NoWhere);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetHitGroupHeader
|
|
|
|
private ColumnGroupHeader GetHitGroupHeader(
|
|
GridPanel panel, Point pt, ColumnGroupHeaderCollection csc)
|
|
{
|
|
if (csc != null)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in csc)
|
|
{
|
|
if (cgh.Visible == true)
|
|
{
|
|
Rectangle r = GetSubScrollBounds(panel, cgh);
|
|
|
|
if (r.Contains(pt) == true)
|
|
return (cgh);
|
|
|
|
ColumnGroupHeader csh2 = GetHitGroupHeader(panel, pt, cgh.GroupHeaders);
|
|
|
|
if (csh2 != null)
|
|
return (csh2);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRowHeaderArea
|
|
|
|
private HeaderArea GetRowHeaderArea(GridPanel panel, Point pt)
|
|
{
|
|
Rectangle r = GetRowHeaderBounds(panel);
|
|
|
|
r.Width += Dpi.Width2;
|
|
|
|
if (r.Contains(pt) == true)
|
|
{
|
|
if (Capture == true)
|
|
return (_HitArea);
|
|
|
|
r.Width -= Dpi.Width2;
|
|
|
|
if (panel.AllowRowHeaderResize == true)
|
|
{
|
|
if (pt.X >= r.Right - Dpi.Width5)
|
|
return (HeaderArea.InRowHeaderResize);
|
|
}
|
|
|
|
return (HeaderArea.InRowHeader);
|
|
}
|
|
|
|
return (HeaderArea.NoWhere);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetHitColumn
|
|
|
|
///<summary>
|
|
/// Gets the associated column at the given location
|
|
///</summary>
|
|
///<param name="x"></param>
|
|
///<param name="y"></param>
|
|
///<returns></returns>
|
|
public GridColumn GetHitColumn(int x, int y)
|
|
{
|
|
return (GetHitColumn(new Point(x, y)));
|
|
}
|
|
|
|
///<summary>
|
|
/// Gets the associated column at the given point
|
|
///</summary>
|
|
///<param name="pt"></param>
|
|
///<returns></returns>
|
|
public GridColumn GetHitColumn(Point pt)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
return (GetHitColumn(panel, pt, false, false));
|
|
|
|
return (null);
|
|
}
|
|
|
|
private GridColumn GetHitColumn(
|
|
GridPanel panel, Point pt, bool isMouseDown, bool limit)
|
|
{
|
|
int dy = (isMouseDown == true) ? 50 : 0;
|
|
|
|
GridColumnCollection columns = _Columns;
|
|
foreach (GridColumn column in columns)
|
|
{
|
|
if (column.Visible == true)
|
|
{
|
|
Rectangle r = GetBounds(panel, column);
|
|
|
|
if (pt.X >= r.Left && pt.X < r.Right)
|
|
{
|
|
int top = limit ? r.Bottom - 10 : r.Top;
|
|
|
|
if (pt.Y >= top && pt.Y < r.Bottom + dy)
|
|
return (column);
|
|
}
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetHeaderArea
|
|
|
|
private HeaderArea GetHeaderArea(GridPanel panel, Point pt, ref GridColumn column)
|
|
{
|
|
GridColumn hcolumn = column;
|
|
|
|
if (column == null)
|
|
column = panel.Columns.LastVisibleColumn;
|
|
|
|
if (column != null)
|
|
{
|
|
Rectangle r = column.BoundsRelative;
|
|
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
|
|
if (panel.IsSubPanel == true || column.IsHFrozen == false)
|
|
r.X -= HScrollOffset;
|
|
|
|
if (pt.X < r.Left + 3 && pt.X >= r.Left)
|
|
{
|
|
if (InLeftResizeArea(ref column, panel) == true)
|
|
return (HeaderArea.InResize);
|
|
}
|
|
|
|
if ((pt.X > r.Right - 5) && (pt.X < r.Right + 3))
|
|
{
|
|
if (InRightResizeArea(ref column, panel) == true)
|
|
return (HeaderArea.InResize);
|
|
}
|
|
|
|
if (column.FilterImageBounds.IsEmpty == false)
|
|
{
|
|
Rectangle t = GetScrollBounds(
|
|
panel, column, column.FilterImageBounds);
|
|
|
|
t.Inflate(2, 2);
|
|
|
|
if (t.Contains(pt) == true)
|
|
return (HeaderArea.InFilterMenu);
|
|
}
|
|
|
|
column = hcolumn;
|
|
|
|
if (hcolumn != null)
|
|
{
|
|
if (column.AllowSelection == true)
|
|
return (HeaderArea.InContent);
|
|
|
|
return (HeaderArea.NoWhere);
|
|
}
|
|
}
|
|
|
|
return (HeaderArea.InWhitespace);
|
|
}
|
|
|
|
#region InLeftResizeArea
|
|
|
|
private bool InLeftResizeArea(ref GridColumn column, GridPanel panel)
|
|
{
|
|
GridColumn pcolumn =
|
|
panel.Columns.GetPrevVisibleColumn(column);
|
|
|
|
if (pcolumn != null)
|
|
{
|
|
if (pcolumn.CanResize == true && pcolumn.ResizeMode != ColumnResizeMode.None)
|
|
{
|
|
column = pcolumn;
|
|
|
|
return (true);
|
|
}
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InRightResizeArea
|
|
|
|
private bool InRightResizeArea(ref GridColumn column, GridPanel panel)
|
|
{
|
|
GridColumn nColumn =
|
|
panel.Columns.GetNextVisibleColumn(column);
|
|
|
|
if (nColumn != null && nColumn.Size.Width < 5)
|
|
{
|
|
if (nColumn.CanResize == true && nColumn.ResizeMode != ColumnResizeMode.None)
|
|
column = nColumn;
|
|
}
|
|
|
|
if (column.CanResize == true && column.ResizeMode != ColumnResizeMode.None)
|
|
return (true);
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region GetParent
|
|
|
|
///<summary>
|
|
///Gets the object that is the "parent" of the given item
|
|
///(either a GridColumn or ColumnGroupHeader).
|
|
///</summary>
|
|
///<param name="item"></param>
|
|
///<returns>Parent or null</returns>
|
|
public object GetParent(object item)
|
|
{
|
|
if (item is GridColumn)
|
|
return (GetParentHeader((GridColumn) item));
|
|
|
|
ColumnGroupHeader cgh = item as ColumnGroupHeader;
|
|
|
|
if (cgh != null)
|
|
return (cgh.Collection.Parent);
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetParentHeader
|
|
|
|
///<summary>
|
|
///Gets the object that is the "parent" of the given column.
|
|
///</summary>
|
|
///<param name="column"></param>
|
|
///<returns>parent or null</returns>
|
|
public object GetParentHeader(GridColumn column)
|
|
{
|
|
int index = GridPanel.Columns.GetDisplayIndex(column);
|
|
|
|
return (GetParentHeader(index));
|
|
}
|
|
|
|
///<summary>
|
|
///Gets the ColumnGroupHeader that is the "parent" of the column at
|
|
///the given DISPLAY index.
|
|
///</summary>
|
|
///<param name="displayIndex">DISPLAY INDEX</param>
|
|
///<returns>parent object or null</returns>
|
|
public ColumnGroupHeader GetParentHeader(int displayIndex)
|
|
{
|
|
ColumnGroupHeader tcsh = GetColumnGroupHeader(GroupHeaders, displayIndex);
|
|
|
|
if (tcsh != null)
|
|
{
|
|
while (tcsh.GroupHeaders != null)
|
|
{
|
|
ColumnGroupHeader fcsh = GetColumnGroupHeader(tcsh.GroupHeaders, displayIndex);
|
|
|
|
if (fcsh == null || fcsh.Visible == false)
|
|
break;
|
|
|
|
tcsh = fcsh;
|
|
}
|
|
}
|
|
|
|
return (tcsh);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetColumnGroupHeader
|
|
|
|
internal ColumnGroupHeader GetColumnGroupHeader(int index)
|
|
{
|
|
return (GetColumnGroupHeader(GroupHeaders, index));
|
|
}
|
|
|
|
private ColumnGroupHeader GetColumnGroupHeader(IEnumerable<ColumnGroupHeader> csc, int index)
|
|
{
|
|
if (csc != null)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in csc)
|
|
{
|
|
if (cgh.Contains(index))
|
|
return (cgh.Visible == true ? cgh : null);
|
|
}
|
|
}
|
|
|
|
return (null);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region UpdateImageBounds
|
|
|
|
internal void UpdateImageBounds(GridPanel panel, GridColumn column)
|
|
{
|
|
Rectangle r = GetColumnHeaderBounds(panel, column);
|
|
|
|
if (column.AdjustSortImagePositionByMargin == true)
|
|
{
|
|
VisualStyle style = GetEffectiveStyle(column);
|
|
|
|
r.X += (style.BorderThickness.Left + style.Margin.Left);
|
|
r.Width -= (style.BorderThickness.Horizontal + style.Margin.Horizontal);
|
|
|
|
r.Y += (style.BorderThickness.Top + style.Margin.Top);
|
|
r.Height -= (style.BorderThickness.Vertical + style.Margin.Vertical);
|
|
}
|
|
|
|
r.Inflate(-3, -3);
|
|
r.Width--;
|
|
|
|
Alignment sortAlignment = (_SortImageAlignment == Alignment.NotSet)
|
|
? Alignment.TopCenter : _SortImageAlignment;
|
|
|
|
Alignment filterAlignment = (_FilterImageAlignment == Alignment.NotSet)
|
|
? Alignment.MiddleLeft : _FilterImageAlignment;
|
|
|
|
Rectangle rt = r;
|
|
|
|
column.SortImageBounds = Rectangle.Empty;
|
|
column.FilterImageBounds = Rectangle.Empty;
|
|
|
|
Image sortImage = GetColumnSortImage(panel, column);
|
|
|
|
if (sortImage != null)
|
|
{
|
|
Rectangle t = GetImageBounds(sortImage, sortAlignment, ref r);
|
|
|
|
column.SortImageBounds = t;
|
|
}
|
|
|
|
Image filterImage = GetColumnFilterImage(column);
|
|
|
|
if (filterImage != null)
|
|
{
|
|
Rectangle t;
|
|
|
|
if (sortImage != null && filterAlignment == sortAlignment)
|
|
{
|
|
t = GetImageBounds(filterImage, filterAlignment, ref r);
|
|
|
|
switch (filterAlignment)
|
|
{
|
|
case Alignment.TopCenter:
|
|
case Alignment.MiddleCenter:
|
|
case Alignment.BottomCenter:
|
|
t.X = rt.X + (r.Width - (sortImage.Width +
|
|
filterImage.Width)) / 2 + sortImage.Width;
|
|
break;
|
|
|
|
case Alignment.TopLeft:
|
|
case Alignment.MiddleLeft:
|
|
case Alignment.BottomLeft:
|
|
break;
|
|
}
|
|
}
|
|
else
|
|
{
|
|
t = GetImageBounds(filterImage, filterAlignment, ref rt);
|
|
|
|
r.Intersect(rt);
|
|
}
|
|
|
|
column.FilterImageBounds = t;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetColumnHeaderBounds
|
|
|
|
private Rectangle GetColumnHeaderBounds(GridPanel panel, GridColumn column)
|
|
{
|
|
Rectangle r = GetRelativeBounds(panel, column);
|
|
|
|
r.X = column.BoundsRelative.X;
|
|
r.Width = column.BoundsRelative.Width;
|
|
|
|
ColumnGroupHeader cgh = GetParentHeader(panel.Columns.GetDisplayIndex(column.ColumnIndex));
|
|
|
|
if (cgh != null)
|
|
{
|
|
int n = cgh.Size.Height - cgh.BoundsRelative.Height;
|
|
|
|
r.Y = r.Bottom - n;
|
|
r.Height = n;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRelativeSubSize
|
|
|
|
internal int GetRelativeSubSize(ColumnGroupHeader cgh, int index)
|
|
{
|
|
int n = cgh.BoundsRelative.Height;
|
|
|
|
foreach (ColumnGroupHeader sub in cgh.GroupHeaders)
|
|
{
|
|
if (sub.Contains(index) == true)
|
|
n += GetRelativeSubSize(sub, index);
|
|
}
|
|
|
|
return (n);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRowHeaderBounds
|
|
|
|
private Rectangle GetRowHeaderBounds(GridPanel panel)
|
|
{
|
|
if (panel.ShowRowHeaders == true)
|
|
{
|
|
Rectangle r = Bounds;
|
|
r.Width = panel.RowHeaderWidthEx;
|
|
|
|
Rectangle p = panel.PanelBounds;
|
|
|
|
if (r.Y < p.Y)
|
|
{
|
|
r.Height -= (p.Y - r.Y + 1);
|
|
r.Y = p.Y + 1;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
return (Rectangle.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region Style support
|
|
|
|
#region GroupHeader Style support
|
|
|
|
#region InvalidateStyle
|
|
|
|
///<summary>
|
|
///Invalidates the cached Style
|
|
///definition for all defined StyleTypes
|
|
///</summary>
|
|
public void InvalidateStyle()
|
|
{
|
|
GridColumnCollection columns = GridPanel.Columns;
|
|
|
|
foreach (GridColumn column in columns)
|
|
column.InvalidateStyle();
|
|
|
|
InvalidateStyle(GroupHeaders);
|
|
}
|
|
|
|
///<summary>
|
|
///Invalidates the cached Style
|
|
///definition for all GroupHeader defined StyleTypes
|
|
///</summary>
|
|
///<param name="cgh"></param>
|
|
public void InvalidateStyle(ColumnGroupHeader cgh)
|
|
{
|
|
if (cgh.EffectiveStyles != null)
|
|
{
|
|
cgh.EffectiveStyles.Dispose();
|
|
cgh.EffectiveStyles = null;
|
|
}
|
|
|
|
InvalidateStyle(cgh.GroupHeaders);
|
|
}
|
|
|
|
private void InvalidateStyle(IEnumerable<ColumnGroupHeader> groups)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in groups)
|
|
InvalidateStyle(cgh);
|
|
}
|
|
|
|
///<summary>
|
|
///Invalidate the cached Style
|
|
///definition for the given StyleType
|
|
///</summary>
|
|
///<param name="type"></param>
|
|
public void InvalidateStyle(StyleType type)
|
|
{
|
|
GridColumnCollection columns = GridPanel.Columns;
|
|
|
|
foreach (GridColumn column in columns)
|
|
column.InvalidateStyle(type);
|
|
|
|
InvalidateStyle(GroupHeaders, type);
|
|
}
|
|
|
|
///<summary>
|
|
///Invalidate the cached Style
|
|
///definition for the given GroupHeader StyleType
|
|
///</summary>
|
|
///<param name="cgh"></param>
|
|
///<param name="type"></param>
|
|
public void InvalidateStyle(ColumnGroupHeader cgh, StyleType type)
|
|
{
|
|
if (cgh.EffectiveStyles != null)
|
|
{
|
|
cgh.EffectiveStyles[type].Dispose();
|
|
cgh.EffectiveStyles[type] = null;
|
|
}
|
|
|
|
InvalidateStyle(cgh.GroupHeaders, type);
|
|
}
|
|
|
|
private void InvalidateStyle(IEnumerable<ColumnGroupHeader> groups, StyleType type)
|
|
{
|
|
foreach (ColumnGroupHeader cgh in groups)
|
|
InvalidateStyle(cgh, type);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSizingStyle
|
|
|
|
private ColumnHeaderVisualStyle GetSizingStyle(GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
StyleType style = panel.GetSizingStyle();
|
|
|
|
if (style == StyleType.NotSet)
|
|
style = StyleType.Default;
|
|
|
|
return (GetEffectiveStyle(cgh, style));
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetGroupHeaderStyleState
|
|
|
|
private StyleState GetGroupHeaderStyleState(ColumnGroupHeader cgh)
|
|
{
|
|
StyleState state = StyleState.Default;
|
|
|
|
if (_Reordering == true)
|
|
{
|
|
if (cgh == _MouseDownHitItem)
|
|
state |= StyleState.MouseOver;
|
|
}
|
|
else if (_HitItem == cgh)
|
|
{
|
|
state |= StyleState.MouseOver;
|
|
}
|
|
|
|
if (IsGroupHeaderSelected(cgh) == true)
|
|
state |= StyleState.Selected;
|
|
|
|
if (IsGroupHeaderReadOnly(cgh) == true)
|
|
state |= StyleState.ReadOnly;
|
|
|
|
return (state);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetEffectiveStyle
|
|
|
|
///<summary>
|
|
/// GetEffectiveStyle
|
|
///</summary>
|
|
///<param name="cgh"></param>
|
|
///<returns></returns>
|
|
public ColumnHeaderVisualStyle GetEffectiveStyle(ColumnGroupHeader cgh)
|
|
{
|
|
StyleState styleState = GetGroupHeaderStyleState(cgh);
|
|
ColumnHeaderVisualStyle style = GetEffectiveStyle(cgh, styleState);
|
|
|
|
return (style);
|
|
}
|
|
|
|
///<summary>
|
|
///Gets the EffectiveStyle for the given StyleState
|
|
///</summary>
|
|
///<param name="cgh"></param>
|
|
///<param name="cellState"></param>
|
|
///<returns></returns>
|
|
public ColumnHeaderVisualStyle
|
|
GetEffectiveStyle(ColumnGroupHeader cgh, StyleState cellState)
|
|
{
|
|
StyleType type = GetStyleType(cellState);
|
|
|
|
return (GetEffectiveStyle(cgh, type));
|
|
}
|
|
|
|
internal ColumnHeaderVisualStyle
|
|
GetEffectiveStyle(ColumnGroupHeader cgh, StyleType sizingStyle)
|
|
{
|
|
return (GetGroupHeaderStyle(cgh, sizingStyle));
|
|
}
|
|
|
|
#region GetGroupHeaderStyle
|
|
|
|
internal ColumnHeaderVisualStyle GetGroupHeaderStyle(ColumnGroupHeader cgh, StyleType e)
|
|
{
|
|
ValidateGroupHeaderStyle(cgh);
|
|
|
|
if (cgh.EffectiveStyles == null)
|
|
cgh.EffectiveStyles = new ColumnHeaderVisualStyles();
|
|
|
|
if (cgh.EffectiveStyles.IsValid(e) == false)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
ColumnHeaderVisualStyle style = new ColumnHeaderVisualStyle();
|
|
|
|
StyleType[] css = style.GetApplyStyleTypes(e);
|
|
|
|
if (css != null)
|
|
{
|
|
ColumnGroupHeader pcgh = GetParent(cgh) as ColumnGroupHeader;
|
|
|
|
if (pcgh != null)
|
|
{
|
|
if (GetAutoApplyGroupColor(cgh) != true)
|
|
pcgh = null;
|
|
}
|
|
|
|
foreach (StyleType cs in css)
|
|
{
|
|
style.ApplyStyle(SuperGrid.BaseVisualStyles.ColumnHeaderStyles[cs]);
|
|
style.ApplyStyle(SuperGrid.DefaultVisualStyles.ColumnHeaderStyles[cs]);
|
|
style.ApplyStyle(GridPanel.DefaultVisualStyles.ColumnHeaderStyles[cs]);
|
|
|
|
style.ApplyStyle(cgh.HeaderStyles[cs]);
|
|
|
|
if (pcgh != null)
|
|
{
|
|
ColumnHeaderVisualStyle gstyle = GetEffectiveStyle(pcgh, cs);
|
|
|
|
if (gstyle.Background != null)
|
|
{
|
|
if (cgh.HeaderStyles[cs].Background == null || cgh.HeaderStyles[cs].Background.IsEmpty)
|
|
style.Background = gstyle.Background.Copy();
|
|
}
|
|
|
|
if (gstyle.TextColor.IsEmpty == false)
|
|
{
|
|
if (cgh.HeaderStyles[cs].TextColor.IsEmpty)
|
|
style.TextColor = gstyle.TextColor;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
SuperGrid.DoGetColumnGroupHeaderStyleEvent(panel, cgh, e, ref style);
|
|
|
|
if (style.Background == null || style.Background.IsEmpty == true)
|
|
style.Background = new Background(Color.White);
|
|
|
|
if (style.Font == null)
|
|
style.Font = SystemFonts.DefaultFont;
|
|
|
|
cgh.EffectiveStyles[e] = style;
|
|
}
|
|
|
|
return (cgh.EffectiveStyles[e]);
|
|
}
|
|
|
|
#region ValidateGroupHeaderStyle
|
|
|
|
private void ValidateGroupHeaderStyle(ColumnGroupHeader cgh)
|
|
{
|
|
if (cgh.StyleUpdateCount != SuperGrid.StyleUpdateCount)
|
|
{
|
|
if (cgh.EffectiveStyles != null)
|
|
{
|
|
cgh.EffectiveStyles.Dispose();
|
|
cgh.EffectiveStyles = null;
|
|
}
|
|
|
|
cgh.StyleUpdateCount = SuperGrid.StyleUpdateCount;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region ColumnHeader Style support
|
|
|
|
#region GetSizingStyle
|
|
|
|
private ColumnHeaderVisualStyle GetSizingStyle(GridPanel panel, GridColumn column)
|
|
{
|
|
StyleType style = panel.GetSizingStyle();
|
|
|
|
if (style == StyleType.NotSet)
|
|
style = StyleType.Default;
|
|
|
|
return (GetEffectiveStyle(column, style));
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetStyleState
|
|
|
|
private StyleState GetStyleState(GridColumn column, bool selected)
|
|
{
|
|
StyleState state = StyleState.Default;
|
|
|
|
if (_Reordering == true)
|
|
{
|
|
if (column == _MouseDownHitItem)
|
|
state |= StyleState.MouseOver;
|
|
}
|
|
else if (_HitItem == column)
|
|
{
|
|
state |= StyleState.MouseOver;
|
|
}
|
|
|
|
if (selected == true)
|
|
state |= StyleState.Selected;
|
|
|
|
if (column.IsReadOnly == true)
|
|
state |= StyleState.ReadOnly;
|
|
|
|
return (state);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetStyleType
|
|
|
|
private StyleType GetStyleType(StyleState state)
|
|
{
|
|
switch (state)
|
|
{
|
|
case StyleState.MouseOver:
|
|
return (StyleType.MouseOver);
|
|
|
|
case StyleState.Selected:
|
|
return (StyleType.Selected);
|
|
|
|
case StyleState.Selected | StyleState.MouseOver:
|
|
return (StyleType.SelectedMouseOver);
|
|
|
|
case StyleState.ReadOnly:
|
|
return (StyleType.ReadOnly);
|
|
|
|
case StyleState.ReadOnly | StyleState.MouseOver:
|
|
return (StyleType.ReadOnlyMouseOver);
|
|
|
|
case StyleState.ReadOnly | StyleState.Selected:
|
|
return (StyleType.ReadOnlySelected);
|
|
|
|
case StyleState.ReadOnly | StyleState.MouseOver | StyleState.Selected:
|
|
return (StyleType.ReadOnlySelectedMouseOver);
|
|
|
|
default:
|
|
return (StyleType.Default);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetEffectiveStyle
|
|
|
|
///<summary>
|
|
/// GetEffectiveStyle
|
|
///</summary>
|
|
///<param name="column"></param>
|
|
///<returns></returns>
|
|
public ColumnHeaderVisualStyle GetEffectiveStyle(GridColumn column)
|
|
{
|
|
StyleState styleState = GetStyleState(column, column.IsSelected);
|
|
ColumnHeaderVisualStyle style = GetEffectiveStyle(column, styleState);
|
|
|
|
return (style);
|
|
}
|
|
|
|
///<summary>
|
|
///Gets the EffectiveStyle for the given StyleState
|
|
///</summary>
|
|
///<param name="column"></param>
|
|
///<param name="cellState"></param>
|
|
///<returns></returns>
|
|
public ColumnHeaderVisualStyle
|
|
GetEffectiveStyle(GridColumn column, StyleState cellState)
|
|
{
|
|
StyleType type = GetStyleType(cellState);
|
|
|
|
return (GetEffectiveStyle(column, type));
|
|
}
|
|
|
|
internal ColumnHeaderVisualStyle
|
|
GetEffectiveStyle(GridColumn column, StyleType type)
|
|
{
|
|
return (column.GetHeaderStyle(type));
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetEffectiveRowHeaderStyle
|
|
|
|
internal ColumnHeaderRowVisualStyle GetEffectiveRowHeaderStyle()
|
|
{
|
|
return (GetEffectiveRowHeaderStyleEx(GetRowHeaderState()));
|
|
}
|
|
|
|
internal ColumnHeaderRowVisualStyle
|
|
GetEffectiveRowHeaderStyleEx(StyleState rowState)
|
|
{
|
|
ValidateRowHeaderStyle();
|
|
|
|
StyleType type = GetStyleType(rowState);
|
|
|
|
return (GetRowHeaderStyle(type));
|
|
}
|
|
|
|
#region ValidateRowHeaderStyle
|
|
|
|
private void ValidateRowHeaderStyle()
|
|
{
|
|
if (_StyleUpdateCount != SuperGrid.StyleUpdateCount)
|
|
{
|
|
_EffectiveRowHeaderStyles = null;
|
|
|
|
_StyleUpdateCount = SuperGrid.StyleUpdateCount;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRowHeaderState
|
|
|
|
private StyleState GetRowHeaderState()
|
|
{
|
|
StyleState rowState = StyleState.Default;
|
|
|
|
if (_HitArea == HeaderArea.InRowHeader || _HitArea == HeaderArea.InWhitespace)
|
|
rowState |= StyleState.MouseOver;
|
|
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
if (panel.ReadOnly == true)
|
|
rowState |= StyleState.ReadOnly;
|
|
|
|
if (panel == SuperGrid.ActiveGrid)
|
|
rowState |= StyleState.Selected;
|
|
}
|
|
|
|
return (rowState);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRowHeaderStyle
|
|
|
|
private ColumnHeaderRowVisualStyle GetRowHeaderStyle(StyleType e)
|
|
{
|
|
if (_EffectiveRowHeaderStyles == null)
|
|
_EffectiveRowHeaderStyles = new ColumnHeaderRowVisualStyles();
|
|
|
|
if (_EffectiveRowHeaderStyles.IsValid(e) == false)
|
|
{
|
|
ColumnHeaderRowVisualStyle style = new ColumnHeaderRowVisualStyle();
|
|
|
|
StyleType[] css = style.GetApplyStyleTypes(e);
|
|
|
|
if (css != null)
|
|
{
|
|
foreach (StyleType cs in css)
|
|
{
|
|
style.ApplyStyle(SuperGrid.BaseVisualStyles.ColumnHeaderRowStyles[cs]);
|
|
style.ApplyStyle(SuperGrid.DefaultVisualStyles.ColumnHeaderRowStyles[cs]);
|
|
style.ApplyStyle(GridPanel.DefaultVisualStyles.ColumnHeaderRowStyles[cs]);
|
|
}
|
|
}
|
|
|
|
SuperGrid.DoGetColumnHeaderRowHeaderStyleEvent(this, e, ref style);
|
|
|
|
if (style.RowHeader.Background == null || style.RowHeader.Background.IsEmpty == true)
|
|
style.RowHeader.Background = new Background(Color.WhiteSmoke);
|
|
|
|
_EffectiveRowHeaderStyles[e] = style;
|
|
}
|
|
|
|
return (_EffectiveRowHeaderStyles[e]);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
|
|
#region GetShowRootColumnHeaders
|
|
|
|
private bool GetShowRootColumnHeaders(ColumnGroupHeader cgh)
|
|
{
|
|
while (cgh != null)
|
|
{
|
|
if (cgh.ShowColumnHeaders != Tbool.NotSet)
|
|
return (cgh.ShowColumnHeaders == Tbool.True);
|
|
|
|
cgh = cgh.Collection.Parent as ColumnGroupHeader;
|
|
}
|
|
|
|
return (_ShowGroupColumnHeaders);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetAutoApplyGroupColor
|
|
|
|
internal bool GetAutoApplyGroupColor(ColumnGroupHeader cgh)
|
|
{
|
|
if (cgh.AutoApplyGroupColors != Tbool.NotSet)
|
|
return (cgh.AutoApplyGroupColors == Tbool.True);
|
|
|
|
return (AutoApplyGroupColors);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region IsGroupHeaderSelected
|
|
|
|
///<summary>
|
|
///Returns whether the given GroupHeader is selected (ie. all
|
|
///visible columns/headers it encompasses must be selected)
|
|
///</summary>
|
|
///<param name="cgh">GroupHeader</param>
|
|
///<returns>true, if all selected</returns>
|
|
public bool IsGroupHeaderSelected(ColumnGroupHeader cgh)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
GridColumnCollection columns = panel.Columns;
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
bool selected = false;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint) i < map.Length)
|
|
{
|
|
GridColumn column = columns[map[i]];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
if (column.IsSelected == false)
|
|
return (false);
|
|
|
|
selected = true;
|
|
}
|
|
}
|
|
}
|
|
|
|
return (selected);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region IsGroupHeaderReadOnly
|
|
|
|
/// <summary>
|
|
///Returns whether the given GroupHeader is ReadOnly (ie. all
|
|
///visible columns/headers it encompasses must be ReadOnly)
|
|
/// </summary>
|
|
/// <param name="cgh"></param>
|
|
/// <returns></returns>
|
|
public bool IsGroupHeaderReadOnly(ColumnGroupHeader cgh)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
GridColumnCollection columns = panel.Columns;
|
|
|
|
int[] map = columns.DisplayIndexMap;
|
|
|
|
bool readOnly = false;
|
|
|
|
for (int i = cgh.StartDisplayIndex; i <= cgh.EndDisplayIndex; i++)
|
|
{
|
|
if ((uint)i >= map.Length)
|
|
break;
|
|
|
|
GridColumn column = columns[map[i]];
|
|
|
|
if (column.Visible == true)
|
|
{
|
|
if (column.IsReadOnly == false)
|
|
return (false);
|
|
|
|
readOnly = true;
|
|
}
|
|
}
|
|
|
|
return (readOnly);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region IsItemHFrozen
|
|
|
|
internal bool IsItemHFrozen(object item)
|
|
{
|
|
if (item is GridColumn)
|
|
return ((GridColumn)item).IsHFrozenEx;
|
|
|
|
if (item is ColumnGroupHeader)
|
|
return (IsGroupHeaderHFrozen(GridPanel, (ColumnGroupHeader)item));
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region IsGroupHeaderHFrozen
|
|
|
|
internal bool IsGroupHeaderHFrozen(GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
if (panel.IsSubPanel == false)
|
|
{
|
|
if (cgh != null)
|
|
return (cgh.StartDisplayIndex < panel.FrozenColumnCount);
|
|
}
|
|
|
|
return (false);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetBounds
|
|
|
|
internal Rectangle GetBounds(GridPanel panel, GridColumn column)
|
|
{
|
|
Rectangle r = GetRelativeBounds(panel, column);
|
|
|
|
return (GetScrollBounds(panel, column, r));
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetRelativeBounds
|
|
|
|
internal Rectangle GetRelativeBounds(GridPanel panel, GridColumn column)
|
|
{
|
|
Rectangle r = BoundsRelative;
|
|
|
|
r.X = column.BoundsRelative.X;
|
|
r.Width = column.BoundsRelative.Width;
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetScrollBounds
|
|
|
|
internal Rectangle GetScrollBounds(
|
|
GridPanel panel, GridColumn column, Rectangle r)
|
|
{
|
|
if (r.IsEmpty == false)
|
|
{
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
|
|
if (panel.IsSubPanel == true || column.IsHFrozen == false)
|
|
r.X -= HScrollOffset;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSubScrollBounds
|
|
|
|
internal Rectangle GetSubScrollBounds(GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
Rectangle r = cgh.BoundsRelative;
|
|
|
|
if (r.IsEmpty == false)
|
|
{
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
|
|
if (panel.IsSubPanel == true || IsGroupHeaderHFrozen(panel, cgh) == false)
|
|
r.X -= HScrollOffset;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetSubContScrollBounds
|
|
|
|
internal Rectangle GetSubContScrollBounds(GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
Rectangle r = cgh.BoundsRelative;
|
|
r.Height = cgh.Size.Height;
|
|
|
|
if (r.IsEmpty == false)
|
|
{
|
|
if (IsVFrozen == false)
|
|
r.Y -= VScrollOffset;
|
|
|
|
if (panel.IsSubPanel == true || IsGroupHeaderHFrozen(panel, cgh) == false)
|
|
r.X -= HScrollOffset;
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetContentBounds
|
|
|
|
internal Rectangle GetContentBounds(GridPanel panel, ColumnHeaderVisualStyle style, Rectangle r)
|
|
{
|
|
if (_ShowHeaderImages == true)
|
|
{
|
|
object figure = style.GetFigure(panel);
|
|
|
|
if (figure != null)
|
|
{
|
|
Size size = style.GetFigureSize(panel);
|
|
|
|
if (style.IsOverlayImage != true)
|
|
{
|
|
switch (style.ImageAlignment)
|
|
{
|
|
case Alignment.TopCenter:
|
|
r.Y += size.Height;
|
|
r.Height -= size.Height;
|
|
break;
|
|
|
|
case Alignment.MiddleCenter:
|
|
break;
|
|
|
|
case Alignment.BottomCenter:
|
|
r.Height -= size.Height;
|
|
break;
|
|
|
|
case Alignment.TopRight:
|
|
case Alignment.MiddleRight:
|
|
case Alignment.BottomRight:
|
|
r.Width -= size.Width;
|
|
break;
|
|
|
|
default:
|
|
r.X += size.Width;
|
|
r.Width -= size.Width;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetAdjustedBounds
|
|
|
|
private Rectangle GetAdjustedBounds(VisualStyle style, Rectangle r)
|
|
{
|
|
r.X += Dpi.Width(style.BorderThickness.Left + style.Margin.Left + style.Padding.Left);
|
|
r.Width -= Dpi.Width(style.BorderThickness.Horizontal + style.Margin.Horizontal + style.Padding.Horizontal);
|
|
|
|
r.Y += Dpi.Height(style.BorderThickness.Top + style.Margin.Top + style.Padding.Top);
|
|
r.Height -= Dpi.Height(style.BorderThickness.Vertical + style.Margin.Vertical + style.Padding.Vertical);
|
|
|
|
return (r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region GetImageBounds
|
|
|
|
/// <summary>
|
|
/// Gets the bounding rectangle for the
|
|
/// given column header image
|
|
/// </summary>
|
|
/// <param name="column"></param>
|
|
/// <returns>Bounding rectangle</returns>
|
|
public Rectangle GetImageBounds(GridColumn column)
|
|
{
|
|
if (_ShowHeaderImages == true)
|
|
{
|
|
GridPanel panel = GridPanel;
|
|
|
|
if (panel != null)
|
|
{
|
|
SuperGridControl sg = panel.SuperGrid;
|
|
|
|
if (sg != null)
|
|
{
|
|
ColumnHeaderVisualStyle style = GetEffectiveStyle(column);
|
|
|
|
object figure = style.GetFigure(panel);
|
|
|
|
if (figure != null)
|
|
{
|
|
Rectangle bounds = GetBounds(panel, column);
|
|
|
|
using (Graphics g = sg.CreateGraphics())
|
|
{
|
|
Rectangle t = GetAdjustedBounds(style,
|
|
GetContentBounds(panel, style, bounds));
|
|
|
|
return (style.GetFigureBounds(panel, t));
|
|
}
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
return (Rectangle.Empty);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InvalidateHeader
|
|
|
|
internal void InvalidateHeader(GridPanel panel, GridColumn column)
|
|
{
|
|
Rectangle bounds = BoundsRelative;
|
|
|
|
if (panel.IsVFrozen == false)
|
|
bounds.Y -= VScrollOffset;
|
|
|
|
bounds.X = column.BoundsRelative.X;
|
|
bounds.Width = column.BoundsRelative.Width;
|
|
|
|
if (panel.IsSubPanel == true || column.IsHFrozen == false)
|
|
bounds.X -= HScrollOffset;
|
|
|
|
InvalidateRender(bounds);
|
|
}
|
|
|
|
private void InvalidateHeader(GridPanel panel, ColumnGroupHeader cgh)
|
|
{
|
|
Rectangle r = GetSubScrollBounds(panel, cgh);
|
|
|
|
InvalidateRender(r);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InvalidateRowHeader
|
|
|
|
internal void InvalidateRowHeader()
|
|
{
|
|
InvalidateRender(RowHeaderBounds);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InvalidateWhitespace
|
|
|
|
internal void InvalidateWhitespace()
|
|
{
|
|
Rectangle bounds = Bounds;
|
|
|
|
GridColumn col = GridPanel.Columns.LastVisibleColumn;
|
|
|
|
if (col != null)
|
|
{
|
|
if (col.Bounds.Right < bounds.Right)
|
|
{
|
|
int n = bounds.Right - col.Bounds.Right;
|
|
|
|
bounds.X = col.Bounds.Right;
|
|
bounds.Width = n;
|
|
}
|
|
|
|
InvalidateRender(bounds);
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region InvalidateItem
|
|
|
|
private void InvalidateItem(GridPanel panel, object item)
|
|
{
|
|
if (item is GridColumn)
|
|
InvalidateHeader(panel, (GridColumn)item);
|
|
|
|
else if (item is ColumnGroupHeader)
|
|
InvalidateHeader(panel, (ColumnGroupHeader)item);
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region CancelCapture
|
|
|
|
/// <summary>
|
|
/// Cancels any in progress operations (resize, reorder)
|
|
/// that may have the mouse captured.
|
|
/// </summary>
|
|
public override void CancelCapture()
|
|
{
|
|
StopReorder();
|
|
StopResize();
|
|
|
|
_MouseDownHitItem = null;
|
|
|
|
base.CancelCapture();
|
|
}
|
|
|
|
#endregion
|
|
}
|
|
|
|
#region enums
|
|
|
|
#region HeaderArea
|
|
|
|
///<summary>
|
|
/// HeaderArea
|
|
///</summary>
|
|
public enum HeaderArea
|
|
{
|
|
///<summary>
|
|
/// NoWhere
|
|
///</summary>
|
|
NoWhere,
|
|
|
|
///<summary>
|
|
/// InContent
|
|
///</summary>
|
|
InContent,
|
|
|
|
///<summary>
|
|
/// InResize
|
|
///</summary>
|
|
InResize,
|
|
|
|
///<summary>
|
|
/// InRowHeader
|
|
///</summary>
|
|
InRowHeader,
|
|
|
|
///<summary>
|
|
/// InRowHeaderResize
|
|
///</summary>
|
|
InRowHeaderResize,
|
|
|
|
///<summary>
|
|
/// InWhitespace
|
|
///</summary>
|
|
InWhitespace,
|
|
|
|
///<summary>
|
|
/// InMarkup
|
|
///</summary>
|
|
InMarkup,
|
|
|
|
///<summary>
|
|
/// InFilterMenu
|
|
///</summary>
|
|
InFilterMenu,
|
|
|
|
///<summary>
|
|
/// InGroupBox
|
|
///</summary>
|
|
InGroupBox,
|
|
}
|
|
|
|
#endregion
|
|
|
|
#region ImageVisibility
|
|
|
|
///<summary>
|
|
/// ImageVisibility
|
|
///</summary>
|
|
public enum ImageVisibility
|
|
{
|
|
///<summary>
|
|
/// NotSet
|
|
///</summary>
|
|
NotSet = -1,
|
|
|
|
///<summary>
|
|
/// Auto
|
|
///</summary>
|
|
Auto,
|
|
|
|
///<summary>
|
|
/// Always
|
|
///</summary>
|
|
Always,
|
|
|
|
///<summary>
|
|
/// Never
|
|
///</summary>
|
|
Never,
|
|
}
|
|
|
|
#endregion
|
|
|
|
#endregion
|
|
} |