seekinghelp
seekinghelp

Reputation: 13

[C# windows form]When invoking a listview in a thread, other controls doesnt work

I am new to C#, I hope my description of the problem is readable. Here's my problem, I am developing a app for a win6.5 mobile. The App should have some memu items, one is 'scan', when clicked, it scans repeatedly the wifi access points nearby, and displays them on a listview. So i create a thread with a while loop for scanning every 10 seconds, i also use listview.invoke to make the listview accessible in the thread. Things looks fine when 'scan' is clicked, however, other menu items cannot be clicked due to the running of the while loop thread. I stuck here for several days, many thanks for u guys help~

private void menuItemScan_Click(object sender, EventArgs e)
        {
            ...

            Thread t = new Thread(new ThreadStart(ScanThread));
            t.Start();
        }

        private void ScanThread()
        {

            listView1.Invoke(new APScanCallback(APScan));

        }

        public void APScan() 
        {
            while (true)
            {

                listView1.Items.Clear();
                foreach (AccessPoint ap in wzcInterface.NearbyAccessPoints)
                {
                    ListViewItem item = new ListViewItem(ap.Name);
                    item.SubItems.Add(ap.PhysicalAddress.ToString());
                    item.SubItems.Add(ap.SignalStrength.Decibels.ToString());
                    item.SubItems.Add(ap.AuthenticationMode.ToString());
                    listView1.Items.Add(item);
                }
                listView1.Refresh();
                Thread.Sleep(10000);
            }

        }

Upvotes: 1

Views: 2639

Answers (2)

Luca
Luca

Reputation: 11961

Control.Invoke "enqueue" the method execution to the thread handling UI (in order to serialize those routine call to the other UI routine calls).

Even if you start a thread which calls Control.Invoke, the routine APSScan is executed in thread which has called Application.Run... and what I see is that APSScan never returns, causing to freeze the UI thread.

The solution is to call Control.Invoke multiple times, looping in ScanThread routine.

Using your code:

private void ScanThread()
    {

        while (true) {
            listView1.Invoke(new APScanCallback(APScan));
            Thread.Sleep(10000);
        }
    }

    public void APScan() 
    {
            listView1.Items.Clear();
            foreach (AccessPoint ap in wzcInterface.NearbyAccessPoints)
            {
                ListViewItem item = new ListViewItem(ap.Name);
                item.SubItems.Add(ap.PhysicalAddress.ToString());
                item.SubItems.Add(ap.SignalStrength.Decibels.ToString());
                item.SubItems.Add(ap.AuthenticationMode.ToString());
                listView1.Items.Add(item);
            }
            listView1.Refresh();
     }

Upvotes: 3

Alex F
Alex F

Reputation: 43311

Your code is actually running in the main thread.

listView1.Invoke(new APScanCallback(APScan));

This code submits execution of APScan in the main application thread. Just use the timer insteaf of worker thread.

Upvotes: 0

Related Questions