Blog Archives

the calling thread cannot access wpf win form c# multi threading

If you receive this error:
The calling thread cannot access this object because a different thread owns it

It is a simple fix to add in some common multi-threading invocation mechanisms.


//with delegate declared
public delegate mydelegate;
this.Dispatcher.Invoke(new mydelegate(funcname));
                    this.Dispatcher.Invoke((mydelegate)delegate() { funcname(); });

//does not require delegate declared, i usually prefer this approach but there are situations for either
                    this.Dispatcher.Invoke((Action)delegate() { funcname(); });
                    this.Dispatcher.Invoke((Action)(()=>{ funcname();}));


this.Invoke(funcname, params);
this.BeginInvoke(funcname, params);


Winforms Databinding

Snippets below have been condensed from their original sources for brevity. See references for original articles.

Dataset usage:

using System;
using System.Data;
using System.Data.SqlClient;

namespace Microsoft.AdoNet.DataSetDemo
    class NorthwindDataSet
        static void Main()
            string connectionString = GetConnectionString();

        private static void ConnectToData(string connectionString)
            //Create a SqlConnection to the Northwind database.
            using (SqlConnection connection =
                       new SqlConnection(connectionString))
                //Create a SqlDataAdapter for the Suppliers table.
                SqlDataAdapter adapter = new SqlDataAdapter();

                // A table mapping names the DataTable.
                adapter.TableMappings.Add("Table", "Suppliers");

                // Open the connection.
                Console.WriteLine("The SqlConnection is open.");

                // Create a SqlCommand to retrieve Suppliers data.
                SqlCommand command = new SqlCommand(
                    "SELECT SupplierID, CompanyName FROM dbo.Suppliers;",
                command.CommandType = CommandType.Text;

                // Set the SqlDataAdapter's SelectCommand.
                adapter.SelectCommand = command;

                // Fill the DataSet.
                DataSet dataSet = new DataSet("Suppliers");

                // Create a second Adapter and Command to get
                // the Products table, a child table of Suppliers. 
                SqlDataAdapter productsAdapter = new SqlDataAdapter();
                productsAdapter.TableMappings.Add("Table", "Products");

                SqlCommand productsCommand = new SqlCommand(
                    "SELECT ProductID, SupplierID FROM dbo.Products;",
                productsAdapter.SelectCommand = productsCommand;

                // Fill the DataSet.

                // Close the connection.
                Console.WriteLine("The SqlConnection is closed.");

                // Create a DataRelation to link the two tables
                // based on the SupplierID.
                DataColumn parentColumn =
                DataColumn childColumn =
                DataRelation relation =
                    new System.Data.DataRelation("SuppliersProducts",
                    parentColumn, childColumn);
                    "The {0} DataRelation has been created.",

        static private string GetConnectionString()
            // To avoid storing the connection string in your code, 
            // you can retrieve it from a configuration file.
            return "Data Source=(local);Initial Catalog=Northwind;"
                + "Integrated Security=SSPI";

Binding DataGridView:

private void GetData(string selectCommand)
        // Specify a connection string. Replace the given value with a 
        // valid connection string for a Northwind SQL Server sample
        // database accessible to your system.
        String connectionString =
            "Integrated Security=SSPI;Persist Security Info=False;" +
            "Initial Catalog=Northwind;Data Source=localhost";

        // Create a new data adapter based on the specified query.
        dataAdapter = new SqlDataAdapter(selectCommand, connectionString);

        // Create a command builder to generate SQL update, insert, and
        // delete commands based on selectCommand. These are used to
        // update the database.
        SqlCommandBuilder commandBuilder = new SqlCommandBuilder(dataAdapter);

        // Populate a new data table and bind it to the BindingSource.
        DataTable table = new DataTable();
        table.Locale = System.Globalization.CultureInfo.InvariantCulture;
        bindingSource1.DataSource = table;

        // Resize the DataGridView columns to fit the newly loaded content.
    catch (SqlException)
        MessageBox.Show("To run this example, replace the value of the " +
            "connectionString variable with a connection string that is " +
            "valid for your system.");

MSDN, “DataSet Class”,

MSDN, “How to: Bind Data to the Windows Forms DataGridView Control”,