Tuesday, 2 August 2016

Powershell_WPF - Part IV - How to manage event


Guess we are back to our powershell folks. 

Where we left off: Up until now, we know how to create a GUI, apply a theme and create some customization before loading our form. Now, let’s check up about the beast running behind: "managing the event".




However, before going deeper, we need to know how to link our xaml tag with a powershell variable. This way we can play with event ;)

How it’s done?
You certainly have noticed theses lines in my previous post:
In the powershell script:
$CloseWindow    = $Form.Findname("CloseWindow")
$CloseWindow.Add_Click({
    $Form.close()
})
And in the xaml file:
<Button x:Name="CloseWindow" …
</Button>

As you have already guessed it, the powershell script is looking for the tag’s Name (“closeWindow”) inside $Form. Then, when there’s a click event, the main form is closed. That ‘all the code does.
So if you want to use an event on an object, you need to specify a name for it with x:Name in your xaml and then call it in your powershell script.

Now let’s move on to the next stage:
What’s an event? Well an event is you know …when something happened when you click a button when you check a checkbox … I guess you know what I mean. :D
There is different element that natively possesses event method or is used on that purpose:
  • For instance: the purpose of a button is to be clicked, like ok and cancel , close exit and so on , … The goal is then to perform something when it’s clicked, you will not use a button tag to display a text. So natively, it has a method called when its clicked. Other elements that natively possess event method are: combobox, checkbox, … 
  • The goal of an Image tag is to display an image nothing more and nothing less. So, natively it doesn’t have a method called when you click on it. It’s the same for Grid and Stackpanel , …

These are the two different elements, one that possess event method, and another one that doesn’t.
You’re going to tell me: but what if a want to perform an action when I click on my image but do not necessarily want to use a big button and put an image as a background (this works too, but it’s ugly). 
Of course, you’re right, they did something about it: and hopefully you can attach an event to those object to behave like a button (answer to the question: D ).

Now lets’s begin,
- When you click on a button: there’s a prompt action executed and that’s it. It doesn’t have a state pushed or not pushed (I'm not talking about toggle button). 
- It’s another story for radiobutton and checkbox. We always want to track their state if you want to execute something on state change. You need to attach an event handler to them.

We're going to see one by one the commonly used event:
   A-           Event for a Button
   B-           Event for a ComboBox and TextBox
   C-          Event for a Radiobutton
   D-           Attaching an event

So, as listed above we need an interface which contains a button, a ckeckbox, a listbox, a textbox and an image. Progress bar is a different matter; we will not see this case here.


   A-           Event for a Button

Always begin with easy tasks
It’s really simple, you just need to add the add_Click({ }) to your PS variable and then you can do everything you want when "MyButton" is clicked.

$MyButton.Add_Click({
    $Form.close()
    Write-Host "You clicked MyButton"
})
Nothing really tough here. 

   B-           Event for a ComboBox and TextBox

When things become a little complicated

ComboBox:
Now let’s just make things a bit complicated. For combobox, you know that there’s a method for “on change” event or something like that. In powershell, It’s add_selecectionChanged({  }).
You call your control in powershell, $myCombobox for example and then you call the method above on this object so it looks like this:
$MyComboBox.add_SelectionChanged({
    $SelectedItem = $MyComboBox.SelectedItem.Name
})
This script returns the Name attributes of the combobox item you selected, and that’s it. 

Textbox:
Imagine that you want something to be executed everytime you type something in your textbox. It can be achieved by doing like this:
$MyTextBox.add_TextChanged({
    Write-Host $MyTextBox.Text
})
The same principle as above is applicable as you can see, your control call the method on it. Everytime the “text has changed” in your textbox then the control trigger the event.

   C-          Event for a Radiobutton

It’s a bit different in these case. We need to add an event handler.
How does it work?
First we need to put all elements inside a container a Stackpanel for example or a grid, and assign a handle on it just like bellow:
$RadioButtonArea.AddHandler()

What goes inside as input parameters is the event type followed by a new PSobject we wish to handle:
[System.Windows.RoutedEventHandler]$ChoosedRadioHandler = {
    Write-Host $_.source.GroupName
    Write-Host $_.source.Content
}
$RadioButtonArea.AddHandler([System.Windows.Controls.RadioButton]::CheckedEvent, $ChoosedRadioHandler)

$_.source:    represents the current element on which the event happened.
[System.Windows.Controls.RadioButton]::CheckedEvent is the event type
$ChoosedRadioHandler  is the PSobject on which the event will be routed


What is the advantage?
When you need to manage many elements or a precise group of controls inside a container, it’s really useful. In our example, it will target radiobutton only.

If you wish to go further and change the type of controls it’s easy too. Replace
[System.Windows.Controls.RadioButton]::CheckedEvent
With:
-              If you want to listen for each button inside a container:
[System.Windows.Controls.Button]::ClickEvent
-              If you want to listen for CheckBox inside a container:
[System.Windows.Controls.CheckBox]::CheckedEvent



But if you don’t really care about how it works but still wants to use it (that works too), just copy and paste the code above



   D-           Attaching an event

When you need to give a thought to your application
This time we are going to see how to attach an event to an element. The goal is to simulate a click event on an image for example.


How it’s done?
You know that when you click on a button you use your mouse, so to reproduce a click event we are going to use a method based on the mouse behaviour. (I haven’t tested it on a touch screen).
We need something like if “mouse Button Clicked”, if “mouse button hover” …
We are going to apply those principles on a picture in our form.
Just like this:

If the mouse enters the picture area
$MyImage.Add_MouseEnter({})
If the mouse leaves the picture area
$MyImage.Add_MouseLeave({})
If the mouse is clicked (left click)
$MyImage.Add_MouseLeftButtonDown({})

And plenty others …
The formula is $YouControl.Add_MouseSomething({ })



Well that is all there is to it.

Thanks for reading and hope it was easy to understand. See you next time!
All files are available here.



Share:

2 comments:

Popular Posts

Join us on Facebook

STATS

Contact Form

Name

Email *

Message *