IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

C# Discussion :

MVVM - accéder aux objets d'une observableCollection à partir d'un autre thread


Sujet :

C#

  1. #1
    Membre régulier
    Homme Profil pro
    Inscrit en
    Mars 2007
    Messages
    244
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Canada

    Informations forums :
    Inscription : Mars 2007
    Messages : 244
    Points : 122
    Points
    122
    Par défaut MVVM - accéder aux objets d'une observableCollection à partir d'un autre thread
    Salut à toutes et à tous,

    Soit un TreeView avec un binding de l'ItemsSource sur une observableCollection<Lot>.
    Soit de longues actions dans un autre Thread.
    Je me suis vite rendu compte que je ne peux pas ajouter ou récupérer de Lot dans l'observableCollection parce que je ne suis pas sur le Thread de l'UI.
    J'ai trouvé de l'info et fait ceci qui fonctionne :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
            public void AddLotToCollection(Lot lot)
            {
                Application app = System.Windows.Application.Current;
                if (app != null)
                    app.Dispatcher.BeginInvoke(DispatcherPriority.Normal, new DispatcherOperationCallback(AddLot), lot);
            }
     
     
            private object AddLot(object lot)
            {
                LotsCollection.Add((Lot)lot);
                return null;
            }
    C'est ici que ça se complique.
    J'ai aussi besoin de récupérer des Lot dans l'observableCollection et de les modifier à partir de l'autre Thread.
    J'avais espéré ceci
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
            public Lot FindLotByNumero(string noLot)
            {
                Application app = System.Windows.Application.Current;
                if (app != null)
                {
                    app.Dispatcher.BeginInvoke(DispatcherPriority.Normal, new DispatcherOperationCallback(FindLot), noLot);
                }
                return null;
            }
     
     
            private Lot FindLot(object noLot)
            {
                return LotsCollection.FirstOrDefault(x => x.NoLot == noLot.ToString());
            }
    Malheureusement, le FindLot me retourne bien le bon lot, mais le FindLotByNumero retourne invariablement null.

    Il me semblait pourtant que le DispatcherOperationCallback retournait l'objet du delegate et que le BeginInvoke retournait l'objet, soit l'objet du delegate du DispatcherOperationCallback.

    Qu'est-ce que je n'ai pas compris et comment dois-je faire ?

    Merci de vos z'avis z'avisés.
    Il n'y a pas de problèmes. Il n'y a que des solutions.
    Malheureusement, elles sont parfois un peu dur à trouver ...


    Aucune touche n'a été maltraitée pour réaliser ce texte.

  2. #2
    Expert éminent sénior Avatar de Pol63
    Homme Profil pro
    .NET / SQL SERVER
    Inscrit en
    Avril 2007
    Messages
    14 154
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 42
    Localisation : France, Puy de Dôme (Auvergne)

    Informations professionnelles :
    Activité : .NET / SQL SERVER

    Informations forums :
    Inscription : Avril 2007
    Messages : 14 154
    Points : 25 072
    Points
    25 072
    Par défaut
    avec invoke au lieu de begininvoke ca ira peut etre mieux

    begininvoke mets sur la pile du thread principal et continue, invoke est "bloquant", le thread va attendre que le thread principal ait dépilé et retourné la réponse (pas de callback donc)
    mais en général c'est plus que court, donc ca ne servirait à rien de continuer et d'avoir un callback (sachant qu'en plus je pense que begininvoke peut plus facilement poser des soucis de deadlock)
    Cours complets, tutos et autres FAQ ici : C# - VB.NET

  3. #3
    Membre régulier
    Homme Profil pro
    Inscrit en
    Mars 2007
    Messages
    244
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : Canada

    Informations forums :
    Inscription : Mars 2007
    Messages : 244
    Points : 122
    Points
    122
    Par défaut
    Merci Pol63,

    Grâce à ton intervention j'ai modifié mon code comme ceci, et cela fonctionne :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
            public Lot FindLotByNumero(string noLot)
            {
                Application app = System.Windows.Application.Current;
                if (app != null)
                    return (Lot)app.Dispatcher.Invoke(DispatcherPriority.Normal, new DispatcherOperationCallback(FindLot), noLot);
                return null;
            }
     
     
            private Lot FindLot(object noLot)
            {
                return LotsCollection.FirstOrDefault(x => x.NoLot == noLot.ToString());
            }

    Je mets le bout de code au cas où cela serait utile à quelqu'un d'autre aussi.

    Encore merci.
    Il n'y a pas de problèmes. Il n'y a que des solutions.
    Malheureusement, elles sont parfois un peu dur à trouver ...


    Aucune touche n'a été maltraitée pour réaliser ce texte.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 6
    Dernier message: 07/07/2010, 11h42
  2. Réponses: 3
    Dernier message: 29/03/2010, 17h01
  3. Réponses: 3
    Dernier message: 02/01/2009, 00h28
  4. Accèder les objets d'une form à partir d'une classe
    Par xyron_x dans le forum Windows Forms
    Réponses: 2
    Dernier message: 05/04/2007, 14h49
  5. Accéder à des objets d'une Form à partir d'une classe
    Par kinouseb dans le forum Windows Forms
    Réponses: 4
    Dernier message: 23/01/2007, 18h07

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo