What I want to achieve is to dynamically change the color of the row of datagridview
based on a condition that is mentioned in the code below which means if the Expiry Date is greater than the current date which means its expired then the Row changed its color to red
And if 30 days remain in Expiration than turn yellow
private void ViewMedicine_DataGrid_CellFormatting(object sender, DataGridViewCellFormattingEventArgs e)
{
if (Dont know what to write here)
{
foreach (DataGridViewRow row in ViewMedicine_DataGrid.Rows)
{
row.DefaultCellStyle.BackColor = Color.Red;
row.DefaultCellStyle.ForeColor = Color.White;
}
}
}
CodePudding user response:
In order to achieve what you're looking for, you could use two nested for
, one to loop your results from the query (DataTable MrkExp), one to loop the values contained in your dataGridView
.
Assuming both of your database's table and dataGridView have one Unique ID or field, you could check if they're equal.
To achieve that:
for (int i = 0; i < ViewMedicine_DataGrid.Rows.Count; i )
{
for (int j = 0; j < MrkExp.Rows.Count; j )
{
if (ViewMedicine_DataGrid.Rows[i].Cells[0].Value != null)
{
if (ViewMedicine_DataGrid.Rows[i].Cells[0].Value == MrkExp.Rows[j]["UNIQUE_FIELD"])
{
ViewMedicine_DataGrid.Rows[i].DefaultCellStyle.BackColor = Color.Red;
ViewMedicine_DataGrid.Rows[i].DefaultCellStyle.ForeColor = Color.White;
}
}
}
}
If you haven't got a unique field or primary, consider updating your question showing your table's structure.
CodePudding user response:
Finally, after a little brainstorming into the code and research a bit I got successful in getting the desired result. Here's what I code to made it possible using a RowPrePaint
Event
private void ViewMedicine_DataGrid_RowPrePaint(object sender, DataGridViewRowPrePaintEventArgs e)
{
var ExpiryDate = Convert.ToDateTime(ViewMedicine_DataGrid.Rows[e.RowIndex].Cells[7].Value);
var TodayDate = DateTime.Today;
var Expired = ExpiryDate >= TodayDate;
var ExpiredToBe = ExpiryDate >= TodayDate.AddDays(-30);
if (Expired)
{
ViewMedicine_DataGrid.Rows[e.RowIndex].DefaultCellStyle.BackColor = Color.Red;
}
else if (ExpiredToBe)
{
ViewMedicine_DataGrid.Rows[e.RowIndex].DefaultCellStyle.BackColor = Color.Yellow;
}
}
Before I was using a CellFormatting
event which was wrong and Created a RowPrePaint
Event and before if
statements declared variables to be used in if
Statement and the code I used shows the rest. It works like a charm
CodePudding user response:
My advice would be to use the event DataGridViewCell.CellFormatting for this. It is called, whenever cell [x, y] needs to be formatted.
Use DataBinding to easily access the data in your rows
I don't know what kind of items you show in your DataGridView, let's assume it's a collection of price offers. Each price offer has an expiry date:
class PriceOffer
{
public DateTime ExpiryDate {get; set;}
...
}
Somewhere you tell which columns of the PriceOffer needs to be shown. Probably in the constructor:
InitializeComponent();
this.ColumnStartDate.DataPropertyName = nameof(PriceOffer.StartDate);
this.ColumnExpiryDate.DataPropertyName = nameof(PriceOffer.ExpiryDate);
this.ColumnPrice.DataPropertyName = nameof(PriceOffer.Price);
...
You also have a property to get your initial collection of PriceOffers:
IEnumerable<PriceOffer> FetchPriceOffersToDisplay(...)
{
return ...
}
And of course a property to attach these PriceOffers to the DataGridView
BindingList<PriceOffer> DisplayedPriceOffers
{
get => return (BindingList<PriceOffer>)this.dataGridView1.DataSource;
set => this.dataGridView1.DataSource = value;
}
Initialize when the form is loaded
void OnFormLoad(object sender, ...)
{
this.DisplayedPriceOffers = new BindingList<PriceOffer>(
this.FetchPriceOffersToDisplay().ToList());
}
All changes that the operator makes: add / remove / edit PriceOffers are automatically updated in this.DisplayedPriceOffers
.
Back to your question
private void dataGridView1_CellFormatting(object sender,
DataGridViewCellFormattingEventArgs e)
{
DataGridViewRow row = this.dataGridView1.Rows[e.RowIndex];
PriceOffer priceOffer = (PriceOffer)row.DataboundItem;
if (DateTime.Today > priceOffer.ExpiryDate)
{
this.ColorRowExpired(row);
}
else
{
this.ColorRowNotExpired(row);
}
}
void ColorRowExpired(DataGridViewRow row)
{
foreach (DataGridViewCell cell in row.Cells)
{
cell.BackColor = ExpiredCellBackColor;
...
}
}