如果要设置网格的数据源,那么……也许……你可以把它扔到网格CellFormating 事件中。但是,应该清楚的是,从长远来看,单元格的格式化次数将超过必要的次数。我认为我们可以做得更好。直到 1) 用户更改 Currency 单元格,或 2) 将新数据加载到网格中,我们才能“格式化”单元格。
第一部分是微不足道的……连接网格CellValueChanged 事件。如果更改的单元格值是Currency 单元格……那么,检查“新”值并相应地格式化Price 单元格。
这在用户更改 Currency 单元格值时有效,但是在加载数据时无效。因此,通过网格行的简单循环应该可以解决该问题。由于我们需要在两个不同的地方设置 Price 单元格格式,我建议创建一个方法,该方法采用 DataGridViewRow 并为给定行格式化“价格”单元格。它可能看起来像……
private void FormatAmountCell(DataGridViewRow row) {
if (!row.IsNewRow && row.Cells["Currency"].Value != null) {
string currency = row.Cells["Currency"].Value.ToString();
DataGridViewCell cellToFormat = row.Cells["Price"];
switch (currency) {
case "EUR":
cellToFormat.Style.FormatProvider = CultureInfo.GetCultureInfo("en-GB");
break;
default:
cellToFormat.Style.FormatProvider = CultureInfo.GetCultureInfo("en-US");
break;
}
}
}
有了这个帮助器,我们就可以在连接CellValueChanged 事件的网格中使用它。
private void dataGridView1_CellValueChanged(object sender, DataGridViewCellEventArgs e) {
FormatAmountCell(dataGridView1.Rows[e.RowIndex]);
}
此外,还有一个小方法可以遍历网格行并设置每个“价格”单元格格式。我们将在数据加载到网格后调用它。
private void FormatAmountCellForAllRows() {
foreach (DataGridViewRow row in dataGridView1.Rows) {
FormatAmountCell(row);
}
}
将所有这些放在一起进行测试可能看起来像……
DataTable GridTable;
public Form1() {
InitializeComponent();
}
private void Form1_Load(object sender, EventArgs e) {
dataGridView1.CellValueChanged += new DataGridViewCellEventHandler(dataGridView1_CellValueChanged);
GridTable = GetData();
dataGridView1.DataSource = GridTable;
dataGridView1.Columns["Price"].DefaultCellStyle.Format = "c";
FormatAmountCellForAllRows();
}
private DataTable GetData() {
DataTable dt = new DataTable();
dt.Columns.Add("Price", typeof(decimal));
dt.Columns.Add("Currency", typeof(string));
Random rand = new Random();
for (int i = 0; i < 10; i++) {
dt.Rows.Add(rand.NextDouble() * 100, (rand.Next(2) == 0 ? "USD" : "EUR"));
}
return dt;
}
现在您可以安心地睡觉了,因为您知道格式化永远不会不必要地进行。