右クリックされた時はまずMouseDownRightButtonイベントを呼ぶ。
次に、CheckFocusedItemの状態に応じ、falseならContextMenuStripを表示、falseならマウスカーソルが選択中のアイテムの上にあるときだけContextMenuStripを表示する。
また右クリックはMouseDownRightButtonの呼び出しと、ConextMenuStripを表示することのみに使われ、それ以外の処理は行われない。つまり、右クリックで選択が解除されたりということは行われない。
かなり端折った実装なので、まぁ、こういうこともできますよー程度に。
ContextMenuStripのOpenedハンドラのsenderにはContextMenuStripが渡されるが、その中のSourceControlに右クリックされたListViewが渡される。ListViewのFocusedItemに選択中のListViewItemが入っている。
ListViewItemに応じて使用するContextMenuStripを変更したい場合は、MouseDownRightButtonハンドラの中で各自実装したりという感じになると思う。
もうちょっと色々作り込みたいところだけど、やる気が続かない。
public class ListViewRightButton : ListView
{
public bool CheckFocusedItem { get; set; }
protected override void WndProc(ref Message m)
{
const int WM_RBUTTONUP = 0x0205;
const int WM_RBUTTONDOWN = 0x0204;
if (m.Msg == WM_RBUTTONUP || m.Msg == WM_RBUTTONDOWN)
{
Point Client = PointToClient(Cursor.Position);
MouseDownRightButton?.Invoke(this, new MouseEventArgs(MouseButtons.Right, 0, Client.X, Client.Y, 0));
if (!CheckFocusedItem)
{
ContextMenuStrip?.Show(this, Client.X, Client.Y);
}
else if (FocusedItem != null && FocusedItem.Bounds.Contains(Client))
{
ContextMenuStrip?.Show(this, Client.X, Client.Y);
}
}
else
{
base.WndProc(ref m);
}
}
public event MouseEventHandler MouseDownRightButton;
}
0 件のコメント:
コメントを投稿