Hello,
J'ai un problème avec mon programme (C# / WPF). Je n'ai pas trouvé une réponse dans les postes déjà existant. Peut-être que j'ai mal exprimer mon problème.
Un petit brief sur mon application. J'ai une image qui est affichée, sur cette dernière on met des pin. Bien sur l'image n'est pas affichée en entière dans l'application. Il est donc possible de la bouger, zoom in et zoom out. (L'image est une image live, un flux)
Du coup je vous explique mon problème; j'ai une liste d'objet Position qui peut contenir jusqu'à 2500 Positions. L'objet Position contient sa PositionOnWindow. Je peux appliquer un déplacement sur ses 2500 Positions en d'autres mots je fais une translation. Jusque là c'est assez simple, le problème et que lorsque j'applique une translation le code s’exécute en 90ms en moyenne mais le UI met 5-10 sec à se rafraîchir ce qui me fait dire que c'est un problème de INotifyChanged qui est levé 2500 fois.
Voilà ma boucle qui prend en compte le déplacement:
J'ai testé avec et sans le Dispatcher. Sans le Dispatcher on voit bien les positions se mettre à jour les une après les autres, le temps pour avoir toutes les positions mise à jour est donc encore plus lent.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4 foreach (var pos in Positions) { Application.Current.Dispatcher.BeginInvoke((Action)(() => { pos.PositionOnWindow += pixelDisplacement; })); } //94ms ellapsed
Voici ma propriété:
Voici la manière que j'utilise pour display mes positions: (le ContentControl va utiliser une propriété qui est le type de "view" lié a un objet)
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14 public Point PositionOnWindow { get => _positionOnWindow; set { if(_positionOnWindow == value) return; lock (_lockPositionOnWindow) { _positionOnWindow = value; DoPropertyChanged(); } } } private Point _positionOnWindow;
Quelques informations en plus:
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9 <ItemsControl ItemsSource="{Binding Positions}"> <ItemsControl.ItemTemplate> <DataTemplate> <Canvas> <ContentControl Content="{Binding Converter={view:ElementToViewConverter}}"/> </Canvas> </DataTemplate> </ItemsControl.ItemTemplate> </ItemsControl>
1. Mon application est en 32bits, je ne pense pas que cela fasse un grand changement.
2. J'ai vu que le première éléments dans la liste Positions est render en 2.06ms, le dernier lui met 52ms (chaque position est plus lente que la précédente). Je n'arrive pas à comprendre pourquoi.
3. J'ai trouvé un article parlant du fait que INotifyChanged était obsolète mais il n'y avait pas de solution pour le remplacer. Je viens donc d'éjà vous demander ce que vous pensez de ce problème ? Est-ce que il y a une autre manière pour faire cette opération sans que le UI soit lent ?
Je répond très volontiers a vos questions. J'espère que j'ai bien expliquer mon problème.
Merci d'avance.
Partager