[英]How do I tell which tab you are moving from/to in a WinForms tab control?
[英]How do I change background colour of tab control in Winforms?
有沒有辦法在winforms中更改選項卡控件的背景顏色,使其周圍沒有白色邊框?
我嘗試了幾種不同的方法,但它們都導致顯示相同的白色邊框。
TabControl
對自定義的支持很差。 我已經成功地使用了這個自定義選項卡控件。 如果您想像我一樣更改外觀,該代碼非常有用。
首先,您需要從 TabControl 創建一個派生類。 到目前為止一切順利,但現在它變臟了。
因為 TabControl 不會調用OnPaint
,所以我們必須重寫WndProc
來處理 WM_PAINT 消息。 在那里,我們繼續用我們喜歡的顏色繪制背景。
protected override void WndProc(ref Message m)
{
base.WndProc(ref m);
if(m.Msg == (int) WindowsMessages.Win32Messages.WM_PAINT)
{
using (Graphics g = this.CreateGraphics())
{
//Double buffering stuff...
BufferedGraphicsContext currentContext;
BufferedGraphics myBuffer;
currentContext = BufferedGraphicsManager.Current;
myBuffer = currentContext.Allocate(g,
this.ClientRectangle);
Rectangle r = ClientRectangle;
//Painting background
if(Enabled)
myBuffer.Graphics.FillRectangle(new SolidBrush(_backColor), r);
else
myBuffer.Graphics.FillRectangle(Brushes.LightGray, r);
//Painting border
r.Height = this.DisplayRectangle.Height +1; //Using display rectangle hight because it excludes the tab headers already
r.Y = this.DisplayRectangle.Y - 1; //Same for Y coordinate
r.Width -= 5;
r.X += 1;
if(Enabled)
myBuffer.Graphics.DrawRectangle(new Pen(Color.FromArgb(255, 133, 158, 191), 1), r);
else
myBuffer.Graphics.DrawRectangle(Pens.DarkGray, r);
myBuffer.Render();
myBuffer.Dispose();
//Actual painting of items after Background was painted
foreach (int index in ItemArgs.Keys)
{
CustomDrawItem(ItemArgs[index]);
}
}
}
}
我在這個方法中做進一步的繪制,所以對於這個問題看起來有點矯枉過正,但只是忽略了不必要的東西。 還要注意foreach
循環。 我稍后會談到這個。
問題是TabControl
在其自己的 WM_PAINT之前繪制其項目(選項卡標題),因此我們的背景將被繪制在頂部,這使得它們不可見。 為了解決這個問題,我為DrawItem
創建了一個EventHandler
,如下所示:
private void DrawItemHandler(object sender, DrawItemEventArgs e)
{
//Save information about item in dictionary but dont do actual drawing
if (!ItemArgs.ContainsKey(e.Index))
ItemArgs.Add(e.Index, e);
else
ItemArgs[e.Index] = e;
}
我將DrawItemEventArgs
保存到字典中(在我的情況下稱為“ItemArgs”),以便以后可以訪問它們。 這就是幾秒鍾前的foreach
發揮作用的地方。 它調用一個方法,我在其中繪制選項卡標題,該方法將我們之前保存的DrawItemEventArgs
作為參數以正確的狀態和位置繪制項目。
因此,簡而言之,我們正在攔截選項卡標題的繪制以延遲它,直到我們完成繪制背景。
這個解決方案不是最佳的,但它可以工作,並且它是唯一可以做的事情來獲得對TabControl
的更多控制(lol),而無需從頭開始繪制它。
我只能想到將 Appearance 屬性更改為 Buttons
更簡單(IMO):將繪制處理程序添加到 TabPage(不是頂級 TabControl,而是其中的 TabPage,然后以您想要的顏色繪制背景矩形。
在設計器中或“手動”中,將 Paint 事件處理程序添加到 TabPage:
Page1.Paint += tabpage_Paint; // custom paint event so we get the backcolor we want
在paint方法中,將頁面矩形繪制成你想要的顏色(在我的例子中,我希望它遵循標准的BackColor):
// force the tab background to the current BackColor private void tabpage_Paint(object sender, PaintEventArgs e) { SolidBrush fillBrush = new SolidBrush(BackColor); e.Graphics.FillRectangle(fillBrush, e.ClipRectangle); }
將面板放在選項卡控件的頂部(而不是內部)並在屬性中設置顏色。 根據需要調用 Panelx.Hide() 和 Panelx.Show()。
不幸的是,在繪制控件時會處理背景顏色屬性。 我的建議是做我所做的並創建一個用戶控件來模仿標簽控制器。
我使用菜單條作為選項卡,並將第二個用戶控件停靠為父用戶控件的填充。 在第二個用戶控件中,我能夠為所述選項卡添加我需要的任何內容。
更難的部分是您必須構建所有功能以使其用作選項卡控件。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.