如何让分割面板拆分器对用户可见,而不是只在鼠标悬停时光标变化不可见?
答案 0 :(得分:51)
出现这个问题是因为SplitContainer
控件有没有直接属性来设置可拖动分割条本身的样式。
有几种方法可以实现这一点,即使这里发布的其他答案有效,我在下面与您分享的最终方式也是快速,可靠和最简单的方法。
@BluMonkMN提出了一种使用3D边框的方法,但是如果你不想要任何边框怎么办?
@Giles Bathgate建议添加一个Paint事件处理程序,即使它确实很优雅并且确实有效,但需要稍微降低性能,要求您为在C#级别执行的项目添加更多代码,并且有一天可能成为维修问题。 @Philip Fourie建议更改SplitContainer.BackColor
属性值;然而,最初导致控件的整个背景改变颜色,而不仅仅是分割条,导致没有颜色对比。
所以,我的解决方案是@Philip Fourie的增强功能。
首先,我提到SplitContainer
实际上有两个不同的子容器,两者都由分割条分隔。这两个属性由Panel1
和Panel2
属性表示。除了其他几个属性之外,它们中的每一个本质上都是一个具有自己的BackColor
属性的Panel容器。
SplitContainer
拥有其自己的BackColor
属性,总共有三种独特的可能颜色。
现在,如果您要设置此SplitContainer.BackColor
属性,Panel1
和Panel2
"子控件"会自动继承那个颜色值,现在它们都是一样的,没有引起视觉对比!
只有在Panel1.BackColor
和/或Panel2.BackColor
属性尚未由您明确设置时(即使查看其属性值),才会发生此[可能不合需要的]属性值继承提前的Visual Studio Properties窗口将显示" Control。")
因此,您设置属性的顺序非常重要:
Panel1.BackColor
和Panel2.BackColor
属性为以外的其他内容默认值" Control"强制一个明确的价值(即使你真的想要"控制&#34 ;;我们稍后会修复它。)SplitContainer.BackColor
为您希望分割条的颜色。{/ li>
Panel1.BackColor
和Panel2.BackColor
属性设置为您希望它们的颜色(可能返回" Control&#34 ;.)正如@Philip Fourie回答的那样,您可能希望设置Width属性,实际上始终命名为SplitterWidth
,而不管[Horizontal vs. Vertical] Orientation
属性。
以下是一些有用的提示:
在Visual Studio表单设计器中工作时,如果单击拆分器栏两侧的SplitContainer
,则会选择那个 Panel1
或Panel2
"孩子"子容器。但是如果你点击分割条本身,你就会选择"父母" SplitContainer
。
与@Stuart Helwig建议的相关,默认SplitterWidth
将导致分割条在焦点处被勾勒出轮廓,从而遮挡您选择的颜色。将值提高到5
,6
或更高,这也使最终用户更容易抓住&阻力。
成品。快乐的编码!
答案 1 :(得分:35)
尝试将BorderStyle设置为Fixed3D
答案 2 :(得分:17)
您可以通过将以下事件处理程序添加到splitcontainer paint事件来绘制自己的拆分器栏。
private void SplitterPaint(object sender, PaintEventArgs e)
{
SplitContainer s = sender as SplitContainer;
if (s != null) {
int top = 5;
int bottom = s.Height - 5;
int left = s.SplitterDistance;
int right = left + s.SplitterWidth - 1;
e.Graphics.DrawLine(Pens.Silver, left, top, left, bottom);
e.Graphics.DrawLine(Pens.Silver, right, top, right, bottom);
}
}
答案 3 :(得分:2)
一种方法是更改拆分器的BackColor
和Width/Height
属性(取决于拆分器的方向)
答案 4 :(得分:2)
您可以在设计器中使用SplitterColor来更改分割器边框颜色。
public class SplitContainerCustomSplitter : SplitContainer
{
[DefaultValue(typeof(Color), "Black")]
public Color SplitterColor { get; set; } = Color.Black;
protected override void OnPaint(PaintEventArgs pevent)
{
Graphics g = pevent.Graphics;
Rectangle rect = SplitterRectangle;
using (Pen pen = new Pen(SplitterColor))
{
if (Orientation == Orientation.Vertical)
{
g.DrawLine(pen, rect.Left, rect.Top, rect.Left, rect.Bottom - 1);
g.DrawLine(pen, rect.Right - 1, rect.Top, rect.Right - 1, rect.Bottom - 1);
}
else
{
g.DrawLine(pen, rect.Left, rect.Top, rect.Right - 1, rect.Top);
g.DrawLine(pen, rect.Left, rect.Bottom - 1, rect.Right, rect.Bottom - 1);
}
}
}
}
答案 5 :(得分:1)
除了将其BorderStyle Fixed3D设为@BlueMonkMN建议我经常发现splitContainer对象上的默认SplitterWidth值为4,有点窄。
如果您使用3D边框将其提升至约6,则对用户来说更为明显。
答案 6 :(得分:0)
改进了Giles Bathgate的答案:
private void ds_SplitContainer_Paint(object sender, PaintEventArgs e)
{
SplitContainer l_SplitContainer = sender as SplitContainer;
if (l_SplitContainer != null)
{
Rectangle ll_ShrinkedSplitterRectangle = l_SplitContainer.SplitterRectangle;
ll_ShrinkedSplitterRectangle.Offset(0, 2);
ll_ShrinkedSplitterRectangle.Height = ll_ShrinkedSplitterRectangle.Height - 2;
e.Graphics.FillRectangle(Brushes.Silver, ll_ShrinkedSplitterRectangle);
}
}
答案 7 :(得分:0)
这是一个水平分割器的快速实现,它充满了一种颜色,有一个顶部和底部边框(类似于Visual Studio分割器),中间有一个抓点。
private void splitContainer_Paint(object sender, PaintEventArgs e)
{
SplitContainer s = sender as SplitContainer;
if (s != null)
{
int gripLineWidth = 9;
// Fill Splitter rectangle
e.Graphics.FillRectangle(SystemBrushes.ControlDark,
s.SplitterRectangle.X, s.SplitterDistance, s.SplitterRectangle.Width, s.SplitterWidth);
// Draw Single Line Border on Top and Bottom
e.Graphics.DrawLine(Pens.LightSlateGray,
s.SplitterRectangle.X, s.SplitterDistance, s.SplitterRectangle.Width, s.SplitterDistance);
e.Graphics.DrawLine(Pens.LightSlateGray,
s.SplitterRectangle.X, s.SplitterDistance + s.SplitterWidth - 1, s.SplitterRectangle.Width, s.SplitterDistance + s.SplitterWidth - 1);
// Draw gripper dots in center
e.Graphics.DrawLine(_dashedPen,
((s.SplitterRectangle.Width / 2) - (gripLineWidth / 2)),
s.SplitterDistance + s.SplitterWidth / 2,
((s.SplitterRectangle.Width / 2) + (gripLineWidth / 2)),
s.SplitterDistance + s.SplitterWidth / 2);
}
}
您可以在执行绘图的类中创建一个Pen作为成员变量,该绘图将在您的类似内容中绘制虚线:
private static Pen _dashedPen = new Pen(Color.DarkRed, 1);
_dashedPen.DashStyle = System.Drawing.Drawing2D.DashStyle.Dot;
答案 8 :(得分:0)
将BackColor
的{{1}}属性设置为其他颜色。让我们说黑色。然后每个SplitContainer
,将其SpliterPanel
属性更改为不同的颜色。让我们说白。然后您会注意到SplitLine将变得更加明显。 :)
答案 9 :(得分:0)
在尝试了一些这里建议的方法而不是逗我之后,我决定在panel1和panel2中放入一个薄标签,与分离器对齐,一切正常。
(label's.Autosize=false, label's.Text = "", label's.Color=SystemColor.Selected, label1.Dock=left; label2.Dock=right)
答案 10 :(得分:0)
这是对GlobalSoftwareSociety's great answer的改进。
为防止面板继承BackColor
,只需要写入属性一次。事实上,您可以简单地将属性分配给自己。这也适用于其他类型的控件和类似继承的属性,如字体。
另外,为了避免烦人的选择矩形,请使SplitContainer
不是一个tabstop,并在鼠标上启动第一个面板。
(需要小心;首先我尝试在Enter
事件中调用“tab to next control”调用,但这阻止了所有子控件的激活。)
总之,这使修复看起来像:
splitBox.Panel1.BackColor = splitBox.Panel1.BackColor;
splitBox.Panel2.BackColor = splitBox.Panel2.BackColor;
splitBox.BackColor = yourFavouriteColor;
splitBox.SplitterWidth = yourFavouriteSize;
splitBox.TabStop = false;
splitBox.MouseUp += (s, e) => splitBox.ActiveControl = splitBox.Panel1;
答案 11 :(得分:-1)
实际上可以看到分割线。真正的问题是很难与其他控件区别开来。
一个想法是为拆分容器设置一个新的背景颜色,并使其与子面板不同。
有时我们可以从设计师的角度解决问题,而不是开发人员。 : - )