2010-05-15 4 views
2

iPHone: Nous utilisons MonoTouch, mais les réponses Obj-C sont correctes.L'équivalent iPhone de Application.DoEvents();

Mon objet de domaine singleton met un certain temps à obtenir toutes les données afin qu'il exécute des parties internes de l'extraction dans un thread.

J'ai besoin d'informer l'interface utilisateur que le domaine est fait. Actuellement je fais ça. Y a-t-il un meilleur moyen? Dans WinForms, j'appellerais Application.DoEvents() au lieu de Thread Sleep.

PlanDomain domain = PlanDomain.Instance(); 
while (domain.IsLoadingData) 
{ 
    Thread.Sleep (100); //this is the main UI thread 
} 

TableView.Hidden = false; 
TableView.Source = new TableSource (this); 
TableView.ReloadData(); 

Répondre

3

D'une manière générale vous voulez éviter DoEvents Le equivilant iPhone en objective-C ressemble à quelque chose comme ceci:..

[[NSRunLoop currentRunLoop] runUntilDate:[NSDate date]]; 
1

Je vois si vous pouvez utiliser performSelectorOnMainThread: déplacer votre code Tableview à sa propre méthode et de rappeler que lorsque vous avez terminé avec les données de chargement.

Les délégués sont également utiles dans ce scénario - obtenez votre PlanDomain à rappeler à une fonction de délégué lorsque c'est fait.

De manière simplifiée, si vous voulez quelque chose de plus détaché, consultez NSNotification s. Ceux-ci sont plus utiles lorsque le code que vous écrivez n'a pas besoin de savoir ou de se préoccuper de ce qui va se passer quand il est fini - il suffit d'annoncer au monde que c'est fait son travail. (Plus utile là où il est potentiellement plus d'une chose qui peut être intéressé à agir lorsque sa complète

Dans toutes ces choses, vous ne voulez pas Sleeps -.. Il suffit de laisser la runloop poignée il

2

Il serait préférable d'avoir quelque chose dérivé de AlertView (une boîte de dialogue de chargement), à moins que vous souhaitez effectuer le chargement d'arrière-plan

Cela exécute ensuite la tâche dans un Thread distinct auquel vous vous connectez, puis fermez la boîte de dialogue. Il y a un exemple here, mais ne comporte aucune filetage mais il est trivial de ne pas ajouter:

public class LoadingView : UIAlertView 
{ 
    private UIActivityIndicatorView _activityView; 

    public void Show(string title) 
    { 
     Title = title; 
     Show(); 

     // Spinner - add after Show() or we have no Bounds. 
     _activityView = new UIActivityIndicatorView(UIActivityIndicatorViewStyle.WhiteLarge); 
     _activityView.Frame = new RectangleF((Bounds.Width/2) - 15, Bounds.Height - 50, 30, 30); 
     _activityView.StartAnimating(); 
     AddSubview(_activityView); 

     // I haven't tested this, it should display the dialog still. 
     Thread thread = new Thread(DoWork); 
     thread.Start(); 
     thread.Join(); 

     Hide(); 
    } 

    private void DoWork() 
    { 
     PlanDomain domain = PlanDomain.Instance(); 
     while (domain.IsLoadingData) 
     { 
      // Maybe replace domain.IsLoadingData with an Event for when it finishes. 
      // And then use a Mutex (WaitHandle) to communicate back 
     } 
    } 

    public void Hide() 
    { 
     DismissWithClickedButtonIndex(0, true); 
    } 
} 
6

Juste pour le suivi des réponses salons, voici un exemple de code C#:

NSRunLoop.Current.RunUntil(DateTime.Now.AddMilliseconds(2000)); 

Cette volonté pause 2000 millisecondes, mais assurez-vous que l'interface utilisateur met à jour. Je l'ai juste utilisé dans un code de test.