I believe it's not a good idea to load actual data to designer. You can fill DataGridView
using some fake data, the same way which web forms designer do it for ASP.NET GridView
control.
Q: How can I get MyDataTableTableAdapter? I don't see any connection between MyDataTable and
MyDataTableTableAdapter in the porject code.
Each dataset has an XSD
file which contains the definition of data set schema and also contains some annotations which will be used for generating TableAdapter
classes, for example it contains some nodes like:
<TableAdapter BaseClass="System.ComponentModel.Component"
DataAccessorModifier="AutoLayout, AnsiClass, Class, Public"
DataAccessorName="CategoryTableAdapter"
GeneratorDataComponentClassName="CategoryTableAdapter"
Name="Category"
UserDataComponentName="CategoryTableAdapter">
You can parse the file and extract the related TableAdapter
for the DataTable
. As you can see above xml is the point which TableAdapter
and DataTable
relates to each other.
You can get the xsd file using Visual Studio API methods. Also as a more simple workaround you can set its BuildAction
to Embedded Resource
and get it from the compiled assembly.
Note
Another option which may satisfy your requirement is putting your DataGridView
control in UserControl
and load data in constructor of UserControl
, this way when you put an instance of your UserControl
on a form, since the designer executes the constructor of your UserControl
then the DataGridView
will be filled with data.
Then if you want to expose Columns
property of DataGridView
you can use this solution.
Example - Just for learning purpose
using System;
using System.Linq;
using System.Windows.Forms;
using System.Data;
using System.Reflection;
using System.IO;
using System.Xml.Linq;
public class MyDataGridView : DataGridView
{
protected override void OnDataSourceChanged(EventArgs e)
{
base.OnDataSourceChanged(e);
TryToPopulateControl();
}
protected override void OnDataMemberChanged(EventArgs e)
{
base.OnDataMemberChanged(e);
TryToPopulateControl();
}
private void TryToPopulateControl()
{
if (!DesignMode)
return;
else
{
try
{
if (this.DataSource is BindingSource)
{
var bs = (BindingSource)this.DataSource;
if (bs.DataSource is DataSet)
{
var ds = bs.DataSource;
var table = bs.DataMember;
if (ds == null || string.IsNullOrEmpty(table))
return;
var name = ds.GetType().FullName + ".xsd";
string result = "";
using (var stream = Assembly.GetExecutingAssembly()
.GetManifestResourceStream(name))
using (StreamReader reader = new StreamReader(stream))
result = reader.ReadToEnd();
var document = XDocument.Parse(result);
var node = document.Descendants()
.Where(x => x.Name.LocalName == "TableAdapter")
.Where(x => x.Attribute("Name").Value == table).FirstOrDefault();
if (node != null)
{
var tableAdapterName = node.Attribute("UserDataComponentName").Value;
var adapterType = Assembly.GetExecutingAssembly()
.GetTypes().Where(x => x.Name == tableAdapterName).FirstOrDefault();
var adapter = Activator.CreateInstance(adapterType);
var fillMethod = adapterType.GetMethod("GetData");
var dataTable = fillMethod.Invoke(adapter, new object[] { }) as DataTable;
foreach (DataRow row in dataTable.Rows)
((DataSet)ds).Tables[table].Rows.Add(row.ItemArray);
}
}
}
}
catch (Exception)
{
//Could not load data
}
}
}
}