Saint
Saint

Reputation: 5469

How to update Controls from static method?

Hello Why I haven't access to my private control on form (e.g. ListBox) from a static method? How to update control in this case?

EDIT 1.

my code:

ThreadStart thrSt = new ThreadStart(GetConnected);
        Thread thr = new Thread(thrSt);
        thr.Start();

and

static void GetConnected()
    {
        //update my ListBox
    }

So it must be void, without param and be static, right?

EDIT 2.

If someone need solution in WPF then should try this:

private void GetConnected()
    {
        myListBox.Dispatcher.Invoke(System.Windows.Threading.DispatcherPriority.Normal,
                    new Action(() =>
                    {
                        myListBox.Items.Add("something");
                    }
                               )
                 );
    }

Upvotes: 12

Views: 32469

Answers (6)

drindrin
drindrin

Reputation: 89

easiest solution for adding an item to a listbox from a static method:

  1. Add on your Form1 public static ListBox frm;
  2. After InitializeComponent() add frm = this.listBox1;
  3. from your static method call Form1.frm.Items.Add(myitem)

Upvotes: 1

MohammadHossein R
MohammadHossein R

Reputation: 1260

I just found a new and different way to update a control from a static method. but we have to choose unique names for our controls

foreach (Form tmp in Application.OpenForms)
    foreach (System.Windows.Forms.Control temp in tmp.Controls)
        if (temp.Name == "textBox1")
            temp.Text = "it works :)";

Upvotes: 3

AKMalkadi
AKMalkadi

Reputation: 982

You cannot access "this", "ui" or any function in MainWindow from a static function.

To solve this problem, make a public pointer of Mainwindow

Mainwindow *THIS;

before calling the callback function (the static function), assign this to the pointer THIS

THIS=this;

Now, you can use THIS instead of this.

for example:

THIS->listBox->Items->Add("Some element");

Upvotes: 0

MohammadHossein R
MohammadHossein R

Reputation: 1260

i found another answer on the web

write this in the form class:

static Form1 frm;

and in the form constructor:

frm = this;

now we can use the variable "frm" for accessing all of controls on the form.

somewhere in a static method:

frm.myListBox.Items.Add("something");

Upvotes: 22

Fredrik Mörk
Fredrik Mörk

Reputation: 158309

Static methods cannot access instance state (such as a non-static control). Either remove static from the method declaration, or pass a reference to the control as argument to the method:

private static void SomeMethod(ListBox listBox)
{
    listBox.Items.Add("Some element");
}

...and call it like so:

SomeMethod(MyListBox);

Update
There are different ways to do asynchronous things in the UI (now assuming winforms). I would recommend you to look into using BackgroundWorker (search here on SO; plenty of examples). If you really want to do it by creating threads on your own, here is one way to do that:

private void SomeMethod()
{
    string newElement = FetchNextElementToAdd():
    SafeUpdate(() => yourListBox.Items.Add(newElement));
}

private void SafeUpdate(Action action)
{
    if (this.InvokeRequired)
    {
        this.BeginInvoke(action);
    }
    else
    {
        action();
    }
}

...and to call it:

Thread thread = new Thread(SomeMethod);
thread.Start();

You can also use the thread pool (preferred over creating your own threads, given that you don't expect them to run for very long):

ThreadPool.QueueUserWorkItem(state => SomeMethod());

Upvotes: 4

jasper
jasper

Reputation: 3474

you need to pass a reference to the control to your static method, or something that contains them. static methods cant access non static fields/methods/etc. dont declare your control as static, i'm not even sure if its possible, but if it was, it would cause you problems you dont even want to know about.

Upvotes: 1

Related Questions