C# MonoMac - Mouse events in NSWindow

TimLTimL SZMember
edited May 2015 in Xamarin.iOS

Hey everybody,
I created simple monomac project in Xamarin Studio. There is only one window, created programmatically, without any controllers. Just single file, like this:

public class MyWindow : NSWindow
{
    public MyWindow()
        :base(new RectangleF (0, 0, 100, 100), 
            NSWindowStyle.Closable | NSWindowStyle.Resizable | NSWindowStyle.Titled, NSBackingStore.Buffered, 
            false)
    {
        this.StyleMask = NSWindowStyle.Borderless;
        this.MakeKeyAndOrderFront( null );
    }
}

No, I'm really struggling with registering mouse events for this window. In WinForms It would be like 2 lines, but for OSX it seems a bit more complicated. I don't have much experience programming for mac platform. I did a little research and found out that I need to create NSView, in NSView object I need to register those events, set AcceptsFirstResponder true and add somehow this NSView to my NSWindow object. I've tried different ways but couldn't get this going. Can somebody help me out with this? I have my NSView wrapper like this:

public class MouseTracking : NSView
{
    public NSTrackingArea tracking;

    public override bool AcceptsFirstResponder ()
    {
        return true;
    }

    public override void DrawRect(RectangleF dirtyRect)
    {
        base.DrawRect(dirtyRect);
        var context = NSGraphicsContext.CurrentContext.GraphicsPort;
        var rectangle = new RectangleF (0,0, this.Frame.Width, this.Frame.Height);
        NSColor.Blue.Set ();
        context.FillRect (rectangle);
    }

    public override void UpdateTrackingAreas()
    {
        if (tracking != null)
        {
            this.RemoveTrackingArea(tracking);
            tracking.Release();
        }
        tracking = new NSTrackingArea(this.Frame,NSTrackingAreaOptions.MouseEnteredAndExited | NSTrackingAreaOptions.ActiveAlways ,this, null);
        this.AddTrackingArea(tracking);
    }

    public override void MouseMoved(NSEvent theEvent)
    {
        Console.WriteLine("MouseMoved");
    }

    public override void MouseExited(NSEvent theEvent)
    {
        Console.WriteLine("MouseExitedTest");
    }
}

I've tried to add NSView object into my NSWindow like this:

MouseTracking tracking = new MouseTracking ();
this.ContentView.AddSubview (tracking);

I'd would be really glad if you correct me if my thinking is wrong. If not, what is the way to add simple Mousemove event to simplest NSWindow object?
Can you tell me if my NSView class if it's missing sth? and how can I add it to my window?

Really thanks for help!

Best Answer

Answers

  • ChrisHamonsChrisHamons Xamurai USForum Administrator, Xamarin Team Xamurai

    Also, you shouldn't call Release. We handle Retain/Release for you, and it will cause nothing but pain. We actually renamed it to DangerousRelease in Unified for that reason.

  • TimLTimL SZMember
    edited May 2015

    Thanks for your answer, I have coupe of questions tho
    I added those two constructors and used second one to create NSView, like this:

                MouseTracking tracking = new MouseTracking (new RectangleF (0, 0, 100, 100));
                this.ContentView.AddSubview (tracking);
    

    Can I override these events inside NSWindow class? So I could interact with objects within MyWindow in these events?
    And second, I saw that MouseMoved is not captured, rest of them looks ok. Perhaps I'm missing some flag, right ?

  • ChrisHamonsChrisHamons Xamurai USForum Administrator, Xamarin Team Xamurai

    You most likely need NSTrackingAreaOptions.MouseMoved if you want movement. NSTrackingArea only events what you ask it for.

    I do not know of a way to override those events in the Window, outside of doing some crazy messing with the message pump, maybe. Doing it in a ContentView is the suggested approach.

  • TimLTimL SZMember

    I see, well I wanted to interact with that window. To be specific, I'd like to move MyWindow in mouse event. What would be the best way to do that?

    Like this?

                public override void MouseDown (NSEvent theEvent)
                {
                    Console.WriteLine("MouseDown");
                    MyWindow wnd = (MyWindow)this.Window;
                    wnd .SetLocation (100, 100);
                    base.MouseDown (theEvent);
                }
    
  • TimLTimL SZMember

    alright, thank you for help!

Sign In or Register to comment.