0

I'm currently developing a software for a Smart Device, using Visual Studio 2008, C#. The device has touch screen as input method. I can't use MouseDown event. I created a custom button, inherited from System.Windows.Forms.Button class.

Trying to override OnMouseDown and OnMouseUp events. But these events are not firing. I searched internet and find a solution with WndProc but it's not able to use with .NET Compact Framework.

Please help me with that. Thanks all. Example code is very simple and you can find it below.

protected override void OnMouseUp(MouseEventArgs e)
{
   Text = "Mouse Up";
   base.OnMouseUp(e);
}

Edit:

As i mentioned at my comment to @josef below, i created my custom control. The control is a butonated panel. First, i tried to add a Label for button text, actually no need to do this. It could be done easily at override method of OnPaint event. This control might have some unnecessary codes, but you can optimize it. If you need it, you can find my solution below:

class ButonatedPanel : Panel
    {
        public int ShadeWidth { get; set; }
        public bool isMouseDown { get; set; }


        protected override void OnMouseDown(MouseEventArgs e)
        {
            Invalidate();
            isMouseDown = true;
            Text = "Mouse Down";
            base.OnMouseDown(e);
        }

        protected override void OnMouseUp(MouseEventArgs e)
        {
            Invalidate();
            isMouseDown = false;
            Text = "Mouse Up";
            base.OnMouseUp(e);
        }
        public override string Text
        {
            get
            {
                return Lb.Text;
            }
            set
            {
                Lb.Text = value;
            }
        }

        protected override void OnPaint(PaintEventArgs e)
        {
            base.OnPaint(e);

            Lb.Size = new Size(Width - ShadeWidth * 2, Height - 2 * ShadeWidth);
            Lb.Location = new Point(ShadeWidth, ShadeWidth);

            SizeF iSizeF = new SizeF(e.Graphics.MeasureString(Text, Lb.Font).Width,
                e.Graphics.MeasureString(Text, Lb.Font).Height);

            e.Graphics.DrawString(Text, Lb.Font, new SolidBrush(Color.FromArgb(0, 0, 0)),
                (Width - 2 * ShadeWidth - iSizeF.Width) / 2, (Height - 2 * ShadeWidth - iSizeF.Height) / 2);
            //gray 128,128,128
            Rectangle Rect1 = new Rectangle(0, 0, ShadeWidth, Height - ShadeWidth);
            Rectangle Rect2 = new Rectangle(0, 0, Width - ShadeWidth, ShadeWidth);
            Rectangle Rect3 = new Rectangle(Width - 2 * ShadeWidth, 0, ShadeWidth, Height - ShadeWidth);
            Rectangle Rect4 = new Rectangle(0, Height - 2 * ShadeWidth, Width - ShadeWidth, ShadeWidth);
            //white 228,228,228
            Rectangle Rect5 = new Rectangle(ShadeWidth, ShadeWidth, ShadeWidth, Height - 4 * ShadeWidth);
            Rectangle Rect6 = new Rectangle(ShadeWidth, ShadeWidth, Width - 4 * ShadeWidth, ShadeWidth);
            //black 0,0,0
            Rectangle Rect7 = new Rectangle(Width - ShadeWidth, 0, ShadeWidth, Height);
            Rectangle Rect8 = new Rectangle(0, Height - ShadeWidth, Width, ShadeWidth);

            if (!isMouseDown)
            {
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect1);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect2);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect1);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect2);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect3);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect4);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect3);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect4);

                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(228, 228, 228)), Rect5);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(228, 228, 228)), Rect6);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(228, 228, 228)), Rect5);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(228, 228, 228)), Rect6);

                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(0, 0, 0)), Rect7);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(0, 0, 0)), Rect8);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(0, 0, 0)), Rect7);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(0, 0, 0)), Rect8);
            }
            else
            {
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(0, 0, 0)), Rect1);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(0, 0, 0)), Rect2);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(0, 0, 0)), Rect1);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(0, 0, 0)), Rect2);

                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(228, 228, 228)), Rect3);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(228, 228, 228)), Rect4);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(228, 228, 228)), Rect3);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(228, 228, 228)), Rect4);

                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect5);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect6);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect5);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect6);

                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect7);
                e.Graphics.DrawRectangle(new Pen(Color.FromArgb(128, 128, 128)), Rect8);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect7);
                e.Graphics.FillRectangle(new SolidBrush(Color.FromArgb(128, 128, 128)), Rect8);
            }

        }
        Label Lb = new Label();
        public ButonatedPanel()
            : base()
        {
            Invalidate();
            ShadeWidth = 1;
            Lb.Size = new Size(Width - ShadeWidth * 2, Height - 2 * ShadeWidth);
            Lb.Location = new Point(ShadeWidth, ShadeWidth);
            Lb.Visible = false;
            Controls.Add(Lb);
        }
