capture doubleclick for MonthCalendar control in windows forms app

妖精的绣舞 提交于 2019-12-05 11:28:38

Do note that MonthCalendar neither shows the DoubleClick nor the MouseDoubleClick event in the Property window. Sure sign of trouble, the native Windows control prevents those events from getting generated. You can synthesize your own by watching the MouseDown events and measuring the time between clicks.

Add a new class to your project and paste the code shown below. Compile. Drop the new control from the top of the toolbox. Write an event handler for the DoubleClickEx event.

using System;
using System.Windows.Forms;

class MyCalendar : MonthCalendar {
    public event EventHandler DoubleClickEx;

    public MyCalender() {
        lastClickTick = Environment.TickCount - SystemInformation.DoubleClickTime;
    }

    protected override void OnMouseDown(MouseEventArgs e) {
        int tick = Environment.TickCount;
        if (tick - lastClickTick <= SystemInformation.DoubleClickTime) {
            EventHandler handler = DoubleClickEx;
            if (handler != null) handler(this, EventArgs.Empty);
        }
        else {
            base.OnMouseDown(e);
            lastClickTick = tick;
        }
    }

    private int lastClickTick;
}

You'll need to keep track of the click events yourself. You need to use the DateSelected event to mark when a date is clicked, and the DateChanged event to 'reset' the time span so you don't count clicking different dates as a double click.

Note: if you use a mouse down event you will get buggy behavior

The mouse down event occurs no matter what is clicked, for example clicking on the month / year etc header of the Calendar will be registered just the same as clicking a real date. Hence the use of DateSelected instead of the mouse down event.

private DateTime last_mouse_down = DateTime.Now;

private void monthCalendar_main_DateSelected(object sender, DateRangeEventArgs e)
{
    if ((DateTime.Now - last_mouse_down).TotalMilliseconds <= SystemInformation.DoubleClickTime)
    {
        // respond to double click
    }
    last_mouse_down = DateTime.Now;
}

private void monthCalendar_main_DateChanged(object sender, DateRangeEventArgs e)
{
    last_mouse_down = DateTime.Now.Subtract(new TimeSpan(1, 0, 0));
}

Best to add following code, otherwise if you click quickly on two dates you will have the event.

    protected override void OnDateChanged(DateRangeEventArgs drevent) {
        lastClickTick = Environment.TickCount - 2 * SystemInformation.DoubleClickTime;
        base.OnDateChanged(drevent);
    }
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!