Thread wartet auf Form1, und Form1 wartet auf Thread. na toll...



  • Hi!

    Ich habe einen Thread der eine ListView regelmäßig aktualisiert.

    Wenn ich die bool-Variable, die den Thread beenden soll auf false setze WÄHREND der Thread Items in die ListView added steigt die Funktion in Zeile 19 aus, also die Stelle gegen eine Endlos-Schleife.

    Vermutlich ist mein Form1 also mit Warten beschäftigt und mein Thread wartet darauf, dass Form1 nicht mehr beschäftigt ist.

    // Ausschnitt aus meinem Thread
    
    //..
    while (MyForm1->execute_thread)	// while Thread is allowed to run
    {
        //...
        Add_viele_Items();
        //...
    }
    
    // Funktion zum Thread beenden
    
    int Form1_Functions::StopScanner (Form * Pointer_to_Form1)
    {
         Form1 * MyForm1 = static_cast<Form1*>(Pointer_to_Form1);
    	if (this->trd_alive(Pointer_to_Form1)) MyForm1->execute_thread = false;
    
    	int anti_never_ending = 0; // Zähler gegen Endlos-Schleife
    
    	while (this->trd_alive(Pointer_to_Form1)) // warte bis der Thread fertig ist
    	{
    		::SetCursor(LoadCursor(NULL, IDC_WAIT));
    		anti_never_ending++;
    		Sleep(100);
    		if (anti_never_ending > 50) 
    		{
                // zu lange gewartet
    			MyForm1->trd->Abort();
    			break;
    		}	
    	}
    return 0;
    }
    

    Kann mit vielleicht jemand einen Tip geben?
    Ich muss auf die ListView zugreifen obwohl Form1 wartet.

    Vielen Dank!

    pAT



  • Ein Thread sollte nie direkt auf UI-Controls zugreifen! Das ganz sollte immer mittels "BeginInvoke" oder "Invoke" geschehen... und bei BeginInvoke hast Du auch nicht die Probleme...



  • Hi!

    Vielen Dank, hört sich vielversprechend an!

    leider komme ich an einer Stelle nicht weiter:

    Ich soll anscheinend ein Array aus Objekten erstellen:

    array<Object^>^myArray = gcnew array<Object^>(2);  // <- Zeile 724
          myArray[ 0 ] = gcnew Label;
          myArray[ 1 ] = "Enter a Value";
          myTextBox->BeginInvoke( gcnew MyDelegate( this, &MyForm::DelegateMethod ), myArray );
    

    der Compiler meldet aber:

    d:\...\Form1_Functions.cpp(724): error C2059: Syntaxfehler: '>'
    d:\...\Form1_Functions.cpp(724): error C2065: 'array': nichtdeklarierter Bezeichner
    d:\...\Form1_Functions.cpp(724): error C2275: 'System::Object': Ungültige Verwendung dieses Typs als Ausdruck

    Ich verwende Microsoft Visual Studio .NET 2003
    Muss ich da etwas einbinden? Bin ich anders?

    gruß

    pAT



  • Die Syntax bei VS2003 ist komplett anders! z.B.:

    System::Void button1_Click(System::Object *  sender, System::EventArgs *  e)
    {
      if (this->InvokeRequired == true)
      {
        Object* o[] = new Object*[2];
        this->BeginInvoke(new System::EventHandler(this, button1_Click), o);
      }
    }
    

    PS: Ich Rate Dir dringend auf VC2005 umzusteigen, da Du sonst später alles wieder der neuen Syntax von VS2005 anpassen musst!



  • Ah, das erklärt so manche copy-paste-Probleme ^^
    Hast du mit 2003 selbst Erfahrungen und den Code aus dem Kopf gepostet?
    Oder kannst du mir verraten wo nu das nachgeschaut hast?

    Vielen herzlichen Dank!



  • www.pat schrieb:

    Oder kannst du mir verraten wo nu das nachgeschaut hast?

    Im Verzeichnis "C:\Programme\Microsoft Visual Studio .NET 2003\Vc7" gibt es ein Word-Dokument mit dem Namen "managedextensionsspec.doc", da steht eigentlich alles über managed C++ drin 😉



  • Vielen Dank für diese Info!

    Ich habe jetzt eine ganze Weile damit herunmexperimentiert und komme hier nicht mehr weiter:

    Object* Object_array[] = new Object*[2];
    Object_array[0] = Pointer_to_Form1;
    Object_array[1] = LVitem;
    
    MyForm1->BeginInvoke(WAS_MUSS_HIER_HIN(this, Add_Item_to_ListView), Object_array ); // <-
    

    Header:

    class Form1_Functions
    {
    
    public:
        //...
        int Add_Item_to_ListView (Form * Pointer_to_Form1_h, ListViewItem* listView_item_h);
        //...
    

    Kann mir das bitte jemand sagen?

    gruß

    pAT



  • Wenn Du was spezielles AUfrufen willst, dann musst Du dazu ein delegate definieren, z.B.:

    __delegate void MyDelegate(Form * Pointer_to_Form1_h, ListViewItem* listView_item_h);
    
    System::Void button1_Click(System::Object *  sender, System::EventArgs *  e)
    {
      Object* o[] = new Object*[2];
      this->BeginInvoke(new MyDelegate(this, MyMethode), o);
    }
    
    void MyMethode(Form * Pointer_to_Form1_h, ListViewItem* listView_item_h)
    {
      // TODO: ...
    }
    


  • Vielen Dank!

    Es lässt sich kompilieren!

    leider bekomme ich jetzt einen Runtime-Error den ich nicht lösen kann:

    Eine nicht behandelte Ausnahme des Typs 'System.TypeLoadException' ist in ListViewDieZweite.exe aufgetreten.

    Zusätzliche Informationen: Der Typ MyDelegate in der Assembly ListViewDieZweite, Version=1.0.2545.19357, Culture=neutral, PublicKeyToken=null konnte nicht geladen werden.

    __delegate void MyDelegate(System::Windows::Forms::Form* ptr_to_Form1, System::Windows::Forms::ListViewItem*);
    
    __gc class for_delegate
    {
    public:
        // ruft Add_Item_to_ListView aus Form1_Functions auf:
        static void Deleated_LV_add(System::Windows::Forms::Form* ptr_to_Form1, System::Windows::Forms::ListViewItem*);
    };
    
    class Form1_Functions
    {
    
    public:
        //...
        int Add_Item_to_ListView(Form * Pointer_to_Form1_h, ListViewItem* listView_item_h);
        //...
    };
    

    Da fehlt doch bestimmt einfach nur irgentwo ein Semikolon oder sowas.
    Siehts jemand?



  • ah wie doof, das public hat gefehlt.
    Anarchie funktioniert doch immernoch am besten ^^

    vorher:

    __delegate void MyDelegate(System::Windows::Forms::Form* ptr_to_Form1, System::Windows::Forms::ListViewItem*);
    

    nacher:

    public __delegate void MyDelegate(System::Windows::Forms::Form* ptr_to_Form1, System::Windows::Forms::ListViewItem*);
    

    jetzt funktionierts.


Anmelden zum Antworten