Alessandro Del Sole's Blog

{ A programming space about Microsoft® .NET® }
posts - 1909, comments - 2047, trackbacks - 352

My Links

News

Your host

This is me! Questo spazio è dedicato a Microsoft® .NET®, di cui sono molto appassionato :-)

Cookie e Privacy

Microsoft MVP

My MVP Profile

Microsoft Certified Professional

Microsoft Specialist

Xamarin Certified Mobile Developer

Il mio libro su VB 2015!

Pre-ordina il mio libro su VB 2015 Pre-ordina il mio libro "Visual Basic 2015 Unleashed". Clicca sulla copertina per informazioni!

Il mio libro su WPF 4.5.1!

Clicca sulla copertina per informazioni! E' uscito il mio libro "Programmare con WPF 4.5.1". Clicca sulla copertina per informazioni!

These postings are provided 'AS IS' for entertainment purposes only with absolutely no warranty expressed or implied and confer no rights.
If you're not an Italian user, please visit my English blog

Le vostre visite

I'm a VB!

Guarda la mia intervista a Seattle

Follow me on Twitter!

Altri spazi

GitHub
I miei progetti open-source su GitHub

Article Categories

Archives

Post Categories

Image Galleries

Privacy Policy

WPF e la clausola Handles di Visual Basic nei gestori di evento

Un problema che può capitare nello sviluppo di applicazioni WPF con Visual Basic 2008 è costituito dall'errato utilizzo della clausola Handles nella gestione degli eventi. In sostanza, se assegno un gestore di evento a un controllo tramite XAML e successivamente specifico una clausola Handles che punta al controllo in questione nel relativo gestore di evento, otterrò, come risultato, che l'evento viene gestito due volte con conseguenze a volte poco piacevoli.

Consideriamo il seguente XAML, relativo alla definizione di un pulsante:

        <Button Width="100" Height="30" Name="Button1" Click="Button1_Click" />

Come potete vedere, ho specificato un gestore di evento. Supponiamo di volerlo implementare da codice Visual Basic in questo modo:

    'Non è corretto se imposto un event handler anche da XAML

    Private Sub Button1_Click(ByVal sender As System.Object, _

                              ByVal e As System.Windows.RoutedEventArgs) _

                              Handles Button1.Click

 

        MessageBox.Show("You clicked!")

    End Sub

Il commento parla chiaro: questa tecnica è errata poichè l'evento viene gestito due volte. Ma perchè? Dopo aver compilato il progetto, attivate la visualizzazione di tutti i file in Solution Explorer e fate doppio clic sul file Window1.g.vb (o il file .g.vb relativo alla vostra finestra), che troverete nella sottocartella Obj\Debug o Obj\Release e che contiene una classe parziale con le definizioni dei controlli. Dovreste trovare il seguente codice, aggiunto già nel momento della dichiarazione da XAML:

    <System.Diagnostics.DebuggerNonUserCodeAttribute(),  _

     System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never),  _

     System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Design", "CA1033:InterfaceMethodsShouldBeCallableByChildTypes")>  _

    Sub System_Windows_Markup_IComponentConnector_Connect(ByVal connectionId As Integer, ByVal target As Object) Implements System.Windows.Markup.IComponentConnector.Connect

        If (connectionId = 1) Then

            Me.Button1 = CType(target,System.Windows.Controls.Button)

           

            #ExternalSource("..\..\Window1.xaml",6)

            AddHandler Me.Button1.Click, New System.Windows.RoutedEventHandler(AddressOf Me.Button1_Click)

            

            #End ExternalSource

            Return

        End If

        Me._contentLoaded = true

    End Sub

Tralasciate corpo del metodo e attributi, ma fate attenzione all'istruzione AddHandler. Ciò significa che Visual Studio ha già provveduto per noi a specificare cosa serve correttamente per gestire l'evento. Specificare anche la clausola Handles ha lo stesso effetto di aggiungere una seconda AddHandler e quindi è spiegato il perchè del problema.

Detto questo, abbiamo due soluzioni. La prima, in cui dichiariamo il gestore da XAML senza usare Handles da codice VB:

        <Button Width="100" Height="30" Name="Button1" Click="Button1_Click" />

 

    Private Sub Button1_Click(ByVal sender As System.Object, _

                              ByVal e As System.Windows.RoutedEventArgs)

         MessageBox.Show("You clicked!")

    End Sub

Oppure la seconda, in cui non specifichiamo nulla in XAML ma usiamo Handles da codice VB:

        <Button Width="100" Height="30" Name="Button1" />

    Private Sub Button1_Click(ByVal sender As System.Object, _

                              ByVal e As System.Windows.RoutedEventArgs) _

                              Handles Button1.Click

        MessageBox.Show("You clicked!")

    End Sub

Spero vi sia utile.

Alessandro

Print | posted on giovedì 15 gennaio 2009 21:02 | Filed Under [ Visual Basic Windows Presentation Foundation ]

Powered by:
Powered By Subtext Powered By ASP.NET