MouseMove Event not static and readonly - c#

I'm trying to add a delegate for a "mousemove" event to a method in a class. I'm using the EventHandler that I would use for the Xaml "MouseMove" but it's not available and only "MouseMoveEvent" is(I don't know if that effect things).
I've looked at the 2 different types in meta Data but it doesn't tell me much. I've also tried making the method that it's linked to read only and static but it's not valid.
I'm making the delegate like this:
MainWindow.MouseMoveEvent += delegate (object sender, MouseEventArgs e) { Project.Mouse_Move(this); };
Where MainWindow is the window of my UI. This is the function it's calling
public partial class Program
{
public void Mouse_Move(MainWindow MainWind)
{
}
}
I'm trying to get the same result as if you would do it through xaml:
Title="MainWindow" MouseMove="Window_MouseMove">
and method like this:
private void Window_MouseMove(object sender, MouseEventArgs e)
{
}

MainWindow is a type. You need a reference to an actual instance of a window to be able to hook up an event handler to its MouseMove event. Try Application.Current.MainWindow:
Application.Current.MainWindow.MouseMove += delegate (object sender, MouseEventArgs e) { Project.Mouse_Move(this); };
Or Application.Current.Windows:
var window = Application.Current.Windows.OfType<MainWindow>().FirstOrDefault();
if(window != null)
window.MouseMove += delegate (object sender, MouseEventArgs e) { Project.Mouse_Move(this); };

Related

How to call an event handler from another method

Given the following event handler code:
private void image1_MouseDown(object sender, MouseButtonEventArgs e)
{
///////////
}
How can I call it from another method:
private void timerTick(object sender, EventArgs e)
{
image1_MouseDown(object, e); // error
}
Event handlers are regular methods like any others.
The reason you can't call it like you're trying to do, is because the MouseDown event takes a MouseButtonEventArgs instance, while the Tick event of timers take the base class EventArgs.
You'll need to create a new instance of MouseButtonEventArgs, but then you'll need to initialize it with a device, and other event data.
A better option would be to refactor the body of the MouseDown event handler to a method taking individual parameters, which you can then call without having to create a MouseButtonEventArgs instance.
private void image1_MouseDown(object sender, MouseButtonEventArgs e)
{
this.ProcessImageMouseDown(e.ChangedButton, e.ButtonState, e.GetPosition(sender as FrameworkElement));
}
private void timerTick(object sender, EventArgs e)
{
this.ProcessImageMouseDown(MouseButton.Left, MouseButtonState.Pressed, new Point(10d, 20d));
}
private void ProcessImageMouseDown(MouseButton button, MouseButtonState state, System.Windows.Point position)
{
// Do actual processing here.
}

Avoid SizeChanged event on startup

I have a MainWindow Class which as a few Events - all of them should call a method in another class.
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
getdata.MainWindow = this;
}
private void button_Click(object sender, RoutedEventArgs e)
{
getdata go = new getdata();
go.clear();
}
private void comboBox1_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
getdata go = new getdata();
go.clear();
}
private void comboBox2_DropDownClosed(object sender, EventArgs e)
{
getdata go = new getdata();
go.clear();
}
private void MainWindow_SizeChanged(object sender, SizeChangedEventArgs e) {
getdata go = new getdata();
go.clear(); //<-this causes exception on Startup
}
}
The Problem is that the MainWindow_SizeChanged Event is also triggered on Startup of the program but the clear method uses also some objects that are not yet created at Startup, which causes an error. How can I avoid this and only have this Event triggered when the size is actually changed while running the program?
You have the IsLoaded property of Window.
You can check it before executing code.
You can check if an item is null when re-sizing so you can avoid this being an issue, this can be done using the null coalescence and null conditional operators. If for example you are using the value of a textBox on startup but it has not been instantiated you can use this
string someText = tB1?.Text?
if(someText == null) return;
SizeChanged Event gets triggered before the window is loaded. You can try subscribing to the SizeChanged event as part of Loaded event and unsubscribe it in the Unloaded as shown below.
//XAML
<Window x:Class="MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525"
Loaded="Window_Loaded"
Unloaded="MainWindow_OnUnloaded">
//Code Behind
private void Window_SizeChanged(object sender, SizeChangedEventArgs e)
{
Debug.WriteLine("Size Changed Triggered");
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
SizeChanged += Window_SizeChanged;
}
private void MainWindow_OnUnloaded(object sender, RoutedEventArgs e)
{
SizeChanged -= Window_SizeChanged;
}

Binding Form Closing event in class

