Reputation: 1466
I have a mvc razor view that has a model populated like so:
public class HomeController : Controller
{
private IDataSource _db;
public HomeController (IDataSource db)
{
_db = db;
}
public ActionResult Events()
{
var allevents = _db.Events;
ViewBag.Title = "Events";
return View(allevents);
}
}
The event model looks like this:
public class Event
{
public virtual int Id { get; set; }
public virtual string Title { get; set; }
public virtual string Description { get; set; }
public virtual Location Location {get;set;}
public virtual DateTime StartDate {get;set;}
public virtual DateTime EndDate { get; set; }
}
I would like to display the items in my view so that they are grouped by the month name. For example:
October
EventA Title, EventA Description etc.
EventB Title, EventA Description etc.
November
EventC Title, EventC Description etc.
If possible you could take it a step further to break it out by year, then month however not entirely necessary as I don't see a situation where events would be entered more than a year in advance.
I have tried this in my razor view but seem to be slightly off...
@{var monthList = from e in Model
group e by e.StartDate.Month into g
orderby g.Key
select g;
foreach(var monthGroup in monthList)
{
string month = monthGroup.Key.ToString();
<h2 class="h4 pi-weight-700 pi-uppercase pi-has-bg pi-margin-bottom-25">
@month
</h2>
foreach (Model e in monthGroup)
{
// do something with the events
}
}}
Upvotes: 1
Views: 8054
Reputation: 1226
Assuming start date and end date are in the same month I would do something like (in controller):
var groupedEvents = _db.Events.ToList().GroupBy(k => new DateTime(k.StartDate.Year, k.StartDate.Month, 1)).OrderBy(k => k.Key).ToDictionary(k => k.Key, v => v.ToList());
return View(groupedEvents);
Then in the view foreach through the dictionary. You can get the month name by:
@model IDictionary<DateTime, List<Event>>
@foreach(var item in Model)
{
//Display month name
<h1>@item.Key.ToString("MMM", CultureInfo.InvariantCulture);</h1>
foreach(var ev in item.Value)
{
//Row specific code
}
}
Upvotes: 4