2010-09-24 3 views
0

J'ai besoin seulement de montrer un contrôle personnalisé (une horloge avec les mains en rotation) et ce pour remplacer le curseur de la souris, le problème est que si j'écris:WPF forcer la mise à jour de l'interface graphique à l'aide Dipatcher

Me.gridScreen.Visibility = Visibility.Visible 
' some operations that takes about 1 second 
Me.gridScreen.Visibility = Visibility.Hidden 
(gridScreen is the grid that contains the user-control) 

Il est évident que je ne peut rien voir, parce que la mise à jour de l'interface utilisateur se produit à la fin de la procédure. J'ai essayé Me.UpdateLayout(), mais cela ne fonctionne pas.

Je tryed d'utiliser le dispacker dans de nombreux cours, mais aucun qui fonctionne :-(

Ceci est ma tentative perdue:

(uCurClock est le usercontrol, gridScreen une grille placée au plus haut niveau dans la fenêtre, avec fond trasparent, qui contient le usercontrol)

Private Sub showClock() 
    Dim thread = New System.Threading.Thread(AddressOf showClockIntermediate) 
    thread.Start() 
End Sub 

Private Sub hideClock() 
    Dim thread = New System.Threading.Thread(AddressOf hideClockIntermediate) 
    thread.Start() 
End Sub 

Private Sub showClockIntermediate() 
    Me.Dispatcher.BeginInvoke(DispatcherPriority.Normal, _ 
     New Action(AddressOf showClockFinale)) 
End Sub 

Private Sub hideClockIntermediate() 
    Me.Dispatcher.BeginInvoke(DispatcherPriority.Normal, _ 
     New Action(AddressOf hideClockFinale)) 
End Sub 

Private Sub showClockFinale() 
    Dim pt As Point = Mouse.GetPosition(Nothing) 
    Me.uCurClock.Margin = New Thickness(pt.X - 9, pt.Y - 9, 0, 0) 
    Me.gridScreen.Visibility = Visibility.Visible 
    Me.Cursor = Cursors.None 
    Me.UpdateLayout() 
End Sub 

Private Sub hideClockFinale() 
    Me.gridScreen.Visibility = Visibility.Hidden 
    Me.Cursor = Cursors.Arrow 
    Me.UpdateLayout() 
End Sub 

Private Sub u_MouseMove(ByVal sender As System.Object, _ 
    ByVal e As MouseEventArgs) Handles gridScreen.MouseMove 

    Dim pt As Point = e.GetPosition(Nothing) 
    Me.uCurClock.Margin = New Thickness(pt.X - 9, pt.Y - 9, 0, 0) 

    e.Handled = True 
End Sub 

Private Sub u_MouseEnter(ByVal sender As System.Object, _ 
    ByVal e As MouseEventArgs) Handles gridScreen.MouseEnter 

    Me.uCurClock.Visibility = Visibility.Visible 

    e.Handled = True 
End Sub 

Private Sub u_MouseLeave(ByVal sender As System.Object, _ 
    ByVal e As MouseEventArgs) Handles gridScreen.MouseLeave 

    Me.uCurClock.Visibility = Visibility.Hidden 

    e.Handled = True 
End Sub 

PILEGGI

Répondre

1

le problème est rien à voir avec la composition de mes sages en cours d'exécution sur le répartiteur, c'est que vous exécutez un travail de longue durée sur le répartiteur du tout. Vous devez vous assurer que les opérations de longue durée/potentiellement bloquantes sont exécutées sur un thread d'arrière-plan. La manière la plus simple de le faire est avec le composant BackgroundWorker.

Excuse C#:

var backgroundWorker = new BackgroundWorker(); 

backgroundWorker.DoWork += delegate 
{ 
    // long running work goes here 
}; 
backgroundWorker.RunWorkerCompleted += delegate 
{ 
    // change cursor back to normal here 
}; 

// change cursor to busy here 

// kick off the background task 
backgroundWorker.RunWorkerAsync(); 
+0

Merci, mais je sais qu'il n'y a pas des solutions. En fait, dans de nombreux cas, j'ai des procédures avec des opérations meny dans lesquelles je récupère des données de l'interface utilisateur et d'autres dans lesquelles je modifie les données de la source des collections de contrôles de l'interface utilisateur. Ces opérations sont interdites dans les threads d'arrière-plan et il est trop difficile de faire une séparation. Je pense que je vais seulement changer le curseur de la souris ... – lamarmora

+0

Merci beaucoup! Je connais le BackgroundWorker mais j'ai le problème qu'il est trop difficile de faire la séparation dans mes méthodes (qui existent déjà) entre les longs processus et les opérations sur l'interface utilisateur. Le seul moyen, pour le moment, est de changer uniquement le curseur de la souris: Me.Cursor = New Cursor ("chemin absolu du fichier .ani") – lamarmora

Questions connexes