PC Review


Reply
Thread Tools Rate Thread

DataGridView refresh problem (DataTable)

 
 
=?Utf-8?B?R2Vvcmdl?=
Guest
Posts: n/a
 
      20th Jun 2006
Hi,

I have been encountering a refresh problem with DataGridView, which is bound
to a DataTable.

When I make updates (Add, Delete, update) to the DataGridView, everything
flow nicely to DataTable. No problem here.

However, when I add data (programatically) to the DataTable, the
DataGridView does not refresh right away. If I minimize and show my form,
the new rows are now shown in my form.

Yet, when I select the new rows, the "selection triangle" is not displayed
properly on the new rows. The selection works fine with the original rows.

I made an attempt to solve the problem by using a delegate to manually
perform refresh. I solve the "non-displaying" problem, but still have the
"selection" problem.

I also notice that, as soon as I delete or cell-update a row, all these
problems go away.

Is this a bug in .Net 2.0?

Thanks,
--
George
 
Reply With Quote
 
 
 
 
=?Utf-8?B?R2Vvcmdl?=
Guest
Posts: n/a
 
      21st Jun 2006
Hi Jeffrey,

My code is similar to yours, with one exception.

You activate the DataTable.Rows.Add() from a control (button).

I have a FileSystemWatcher which detects a new input file. When a new file
appears, my code reads this file and append new data to my DataTable. Hence,
there is no interaction to the DataGridView.

I suspect the "in-activity" is causing the refresh problem. As I stated in
my first e-mail. As soon as I "interactively" delete a row, everything is
fine.

Any ideas?

Thanks,




--
George


""Jeffrey Tan[MSFT]"" wrote:

> Hi George,
>
> Thanks for your post!
>
> I have written a sample project regarding your scenario, however, it works
> well on my side:
>
> DataTable dt;
> private void Form1_Load(object sender, EventArgs e)
> {
> dt = new DataTable();
> dt.Columns.Add("column1", typeof(int));
> dt.Columns.Add("column2", typeof(string));
>
> for (int i = 0; i < 5; i++)
> {
> DataRow dr = dt.NewRow();
> dr["column1"] = i;
> dr["column2"] = "item" + i.ToString();
> dt.Rows.Add(dr);
> }
> this.dataGridView1.DataSource = dt;
> }
>
> private void button1_Click(object sender, EventArgs e)
> {
> DataRow dr=this.dt.NewRow();
> dr["column1"] = 1000;
> dr["column2"] = "NewItem";
> dt.Rows.Add(dr);
> }
> When I clicked Button1 to add a new row to the DataTable, the DataGridView
> refresh the update immediately.
>
> I have attached my sample project in this reply for your reference. You may
> download it with Outlook Express, not IE.
>
> Thanks!
>
> Best regards,
> Jeffrey Tan
> Microsoft Online Community Support
> ==================================================
> When responding to posts, please "Reply to Group" via your newsreader so
> that others may learn and benefit from your issue.
> ==================================================
> This posting is provided "AS IS" with no warranties, and confers no rights

 
Reply With Quote
 
Jeffrey Tan[MSFT]
Guest
Posts: n/a
 
      22nd Jun 2006
Hi George,

Thanks for your feedback information!

Yes, I think your background information is critical regarding resolving
your problem.

FileSystemWatcher event fires in another thread other than the main GUI
thread, if you add the new row into the DataTable directly, the .Net
Winform databinding code will try to update the new row into the
DataGridView UI.
However, .Net Windows Forms uses the single-threaded apartment (STA) model
because Windows Forms is based on native Win32 windows that are inherently
apartment-threaded. The STA model implies that a window can be created on
any thread, but it cannot switch threads once created, and all function
calls to it must occur on its creation thread. So your code indirectly
manipulates the DataGridView from the non GUI thread which offends the STA
rule in .Net Winform. This may cause some strange and hard to detect
multithreading issue. Please refer to the the article below for more
information:
"Multithreaded Windows Forms Control Sample"
http://msdn.microsoft.com/library/de...us/cpguide/htm
l/cpconDevelopingMultithreadedWindowsFormsControl.asp

You should use Control.Invoke method to marshal the manipulating to the GUI
control from another thread. Below is my modified sample code snippet:

DataTable dt;
private void Form1_Load(object sender, EventArgs e)
{
dt = new DataTable();
dt.Columns.Add("column1", typeof(int));
dt.Columns.Add("column2", typeof(string));

for (int i = 0; i < 5; i++)
{
DataRow dr = dt.NewRow();
dr["column1"] = i;
dr["column2"] = "item" + i.ToString();
dt.Rows.Add(dr);
}
this.dataGridView1.DataSource = dt;

FileSystemWatcher fsw = new FileSystemWatcher("C:\\");
fsw.EnableRaisingEvents = true;
fsw.Created += new FileSystemEventHandler(fsw_Created);
}

void fsw_Created(object sender, FileSystemEventArgs e)
{
this.dataGridView1.Invoke(new EventHandler(button1_Click));
}

private void button1_Click(object sender, EventArgs e)
{
DataRow dr=this.dt.NewRow();
dr["column1"] = 1000;
dr["column2"] = "NewItem";
dt.Rows.Add(dr);
}

This code snippet works well on my side. If I create a new file in the
"C:\" folder, a new row will be added to the DataGridView. I have also
attached the modified project in this reply for your reference.

I hope this will resolve your problem. If you still have any problem of
resolving it, please feel free to tell me, I will work with you.

Thanks!

Best regards,
Jeffrey Tan
Microsoft Online Community Support
==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================
This posting is provided "AS IS" with no warranties, and confers no rights.

 
Reply With Quote
 
