筆者重載了控件的WndProc方法來處理控件接受的 Windows底層消息,其代碼如下
/// <summary>
/// 處理底層 Windows消息處理方法
/// </summary>
/// <param name="m">Windows消息對象</param>
protected override void WndProc(ref Message m)
{
if (bolFixedBackground)
{
if (m.HWnd == this.Handle)
{
// 當前消息是橫向滾動條或縱向滾動條事件
if (m.Msg == 0x0114 // WM_HSCROLL
|| m.Msg == 0x0115)// WM_VSCROLL )
{
int v = m.WParam.ToInt32();
if ((v & 0xf) == 5)
{
// 滾動消息是 THUMBTRACK 類型
base.WndProc(ref m);
if (bolDragFullWindows == false)
{
// Windows操作系統沒有設置為拖動時顯示窗口內容
// 則重復執行 THUMBPOSITION 類型 的滾動消息
v = v - 1;
m.WParam = new IntPtr(v);
base.WndProc(ref m);
}
}
else
{
base.WndProc(ref m);
}
return;
}
}
}
base.WndProc(ref m);
}
在這段代碼中,若消息類型是ThumbTrack類 型的滾動消息,則執行控件的默認處理方法,然後將消息類型修改為ThumbPosition類型的滾 動消息,然後再次執行控件默認的消息處理方法,這樣就使得控件每接受到一個ThumbTrack 類型的滾動消息就處理了ThumbTrack和ThumbPosition兩個消息。這就統一了有和沒有 “拖動時顯示窗口內容”兩種情況。
由於用戶進行鼠標滾輪操作時不會觸 發滾動事件,因此還需要處理控件的鼠標滾輪事件來,其代碼如下
/// <summary>
/// 處理鼠標滾輪事件
/// </summary>
/// <param name="e"></param>
protected override void OnMouseWheel(MouseEventArgs e)
{
if (bolFixedBackground)
{
LockWindowUpdate(this.Handle);
base.OnMouseWheel(e);
LockWindowUpdate(IntPtr.Zero);
this.Invalidate();
}
else
{
base.OnMouseWheel(e);
}
}
筆者還進行了一些其他非關鍵的代碼的編寫,這樣,一個具有固定背景圖片 的可滾動的控件開發完畢。