------ #### RaUIV4 V4.0.2311.0701 - *.[全新]整合了MyDb、ryControls、MyDb_MySQL等dll文件到RaUI一个项目。 - *.[新增]新增ApkOp类,可以轻松获取APK信息。 - *.[新增]新增JsonExt扩展类,让Json操作更简单。 - *.[新增]新增WebP类,可以支持webp格式的图片。 - *.[改进]ryQuickSQL中的AddField方法改为自动替换已存在的同名值。 - *.[修复]ryQuickSQL中的AddFieldCalc方法无法正常计算的BUG。
477 lines
16 KiB
C#
477 lines
16 KiB
C#
using System;
|
|
using System.Drawing;
|
|
using System.Windows.Forms;
|
|
using System.Drawing.Drawing2D;
|
|
|
|
namespace WeifenLuo.WinFormsUI.Docking
|
|
{
|
|
internal class VS2012AutoHideStrip : AutoHideStripBase
|
|
{
|
|
private class TabVS2012 : Tab
|
|
{
|
|
internal TabVS2012(IDockContent content)
|
|
: base(content)
|
|
{
|
|
}
|
|
|
|
/// <summary>
|
|
/// X for this <see href="TabVS2012"/> inside the logical strip rectangle.
|
|
/// </summary>
|
|
public int TabX { get; set; }
|
|
|
|
/// <summary>
|
|
/// Width of this <see href="TabVS2012"/>.
|
|
/// </summary>
|
|
public int TabWidth { get; set; }
|
|
|
|
public bool IsMouseOver { get; set; }
|
|
}
|
|
|
|
private const int TextGapLeft = 0;
|
|
private const int TextGapRight = 0;
|
|
private const int TextGapBottom = 3;
|
|
private const int TabGapTop = 3;
|
|
private const int TabGapBottom = 8;
|
|
private const int TabGapLeft = 0;
|
|
private const int TabGapBetween = 12;
|
|
|
|
#region Customizable Properties
|
|
public Font TextFont
|
|
{
|
|
get { return DockPanel.Theme.Skin.AutoHideStripSkin.TextFont; }
|
|
}
|
|
|
|
private static StringFormat _stringFormatTabHorizontal;
|
|
private StringFormat StringFormatTabHorizontal
|
|
{
|
|
get
|
|
{
|
|
if (_stringFormatTabHorizontal == null)
|
|
{
|
|
_stringFormatTabHorizontal = new StringFormat();
|
|
_stringFormatTabHorizontal.Alignment = StringAlignment.Near;
|
|
_stringFormatTabHorizontal.LineAlignment = StringAlignment.Center;
|
|
_stringFormatTabHorizontal.FormatFlags = StringFormatFlags.NoWrap;
|
|
_stringFormatTabHorizontal.Trimming = StringTrimming.None;
|
|
}
|
|
|
|
if (RightToLeft == RightToLeft.Yes)
|
|
_stringFormatTabHorizontal.FormatFlags |= StringFormatFlags.DirectionRightToLeft;
|
|
else
|
|
_stringFormatTabHorizontal.FormatFlags &= ~StringFormatFlags.DirectionRightToLeft;
|
|
|
|
return _stringFormatTabHorizontal;
|
|
}
|
|
}
|
|
|
|
private static StringFormat _stringFormatTabVertical;
|
|
private StringFormat StringFormatTabVertical
|
|
{
|
|
get
|
|
{
|
|
if (_stringFormatTabVertical == null)
|
|
{
|
|
_stringFormatTabVertical = new StringFormat();
|
|
_stringFormatTabVertical.Alignment = StringAlignment.Near;
|
|
_stringFormatTabVertical.LineAlignment = StringAlignment.Center;
|
|
_stringFormatTabVertical.FormatFlags = StringFormatFlags.NoWrap | StringFormatFlags.DirectionVertical;
|
|
_stringFormatTabVertical.Trimming = StringTrimming.None;
|
|
}
|
|
if (RightToLeft == RightToLeft.Yes)
|
|
_stringFormatTabVertical.FormatFlags |= StringFormatFlags.DirectionRightToLeft;
|
|
else
|
|
_stringFormatTabVertical.FormatFlags &= ~StringFormatFlags.DirectionRightToLeft;
|
|
|
|
return _stringFormatTabVertical;
|
|
}
|
|
}
|
|
|
|
#endregion
|
|
|
|
private static Matrix _matrixIdentity = new Matrix();
|
|
private static Matrix MatrixIdentity
|
|
{
|
|
get { return _matrixIdentity; }
|
|
}
|
|
|
|
private static DockState[] _dockStates;
|
|
private static DockState[] DockStates
|
|
{
|
|
get
|
|
{
|
|
if (_dockStates == null)
|
|
{
|
|
_dockStates = new DockState[4];
|
|
_dockStates[0] = DockState.DockLeftAutoHide;
|
|
_dockStates[1] = DockState.DockRightAutoHide;
|
|
_dockStates[2] = DockState.DockTopAutoHide;
|
|
_dockStates[3] = DockState.DockBottomAutoHide;
|
|
}
|
|
return _dockStates;
|
|
}
|
|
}
|
|
|
|
private static GraphicsPath _graphicsPath;
|
|
internal static GraphicsPath GraphicsPath
|
|
{
|
|
get
|
|
{
|
|
if (_graphicsPath == null)
|
|
_graphicsPath = new GraphicsPath();
|
|
|
|
return _graphicsPath;
|
|
}
|
|
}
|
|
|
|
public VS2012AutoHideStrip(DockPanel panel)
|
|
: base(panel)
|
|
{
|
|
SetStyle(ControlStyles.ResizeRedraw |
|
|
ControlStyles.UserPaint |
|
|
ControlStyles.AllPaintingInWmPaint |
|
|
ControlStyles.OptimizedDoubleBuffer, true);
|
|
BackColor = DockPanel.Theme.ColorPalette.MainWindowActive.Background;
|
|
}
|
|
|
|
protected override void OnPaint(PaintEventArgs e)
|
|
{
|
|
base.OnPaint(e);
|
|
Graphics g = e.Graphics;
|
|
DrawTabStrip(g);
|
|
}
|
|
|
|
protected override void OnLayout(LayoutEventArgs levent)
|
|
{
|
|
CalculateTabs();
|
|
base.OnLayout(levent);
|
|
}
|
|
|
|
private void DrawTabStrip(Graphics g)
|
|
{
|
|
DrawTabStrip(g, DockState.DockTopAutoHide);
|
|
DrawTabStrip(g, DockState.DockBottomAutoHide);
|
|
DrawTabStrip(g, DockState.DockLeftAutoHide);
|
|
DrawTabStrip(g, DockState.DockRightAutoHide);
|
|
}
|
|
|
|
private void DrawTabStrip(Graphics g, DockState dockState)
|
|
{
|
|
Rectangle rectTabStrip = GetLogicalTabStripRectangle(dockState);
|
|
|
|
if (rectTabStrip.IsEmpty)
|
|
return;
|
|
|
|
Matrix matrixIdentity = g.Transform;
|
|
if (dockState == DockState.DockLeftAutoHide || dockState == DockState.DockRightAutoHide)
|
|
{
|
|
Matrix matrixRotated = new Matrix();
|
|
matrixRotated.RotateAt(90, new PointF((float)rectTabStrip.X + (float)rectTabStrip.Height / 2,
|
|
(float)rectTabStrip.Y + (float)rectTabStrip.Height / 2));
|
|
g.Transform = matrixRotated;
|
|
}
|
|
|
|
foreach (Pane pane in GetPanes(dockState))
|
|
{
|
|
foreach (TabVS2012 tab in pane.AutoHideTabs)
|
|
DrawTab(g, tab);
|
|
}
|
|
|
|
g.Transform = matrixIdentity;
|
|
}
|
|
|
|
private void CalculateTabs()
|
|
{
|
|
CalculateTabs(DockState.DockTopAutoHide);
|
|
CalculateTabs(DockState.DockBottomAutoHide);
|
|
CalculateTabs(DockState.DockLeftAutoHide);
|
|
CalculateTabs(DockState.DockRightAutoHide);
|
|
}
|
|
|
|
private void CalculateTabs(DockState dockState)
|
|
{
|
|
Rectangle rectTabStrip = GetLogicalTabStripRectangle(dockState);
|
|
|
|
int x = TabGapLeft + rectTabStrip.X;
|
|
foreach (Pane pane in GetPanes(dockState))
|
|
{
|
|
foreach (TabVS2012 tab in pane.AutoHideTabs)
|
|
{
|
|
int width = TextRenderer.MeasureText(tab.Content.DockHandler.TabText, TextFont).Width +
|
|
TextGapLeft + TextGapRight;
|
|
tab.TabX = x;
|
|
tab.TabWidth = width;
|
|
x += width + TabGapBetween;
|
|
}
|
|
}
|
|
}
|
|
|
|
private Rectangle RtlTransform(Rectangle rect, DockState dockState)
|
|
{
|
|
Rectangle rectTransformed;
|
|
if (dockState == DockState.DockLeftAutoHide || dockState == DockState.DockRightAutoHide)
|
|
rectTransformed = rect;
|
|
else
|
|
rectTransformed = DrawHelper.RtlTransform(this, rect);
|
|
|
|
return rectTransformed;
|
|
}
|
|
|
|
private GraphicsPath GetTabOutline(TabVS2012 tab, bool rtlTransform)
|
|
{
|
|
DockState dockState = tab.Content.DockHandler.DockState;
|
|
Rectangle rectTab = GetTabRectangle(tab);
|
|
if (rtlTransform)
|
|
rectTab = RtlTransform(rectTab, dockState);
|
|
|
|
if (GraphicsPath != null)
|
|
{
|
|
GraphicsPath.Reset();
|
|
GraphicsPath.AddRectangle(rectTab);
|
|
}
|
|
|
|
return GraphicsPath;
|
|
}
|
|
|
|
private void DrawTab(Graphics g, TabVS2012 tab)
|
|
{
|
|
Rectangle rectTabOrigin = GetTabRectangle(tab);
|
|
if (rectTabOrigin.IsEmpty)
|
|
return;
|
|
|
|
DockState dockState = tab.Content.DockHandler.DockState;
|
|
IDockContent content = tab.Content;
|
|
|
|
//Set no rotate for drawing icon and text
|
|
Matrix matrixRotate = g.Transform;
|
|
g.Transform = MatrixIdentity;
|
|
|
|
Color borderColor;
|
|
Color backgroundColor;
|
|
Color textColor;
|
|
if (tab.IsMouseOver)
|
|
{
|
|
borderColor = DockPanel.Theme.ColorPalette.AutoHideStripHovered.Border;
|
|
backgroundColor = DockPanel.Theme.ColorPalette.AutoHideStripHovered.Background;
|
|
textColor = DockPanel.Theme.ColorPalette.AutoHideStripHovered.Text;
|
|
}
|
|
else
|
|
{
|
|
borderColor = DockPanel.Theme.ColorPalette.AutoHideStripDefault.Border;
|
|
backgroundColor = DockPanel.Theme.ColorPalette.AutoHideStripDefault.Background;
|
|
textColor = DockPanel.Theme.ColorPalette.AutoHideStripDefault.Text;
|
|
}
|
|
|
|
g.FillRectangle(DockPanel.Theme.PaintingService.GetBrush(backgroundColor), rectTabOrigin);
|
|
|
|
Rectangle rectBorder = GetBorderRectangle(rectTabOrigin, dockState, TextRenderer.MeasureText(tab.Content.DockHandler.TabText, TextFont).Width);
|
|
g.FillRectangle(DockPanel.Theme.PaintingService.GetBrush(borderColor), rectBorder);
|
|
|
|
// Draw the text
|
|
Rectangle rectText = GetTextRectangle(rectTabOrigin, dockState);
|
|
|
|
if (dockState == DockState.DockLeftAutoHide || dockState == DockState.DockRightAutoHide)
|
|
g.DrawString(content.DockHandler.TabText, TextFont, DockPanel.Theme.PaintingService.GetBrush(textColor), rectText, StringFormatTabVertical);
|
|
else
|
|
g.DrawString(content.DockHandler.TabText, TextFont, DockPanel.Theme.PaintingService.GetBrush(textColor), rectText, StringFormatTabHorizontal);
|
|
|
|
// Set rotate back
|
|
g.Transform = matrixRotate;
|
|
}
|
|
|
|
private Rectangle GetBorderRectangle(Rectangle tab, DockState state, int width)
|
|
{
|
|
var result = new Rectangle(tab.Location, tab.Size);
|
|
if (state == DockState.DockLeftAutoHide)
|
|
{
|
|
result.Height = width;
|
|
result.Width = DockPanel.Theme.Measures.AutoHideTabLineWidth;
|
|
result.Y += TextGapLeft;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockRightAutoHide)
|
|
{
|
|
result.Height = width;
|
|
result.Width = DockPanel.Theme.Measures.AutoHideTabLineWidth;
|
|
result.X += tab.Width - result.Width;
|
|
result.Y += TextGapLeft;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockBottomAutoHide)
|
|
{
|
|
result.Width = width;
|
|
result.Height = DockPanel.Theme.Measures.AutoHideTabLineWidth;
|
|
result.X += TextGapLeft;
|
|
result.Y += tab.Height - result.Height;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockTopAutoHide)
|
|
{
|
|
result.Width = width;
|
|
result.Height = DockPanel.Theme.Measures.AutoHideTabLineWidth;
|
|
result.X += TextGapLeft;
|
|
return result;
|
|
}
|
|
|
|
return Rectangle.Empty;
|
|
}
|
|
|
|
public Rectangle GetLogicalTabStripRectangle(DockState state)
|
|
{
|
|
var rectStrip = GetTabStripRectangle(state);
|
|
var location = rectStrip.Location;
|
|
if (state == DockState.DockLeftAutoHide || state == DockState.DockRightAutoHide)
|
|
{
|
|
return new Rectangle(0, 0, rectStrip.Height, rectStrip.Width);
|
|
}
|
|
|
|
return new Rectangle(0, 0, rectStrip.Width, rectStrip.Height);
|
|
}
|
|
|
|
private Rectangle GetTabRectangle(TabVS2012 tab)
|
|
{
|
|
var state = tab.Content.DockHandler.DockState;
|
|
var rectStrip = GetTabStripRectangle(state);
|
|
var location = rectStrip.Location;
|
|
if (state == DockState.DockLeftAutoHide || state == DockState.DockRightAutoHide)
|
|
{
|
|
location.Y += tab.TabX;
|
|
return new Rectangle(location.X, location.Y, rectStrip.Width, tab.TabWidth);
|
|
}
|
|
|
|
location.X += tab.TabX;
|
|
return new Rectangle(location.X, location.Y, tab.TabWidth, rectStrip.Height);
|
|
}
|
|
|
|
private Rectangle GetTextRectangle(Rectangle tab, DockState state)
|
|
{
|
|
var result = new Rectangle(tab.Location, tab.Size);
|
|
if (state == DockState.DockLeftAutoHide)
|
|
{
|
|
result.X += TextGapBottom;
|
|
result.Y += TextGapLeft;
|
|
result.Height -= TextGapLeft + TextGapRight;
|
|
result.Width -= TextGapBottom;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockRightAutoHide)
|
|
{
|
|
result.Y += TextGapLeft;
|
|
result.Height -= TextGapLeft + TextGapRight;
|
|
result.Width -= TextGapBottom;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockBottomAutoHide)
|
|
{
|
|
result.X += TextGapLeft;
|
|
result.Width -= TextGapLeft + TextGapRight;
|
|
result.Height -= TextGapBottom;
|
|
return result;
|
|
}
|
|
|
|
if (state == DockState.DockTopAutoHide)
|
|
{
|
|
result.X += TextGapLeft;
|
|
result.Y += TextGapBottom;
|
|
result.Width -= TextGapLeft + TextGapRight;
|
|
result.Height -= TextGapBottom;
|
|
return result;
|
|
}
|
|
|
|
return Rectangle.Empty;
|
|
}
|
|
|
|
protected override IDockContent HitTest(Point point)
|
|
{
|
|
Tab tab = TabHitTest(point);
|
|
|
|
if (tab != null)
|
|
return tab.Content;
|
|
else
|
|
return null;
|
|
}
|
|
|
|
protected override Rectangle GetTabBounds(Tab tab)
|
|
{
|
|
GraphicsPath path = GetTabOutline((TabVS2012)tab, true);
|
|
RectangleF bounds = path.GetBounds();
|
|
return new Rectangle((int)bounds.Left, (int)bounds.Top, (int)bounds.Width, (int)bounds.Height);
|
|
}
|
|
|
|
protected Tab TabHitTest(Point ptMouse)
|
|
{
|
|
foreach (DockState state in DockStates)
|
|
{
|
|
Rectangle rectTabStrip = GetTabStripRectangle(state);
|
|
if (!rectTabStrip.Contains(ptMouse))
|
|
continue;
|
|
|
|
foreach (Pane pane in GetPanes(state))
|
|
{
|
|
foreach (TabVS2012 tab in pane.AutoHideTabs)
|
|
{
|
|
GraphicsPath path = GetTabOutline(tab, true);
|
|
if (path.IsVisible(ptMouse))
|
|
return tab;
|
|
}
|
|
}
|
|
}
|
|
|
|
return null;
|
|
}
|
|
|
|
private TabVS2012 lastSelectedTab = null;
|
|
|
|
protected override void OnMouseMove(MouseEventArgs e)
|
|
{
|
|
base.OnMouseMove(e);
|
|
var tab = (TabVS2012)TabHitTest(PointToClient(MousePosition));
|
|
if (tab != null)
|
|
{
|
|
tab.IsMouseOver = true;
|
|
Invalidate();
|
|
}
|
|
|
|
if (lastSelectedTab != tab)
|
|
{
|
|
if (lastSelectedTab != null)
|
|
{
|
|
lastSelectedTab.IsMouseOver = false;
|
|
Invalidate();
|
|
}
|
|
|
|
lastSelectedTab = tab;
|
|
}
|
|
}
|
|
|
|
protected override void OnMouseLeave(EventArgs e)
|
|
{
|
|
base.OnMouseLeave(e);
|
|
|
|
if (lastSelectedTab != null)
|
|
lastSelectedTab.IsMouseOver = false;
|
|
Invalidate();
|
|
}
|
|
|
|
protected internal override int MeasureHeight()
|
|
{
|
|
return 31;
|
|
}
|
|
|
|
protected override void OnRefreshChanges()
|
|
{
|
|
CalculateTabs();
|
|
Invalidate();
|
|
}
|
|
|
|
protected override AutoHideStripBase.Tab CreateTab(IDockContent content)
|
|
{
|
|
return new TabVS2012(content);
|
|
}
|
|
}
|
|
}
|