=?Utf-8?B?R2Vvcmdl?=
Guest
Posts: n/a
 
      22nd Jun 2006
Hi Jeffrey,

Thanks, your suggestion works. I no longer needs to manually refresh or
ResetBindings the DataGridView.

I have some additional questions/comments though. Questions first.

Q. Should I wrap all readonly, read-write and write calls to DataTable
(bounded source) and use Control.Invoke to ensure UI thread is used? For
example, DataTable.Rows[index] could be read only, or write.
DataTable.Update() may cause changes. How far should I go?

Comment: Wrapping these calls become very cumbersome, and potentially a
bottle neck since UI thread may be bogged down by work. Does Microsoft plan
to make Data bound control such as DataGridView, multi-thread safe?

Thanks,


--
George


""Jeffrey Tan[MSFT]"" wrote:

> Sorry, forgot to attach the sample project. Here it is.
>
> Best regards,
> Jeffrey Tan
> Microsoft Online Community Support
> ==================================================
> When responding to posts, please "Reply to Group" via your newsreader so
> that others may learn and benefit from your issue.
> ==================================================
> This posting is provided "AS IS" with no warranties, and confers no rights

 
Reply With Quote
 
=?Utf-8?B?R2Vvcmdl?=
Guest
Posts: n/a
 
      22nd Jun 2006
Jeffrey,

DataTable.Update(), I meant DataAdapter.Update(DataTable). This potentially
changes DataTable.

Thanks,
--
George


"George" wrote:

> Hi Jeffrey,
>
> Thanks, your suggestion works. I no longer needs to manually refresh or
> ResetBindings the DataGridView.
>
> I have some additional questions/comments though. Questions first.
>
> Q. Should I wrap all readonly, read-write and write calls to DataTable
> (bounded source) and use Control.Invoke to ensure UI thread is used? For
> example, DataTable.Rows[index] could be read only, or write.
> DataTable.Update() may cause changes. How far should I go?
>
> Comment: Wrapping these calls become very cumbersome, and potentially a
> bottle neck since UI thread may be bogged down by work. Does Microsoft plan
> to make Data bound control such as DataGridView, multi-thread safe?
>
> Thanks,
>
>
> --
> George
>
>
> ""Jeffrey Tan[MSFT]"" wrote:
>
> > Sorry, forgot to attach the sample project. Here it is.
> >
> > Best regards,
> > Jeffrey Tan
> > Microsoft Online Community Support
> > ==================================================
> > When responding to posts, please "Reply to Group" via your newsreader so
> > that others may learn and benefit from your issue.
> > ==================================================
> > This posting is provided "AS IS" with no warranties, and confers no rights

 
Reply With Quote
 
Jeffrey Tan[MSFT]
Guest
Posts: n/a
 
      23rd Jun 2006
Hi George,

Thanks for your feedback!

1. Yes, read-only manipulation to the GUI thread also needs to be wrapped
with Control.Invoke/BeginInvoke method. Let's suppose a control is still
updating its state while you are retrieving its state, you may get an
immediate partial updated state which may appear to be incorrect.

2. To wrap these methods or properties calling, you may write a
method(let's call it WrapMethod() ) in Form class which contains all these
code, then in FileSystemWatcher thread, you can just marshal once calling
to the WrapMethod(), not marshal to all the code statements. This will save
a lot of work.

3. Yes, any operations may cause calling to the GUI thread
methods/properties need to be mashaled.

4. Yes, I see your concern, many customers have feedbacked such request
regarding .Net winform multithreading. However, this marshaling request is
not caused by .Net Winform code, it is caused by the native Win32 standard
controls. Native Win32 windows that are inherently apartment-threaded
without thread-safe build-in for legacy reason. Because .Net controls
always encapsulate the native Win32 standard controls, it is almost
impossible for .Net winform to get rid of the STA feature. Thanks for your
understanding.

Hope my comment makes sense to you.

Best regards,
Jeffrey Tan
Microsoft Online Community Support
==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================
This posting is provided "AS IS" with no warranties, and confers no rights.

 
Reply With Quote
 
Jeffrey Tan[MSFT]
Guest
Posts: n/a
 
      27th Jun 2006
Hi George,

Does my reply make sense to you? If you have any concern, please feel free
to tell me, thanks!

Best regards,
Jeffrey Tan
Microsoft Online Community Support
==================================================
When responding to posts, please "Reply to Group" via your newsreader so
that others may learn and benefit from your issue.
==================================================
This posting is provided "AS IS" with no warranties, and confers no rights.

 
Reply With Quote
 
 
 
Reply

Thread Tools
Rate This Thread
Rate This Thread:

Posting Rules
You may not post new threads
You may not post replies
You may not post attachments
You may not edit your posts

BB code is On
Smilies are On
[IMG] code is On
HTML code is Off
Trackbacks are On
Pingbacks are On
Refbacks are Off


Similar Threads
Thread Thread Starter Forum Replies Last Post
Problem with REFRESH DataGridView Christian Microsoft C# .NET 4 22nd Apr 2008 11:52 AM
DataGridView doesn't refresh when DataTable rows are changed Dagan Microsoft Dot NET Framework Forms 1 30th Jun 2006 02:49 AM
DataGridView doesn't refresh when DataTable rows are changed Dagan Microsoft Dot NET 0 18th Jun 2006 01:20 PM
DataGridView doesn't refresh when DataTable rows are changed Dagan Microsoft Dot NET Framework 0 18th Jun 2006 01:20 PM
dataTable to Datagridview problem Irfan Microsoft VB .NET 0 14th Feb 2006 10:34 AM


Features
 

Advertising
 

Newsgroups
 


All times are GMT +1. The time now is 02:48 AM.