From 1c5daae7377b91d45c58251c5361d271c067bad6 Mon Sep 17 00:00:00 2001 From: loudej Date: Wed, 16 Dec 2009 22:35:25 +0000 Subject: [PATCH] Filling out zone rendering implementations --HG-- extra : convert_revision : svn%3A5ff7c347-ad56-4c35-b696-ccb81de16e03/trunk%4044186 --- src/Orchard/Mvc/Html/LayoutExtensions.cs | 3 +- src/Orchard/UI/Zones/ZoneCollection.cs | 26 +++++++++++++ src/Orchard/UI/Zones/ZoneManager.cs | 47 +++++++++++++++++++++--- 3 files changed, 69 insertions(+), 7 deletions(-) diff --git a/src/Orchard/Mvc/Html/LayoutExtensions.cs b/src/Orchard/Mvc/Html/LayoutExtensions.cs index 1016bd857..937d960d8 100644 --- a/src/Orchard/Mvc/Html/LayoutExtensions.cs +++ b/src/Orchard/Mvc/Html/LayoutExtensions.cs @@ -27,7 +27,7 @@ namespace Orchard.Mvc.Html { } public static void Zone(this HtmlHelper html, string zoneName, string partitions) where TModel : BaseViewModel { - //is IoC necessary for this to work properly? + //TODO: is IoC necessary for this to work properly? var manager = new ZoneManager(); manager.Render(html, html.ViewData.Model.Zones, zoneName, partitions); } @@ -37,6 +37,7 @@ namespace Orchard.Mvc.Html { } public static void Zone(this HtmlHelper html, string zoneName, Action action) where TModel : BaseViewModel { + //TODO: again, IoC could move this AddAction (or similar) method out of the data-bearing object html.ViewData.Model.Zones.AddAction(zoneName, x => action()); Zone(html, zoneName, string.Empty); } diff --git a/src/Orchard/UI/Zones/ZoneCollection.cs b/src/Orchard/UI/Zones/ZoneCollection.cs index a2b576309..644c9248b 100644 --- a/src/Orchard/UI/Zones/ZoneCollection.cs +++ b/src/Orchard/UI/Zones/ZoneCollection.cs @@ -12,6 +12,32 @@ namespace Orchard.UI.Zones { } public void AddAction(string location, Action action) { + AddZoneItem(location, new DelegateZoneItem { Action = action }); + } + + private void AddZoneItem(string location, ZoneItem item) { + string zoneName; + var position = string.Empty; + + var colonIndex = location.IndexOf(':'); + if (colonIndex == -1) { + zoneName = location.Trim(); + } + else { + zoneName = location.Substring(0, colonIndex).Trim(); + position = location.Substring(colonIndex + 1).Trim(); + } + + item.Position = position; + ZoneEntry entry; + if (TryGetValue(zoneName, out entry)) { + entry.Items.Add(item); + } + else { + entry = new ZoneEntry { ZoneName = zoneName, Items = new List() }; + Add(zoneName, entry); + entry.Items.Add(item); + } } } diff --git a/src/Orchard/UI/Zones/ZoneManager.cs b/src/Orchard/UI/Zones/ZoneManager.cs index 0a31b4714..42528ceb7 100644 --- a/src/Orchard/UI/Zones/ZoneManager.cs +++ b/src/Orchard/UI/Zones/ZoneManager.cs @@ -12,14 +12,49 @@ namespace Orchard.UI.Zones { if (!zones.TryGetValue(zoneName, out zone)) return; - //TODO: partitions - foreach (var item in zone.Items) { - if (item.WasExecuted) - continue; + var partitionItems = LocatePartitionItems(partitions, zone); + + foreach (var partitionItem in partitionItems) { + foreach (var item in zone.Items) { + if (item.WasExecuted) + continue; + + item.WasExecuted = true; + item.Execute(html); + } - item.WasExecuted = true; - item.Execute(html); } } + + private IEnumerable LocatePartitionItems(string partitions, ZoneEntry zone) { + + var partitionCodes = (":before " + partitions + " :* :after").Split(new[] { ' ' }, StringSplitOptions.RemoveEmptyEntries); + + var itemsRemaining = zone.Items.Where(x => x.WasExecuted == false); + + PartitionItem catchAllItem = null; + + var results = new List(); + foreach (var code in partitionCodes) { + if (code == ":*") { + catchAllItem=new PartitionItem(); + results.Add(catchAllItem); + } + else { + var value = code; + var items = itemsRemaining.Where(x => (":" + x.Position).StartsWith(value)); + results.Add(new PartitionItem { ZoneItems = items.ToArray() }); + itemsRemaining = itemsRemaining.Except(items).ToArray(); + } + } + if (catchAllItem != null) { + catchAllItem.ZoneItems = itemsRemaining; + } + return results; + } + + class PartitionItem { + public IEnumerable ZoneItems { get; set; } + } } }