C# Cross-thread operation not valid hatası için çözüm

  1. bobmarley
    25
    442
    26.06.2018 17:55:00

    C# windows form uygulamamda Control '' accessed from a thread other than the thread it was created on hatası alıyorum

    Hata Detayı

    > > Cross-thread operation not valid: Control 'listBox1' accessed from a thread other than the thread it was created on

    hata bu şekilde.

    Hata da listBox1 satırının olduğu yerde çıkıyor tam.Bir tane ocr yapan dll var , o dll in bir callBack metodu var ona resultCallback() metodunu bağlıyorum.Ocr ı start ediyorum , o da sonucu benim resultCallback() metoduma gönderiyor.

    Sonucu bir dosyaya yazmıştım sorun olmamıştı.Ancak bir tane ListBox a yazayım dedim , fakat yukardaki hatayı alıyorum

    private void resultCallback(Result newResult)
    {
        string result=newResult.OcrResult+"-"newResult.OcrDate;
        listBox1.Items.Add(result);
    }
    

    Teşekkürler yardımlarınız ve önerileriniz için

    c# .net 1 yıl önce 714 Görüntüleme
    • Snoopy Callback ile sonucu almandan ve bu hatadan yola çıkarak , Ocr dediğin tarafta sanki asenkron bir süreç var , orda main threadden farklı bir thread var , sonuç o thread den geliyorsa , main threadin kontrolünde olan Windows form componentlerine müdehele etmeye kalkınca bu hata olur

    • bobmarley ya ben o tarafa çok hakim değilim , ama sordum o kısmı yazan kişiye , evet o tarafta bir thread bize bu sonuçları yakaladıkça veriyormuş

    • Yorum Ekleyin

( 2 ) Cevap

  1. Snoopy
    25
    11251
    26.06.2018 23:00:00

    Şimdi Windows Form uygulamalarında , main thread den ayrı bir thread , herhangi bir listbox, textbox ,label vb. componente müdahele etmeye kalkınca dananın kuyruğu kopar.Aynen yukarda ki hatayı alırsın.

    Bunun için bir kaç yöntem var ,ben bir en sık kullandığım yöntemi senin koduna uyarlıyayım;

    private void resultCallback(Result newResult)
    {
        string result=newResult.OcrResult+"-"newResult.OcrDate;
        if (listBox1.InvokeRequired)
        {
            listBox1.Invoke(new MethodInvoker(delegate
            {
                listBox1.Items.Add(result);
            }));
        }
        else
        {
            listBox1.Items.Add(result);
        }
    }
    

    listBox1 i InvokeRequired ile kontrol ediyorsun , invoke gerekliyse , listBox1 componentini invoke edilecek , gerekli değilse normal bildiğimiz gibi herşey.

    Diğer tüm componentler de aynı yöntem kullanılabilir ,label de de ,textbox da da...

    • kara26 visual studio da Toolbox da , listbox , label , textbox , button vb şeyler Common Controls olarak geçiyor , Components ler sekmesi altında ise , Timer , EventLog, ImageList , vb şeyler var , bu yüzden component değilde Control demek daha doğru olabilir

    • Yorum Ekleyin

  2. kara26
    3
    426
    25.04.2019 09:26:00

    Windows form uygulamasın da alınıyorsa bu hata , Program dosyası içerisindeki , programın ilk başta çalıştırdığı Main içerisine , Control.CheckForIllegalCrossThreadCalls = false; kodu eklenerek de kısa yoldan çözülebilir , başka bir şey yapmaya gerek kalmaz , her türlü control(listbox,textbox) farklı bir thread müdahale edebilir.

    //Program.cs içerisindeki Main metodu
    static void Main()
    {
            Application.EnableVisualStyles();
            Application.SetCompatibleTextRenderingDefault(false);
    
            //Cross-Thread Operation Not Valid hatası çözümü
            Control.CheckForIllegalCrossThreadCalls = false;
    
            Application.Run(new Form1());
    }
    

Cevabınız