Bee-
  • 64
  • 6
  • I assume the Button control does not implement MouseDown and only supports the onClicked event. An example for subclassing is at https://stackoverflow.com/questions/30329338/trigger-button-click-in-net-compact-framework. WndProc is supported in WindowsCE.Forms. Possibly you have to override the Forms OnMouseDown event, test for the click location and if it is the Button area .... – josef May 02 '19 at 17:14
  • @josef This could be good solution. It works when i try it on a blank space at Form. But it is not an option when i try this with the button. Or i don't know, maybe i do something wrong. But it looks like i will create a custom control with a panel and label, a pseudo button. Thank you for your interest. – Bee- May 02 '19 at 19:30
  • You need to use SetWindowLong with WndProc on the button and write your own WndProc to handles OnMouseDown. A starter can be found here: https://blogs.msdn.microsoft.com/netcfteam/2005/05/20/subclassing-controls-in-netcf-2-0-part-1/ – josef May 10 '19 at 05:48

1 Answers1

0

I used to build Wince application (CF 3.5) which required the application to capture custom event, like RFID card reading event. The concept is the same, which is to get the control handle, use SetWindowLong to enable the focused control to get the message via event triggered. Just remember to undo the attribute changing you did to the control. * I mainly used it on Windows Form, but it should work for Panel control.

public delegate void MouseDownEventHandler(object sender, MouseDownEventArgs e);

public class WndProcTest
{
    [DllImport("coredll.dll", SetLastError = true)]
    private static extern IntPtr GetWindowLong(IntPtr hWnd, int nIndex);

    [DllImport("coredll.dll", SetLastError = true)]
    private static extern int SetWindowLong(IntPtr hWnd, int nIndex, WndProcDelegate dwNewLong);

    [DllImport("coredll.dll", SetLastError = true)]
    static extern IntPtr CallWindowProc(IntPtr lpPrevWndFunc, IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);

    [DllImport("coredll.dll", SetLastError = true)]
    private static extern IntPtr FindWindow(string lpClassName, string lpWindowsName);

    private delegate IntPtr WndProcDelegate(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam);

    public event MouseDownEventHandler mouseDownTriggered;

    private WndProcDelegate _newproc;
    private int result;
    private IntPtr _oldproc = IntPtr.Zero;
    internal static IntPtr _hwnd = IntPtr.Zero;

    // Mouse down message value
    const int WM_LBUTTONDOWN = 0x0201;

    // Get window/control handle using name
    public WndProcTest(string windowsName)
    {
        _hwnd = FindWindow(null, windowsName);
    }

    // Initialization to allow a control to receive message
    public void InitWndProcModification()
    {
        _newproc = new WndProcDelegate(MyWndProc);
        _oldproc = GetWindowLong(_hwnd, -4);
        result = SetWindowLong(_hwnd, -4, Marshal.GetFunctionPointerForDelegate(_newproc));
    }

    // Intercept the message
    private IntPtr MyWndProc(IntPtr hWnd, uint msg, IntPtr wParam, IntPtr lParam)
    {
        switch (msg)
        {
            case WM_LBUTTONDOWN:
                MouseDownEventArgs mouseDownEventArgs = new FingerPrintSensorEventArgs();
                OnMouseDownTriggered(mouseDownEventArgs);
                break;

            default:
                break;
        }

        return CallWindowProc(_oldproc, hWnd, msg, wParam, lParam);
    }


    public void RemoveWndProcModification(IntPtr currentHandle)
    {
        result = SetWindowLong(currentHandle, -4, _oldproc);
        _newproc = null;
        _oldproc = IntPtr.Zero;
        _hwnd = IntPtr.Zero;
    }

    // Fire the event
    protected virtual void OnMouseDownTriggered(MouseDownEventArgs e)
    {
        if (mouseDownTriggered != null)
        {
            mouseDownTriggered(this, e);
        }
    }
}

// Event arguments, to pass the X & Y location?
public class MouseDownEventArgs : EventArgs
{

}

// To use the class above 
WndProcTest wp = new WndProcTest("Form1"); 
wp.InitWndProcModification(); 
wp.mouseDownTriggered += ReceivedMsg;

public void ReceivedMsg(Object sender, MouseDownEventArgs e) {   }
YYTan
  • 471
  • 1
  • 5
  • 21