0

Am having a method

public void selectingTab(string name)
{
   //Code to select a particular tabitem in the XAML based on the parameter name
}`

in my WPF code behind and in my XAML page, i have a tab control.The parameter of the function specifies which tabitem should be brought to focus.And i want to call this method in a class file in the same solution. But when i try to call this method as NewChatWindow.selectingTab(clientName) am getting an error like object reference is required.When i try to create some object for the window and call the method like

NewChatWindow win = new NewChatWindow();
win.selectingTab(clientName);

Am getting the error "The calling thread must be STA, because many UI components" . How can i go about this.Thanks in advance.

Gayot Fow
  • 8,710
  • 1
  • 35
  • 48
Dhivya Sadasivam
  • 155
  • 2
  • 2
  • 14

3 Answers3

2

There's TWO things going on here...

The UI thread cannot interact with activity originating in a different thread when controls are involved (such as your tab control). To avoid cross-threading problems, use a construct like this...

  private void DoSomethingOnTheUiThread()
        {
            Dispatcher.BeginInvoke((Action) (() =>
                {
                    // your code goes here...
                    Window w = new Window();
                    w.Show();
                }));
        }

...where the 'Dispatcher' gets the System.Windows.Threading.Dispatcher the window is associated with. Every UIElement has a dispatcher for this purpose. BeginInvoke schedules the delegate to run on the UI thread.

A related SO question gives more insight here: WPF Cross Thread Object Access

...and here How to deal with cross-thread access exceptions?

For your other issue, let's look at your code...

Task.Factory.StartNew(() => 
{
   NewWindow.selectingTab(ClientName); 
   using (var ns = cl.GetStream()) 
   using (var br = new BinaryReader(ns)) 
   using (var bw = new BinaryWriter(ns)) 
   { 
      Console.WriteLine("Message from client is " + br.ReadString() + " from " + clientName); } }); 

In your commentary you point out that 'NewWindow' is a class. But you are calling an instance method of 'NewWindow', not a static method of 'NewWindow'. So the compiler has complained about it.

To call an instance method, you must first create an instance, like this...

NewWindow nw = new NewWindow();
nw.selectedTab("some name");

The c# forefathers made the syntax 'NewWindow.selectedTab' to mean a static method. I don't know which of these you want to implement, but you'll need to pick one that is consistent with your usage.

Relevant docs are here: http://msdn.microsoft.com/en-us/library/aa645766(v=vs.71).aspx

**

When a method is referenced in a member-access (Section 7.5.4) of the form E.M, if M is a static method, E must denote a type containing M, and if M is an instance method, E must denote an instance of a type containing M.

**

Community
  • 1
  • 1
Gayot Fow
  • 8,710
  • 1
  • 35
  • 48
0

I am assuming that you are using reflection to obtain the property information during runtime. You may be getting the object reference required error by how you are calling the instance method (Object reference is required for the nonstatic field method or property). Until you include the code that you have omitted, we can only guess as to why this error occurred.

  1. If you want to reference an object in the XAML, you need an x:Name directive (The x:Name directive in WPF).

Here's an example of the WPF part:

<StackPanel DockPanel.Dock="Right" Background="Yellow" MinWidth="150" Margin="2" x:Name="StackPanelRight"></StackPanel>

Then, you can reference your named attribute from your code-behind.

        StackPanel sp = new StackPanel();
        StackPanel btnSP = new StackPanel();
        btnSP.Orientation = Orientation.Horizontal;
        btnSP.HorizontalAlignment = System.Windows.HorizontalAlignment.Center;
        btnSP.Children.Add(btn3);
        btnSP.Children.Add(btn4);
        sp.Children.Add(btnSP);
        StackPanelRight.Children.Add(sp);

STA stands for Single-Threaded Apartment. STA was coined during the COM days (Understanding The COM Single-Threaded Apartment ). Assuming your threading is asynchronous, this article may help you: Best practices in asynchronous programming.

Community
  • 1
  • 1
devinbost
  • 4,658
  • 2
  • 44
  • 57
  • I think i explained the question in a reverse way.All i need is am having a method in the XAML code behind all i want is to call the method from another .cs file tats all. – Dhivya Sadasivam Oct 19 '13 at 17:17
  • I'm not sure that I understand what you mean by this: "All i need is am having a method in the XAML code behind all i want is to call the method from another .cs file tats all." What do you mean by "a method in the XAML code behind"? – devinbost Oct 21 '13 at 00:38
0

In order to utilize WPF functionality and benefits I would suggest using the MVVM pattern. From a model notification the UI can be modified (the required tab selected) event if a background thread initiates the change.

More about the MVVM pattern: This thread

Community
  • 1
  • 1
Daniel Leiszen
  • 1,827
  • 20
  • 39