Hello I'm trying to make a class that can handle the form closing event for my winForm
I have figured out how to work the event handlers, like this for a ContextMenuStrip items click event:
mnuItemShow.Click += new EventHandler(mnuItemShow_Click);
private void mnuItemShow_Click(object sender, EventArgs e)
{
}
But I can't figure out how to bind the Form Closing event..
I have tried it like this:
this.form.FormClosing += new EventHandler(closing);
private override void closing(EventArgs e)
{
}
But I get this error message:
No overload for 'closing' matches delegate 'System.EventHandler'
This works:
this.FormClosing += new System.Windows.Forms.FormClosingEventHandler(this.Main_FormClosing);
private void Main_FormClosing(object sender, FormClosingEventArgs e)
{
}
it should be like this:
private void closing(object sender, FormClosingEventArgs e)
{
}
and you have to add handler like below
frm.FormClosing += new FormClosingEventHandler();

C# .net framework2.0 how to dynamically assign methods to an event

VS2008, C#, .NET FRAMEWORK2.0
I want this: click button1, webbrowser1._DocumentCompleted() event revokes doA(); click button2, it revokes doB(); click button3, it revokes doC().
I know how to do it using JAVA and I guess C# has this mechanism too. Could anyone give me some idea or better, show me some example?
myButton.Click += myButton_Click;
protected void myButton_Click(object sender, EventArgs e) {}
To Add a handler
button.Click += buttonClickEventHandler;
To remove a handler
button.Click -= buttonClickEventHandler;
To add to these answers, you can also add an anonymous method to an event:
myButton.Click += (object sender, EventArgs e) => {
MessageBox.Show("MASSIVE ERROR!");
};
What this means is that you can effectively call a method even if it does not match the appropriate event handler signature:
myButton.Click += (object sender, EventArgs e) => {
DoA();
};
Or (without using a lamba expression):
myButton.Click += delegate(object sender, EventArgs e) {
DoA();
};
If you want to add event handlers to a control, which is what I think you are describing, you can easily do this. One common approach is to assign control event handlers in the code behind during page load:
protected void Page_Load(object sender, EventArgs e)
{
//add the event handler for the click event. You could provide other
//logic to determine dynamically if the handler should be added, etc.
btnButton1.Click += new EventHandler(btnButton1_Click);
btnButton2.Click += new EventHandler(btnButton2_Click);
btnButton3.Click += new EventHandler(btnButton3_Click);
}
protected void btnButton1_Click(object sender, EventArgs e)
{
//get the button, if you need to...
Button btnButton1 = (Button)sender;
//do some stuff...
DoA();
}
protected void btnButton2_Click(object sender, EventArgs e)
{
//do some stuff...
DoB();
}
protected void btnButton3_Click(object sender, EventArgs e)
{
//do some stuff...
DoC();
}
private void DoA() {}
private void DoB() {}
private void DoC() {}
Declaring an event
public class MyClass1
{
...
public event EventHandler<EventArgs> NotifyValidate;
protected void RaiseNotifyValidate(EventArgs e)
{
if (NotifyValidate != null)
{
NotifyValidate(this, e);
}
}
...
}
Firing that event in your code
...
RaiseNotifyValidate(new EventArgs()); //EventArgs could be more sophisticated, containing data etc..
Registering for that event in your code:
...
MyClass aObj = new MyClass();
aObj.NotifyValidate += new EventHandler(onNotifyValidate);
...
private void onNotifyValidate(object sender, EventArgs e)
{
//do what you need to
}
As Dan pointed out, with Lambda expressions you can define events like
aObj.NotifyValidate += (s,ev) =>
{
//handle your event
};

How to subscribe to other class' events in C#?

A simple scenario: a custom class that raises an event. I wish to consume this event inside a form and react to it.
How do I do that?
Note that the form and custom class are separate classes.
public class EventThrower
{
public delegate void EventHandler(object sender, EventArgs args) ;
public event EventHandler ThrowEvent = delegate{};
public void SomethingHappened() => ThrowEvent(this, new EventArgs());
}
public class EventSubscriber
{
private EventThrower _Thrower;
public EventSubscriber()
{
_Thrower = new EventThrower();
// using lambda expression..could use method like other answers on here
_Thrower.ThrowEvent += (sender, args) => { DoSomething(); };
}
private void DoSomething()
{
// Handle event.....
}
}
Inside your form:
private void SubscribeToEvent(OtherClass theInstance) => theInstance.SomeEvent += this.MyEventHandler;
private void MyEventHandler(object sender, EventArgs args)
{
// Do something on the event
}
You just subscribe to the event on the other class the same way you would to an event in your form. The three important things to remember:
You need to make sure your method (event handler) has the appropriate declaration to match up with the delegate type of the event on the other class.
The event on the other class needs to be visible to you (ie: public or internal).
Subscribe on a valid instance of the class, not the class itself.
Assuming your event is handled by EventHandler, this code works:
protected void Page_Load(object sender, EventArgs e)
{
var myObj = new MyClass();
myObj.MyEvent += new EventHandler(this.HandleCustomEvent);
}
private void HandleCustomEvent(object sender, EventArgs e)
{
// handle the event
}
If your "custom event" requires some other signature to handle, you'll need to use that one instead.

Categories

Resources