Skip to content

Instantly share code, notes, and snippets.

@MattisOlsson
Last active July 12, 2016 18:34
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save MattisOlsson/4e617c1486f192550d37e1b8326bc14f to your computer and use it in GitHub Desktop.
Save MattisOlsson/4e617c1486f192550d37e1b8326bc14f to your computer and use it in GitHub Desktop.
[ServiceConfiguration(typeof(ContentAreaRenderer), Lifecycle = ServiceInstanceScope.Singleton)]
public class ContainerAndRowContentAreaRenderer : ContentAreaRenderer
{
// Number of columns in site grid
protected const int NumberOfGridColumns = 12;
// TagBuilder for the current container div.
protected TagBuilder CurrentContainer;
// TagBuilder for the current row div.
protected TagBuilder CurrentRow;
// To keep track of the current container.
protected bool IsContainerOpen;
// To keep track of the current row.
protected bool IsRowOpen;
// Current column counter for each row
protected int CurrentColumn;
public ContainerAndRowContentAreaRenderer(IContentRenderer contentRenderer, TemplateResolver templateResolver, ContentFragmentAttributeAssembler attributeAssembler, IContentRepository contentRepository, IContentAreaLoader contentAreaLoader) : base(contentRenderer, templateResolver, attributeAssembler, contentRepository, contentAreaLoader)
{
}
protected virtual string GetContentAreaItemCssClass(HtmlHelper html, ContentAreaItem contentAreaItem, string templateTag)
{
var baseClass = base.GetContentAreaItemCssClass(html, contentAreaItem);
// Allow developer to override by passing ChildrenCssClass in ViewData.
if (string.IsNullOrEmpty(baseClass) == false)
{
return baseClass;
}
return string.Format("block {0}", GetDisplayOptionCssClass(templateTag));
}
protected override string GetContentAreaItemTemplateTag(HtmlHelper html, ContentAreaItem contentAreaItem)
{
var templateTag = base.GetContentAreaItemTemplateTag(html, contentAreaItem);
if (string.IsNullOrWhiteSpace(templateTag))
{
// Default to full width.
return SiteDisplayOptions.FullWidth;
}
return templateTag;
}
protected virtual string GetDisplayOptionCssClass(string templateTag)
{
switch (templateTag)
{
case SiteDisplayOptions.FullWidth:
return "full";
case SiteDisplayOptions.TwoThirdsWidth:
return "two-thirds";
case SiteDisplayOptions.HalfWidth:
return "one-half";
case SiteDisplayOptions.OneThirdWidth:
return "one-third";
case SiteDisplayOptions.Hero:
return "hero";
default:
return templateTag;
}
}
protected virtual int GetNumberOfGridColumns(string templateTag)
{
switch (templateTag)
{
case SiteDisplayOptions.TwoThirdsWidth:
return 8;
case SiteDisplayOptions.HalfWidth:
return 6;
case SiteDisplayOptions.OneThirdWidth:
return 4;
default:
return 12;
}
}
protected override void RenderContentAreaItems(HtmlHelper html, IEnumerable<ContentAreaItem> contentAreaItems)
{
CurrentColumn = 0;
IsContainerOpen = false;
IsRowOpen = false;
foreach (ContentAreaItem contentAreaItem in contentAreaItems)
{
string templateTag = this.GetContentAreaItemTemplateTag(html, contentAreaItem);
bool isHeroContentAreaItem = this.IsHeroTag(templateTag);
if (isHeroContentAreaItem)
this.BeforeRenderHeroContentAreaItem(html, contentAreaItem);
else
this.BeforeRenderNormalContentAreaItem(html, contentAreaItem, templateTag);
using (html.BeginRenderingTag(templateTag))
{
this.RenderContentAreaItem(html, contentAreaItem, templateTag, this.GetContentAreaItemHtmlTag(html, contentAreaItem), this.GetContentAreaItemCssClass(html, contentAreaItem, templateTag));
}
}
// Close last row if open.
if (IsRowOpen)
EndRow(html);
// Close last container if open.
if (IsContainerOpen)
EndContainer(html);
}
protected virtual void BeforeRenderHeroContentAreaItem(HtmlHelper html, ContentAreaItem contentAreaItem)
{
// Make sure to close row and container if open. We don't want to wrap hero blocks.
if (IsRowOpen)
EndRow(html);
if (IsContainerOpen)
EndContainer(html);
}
protected virtual void BeforeRenderNormalContentAreaItem(HtmlHelper html, ContentAreaItem contentAreaItem, string templateTag)
{
int itemColumns = this.GetNumberOfGridColumns(templateTag);
CurrentColumn += itemColumns;
bool fitsInRow = CurrentColumn <= NumberOfGridColumns;
// Open container if not already open.
if (IsContainerOpen == false)
StartContainer(html);
if (fitsInRow == false || IsRowOpen == false)
{
// Make sure to close row if open.
if (IsRowOpen)
EndRow(html);
// Start on a new row.
StartRow(html);
// Set current column
CurrentColumn = itemColumns;
}
}
protected virtual void StartContainer(HtmlHelper html)
{
CurrentContainer = new TagBuilder("div");
CurrentContainer.AddCssClass("container");
html.ViewContext.Writer.Write(CurrentContainer.ToString(TagRenderMode.StartTag));
IsContainerOpen = true;
}
protected virtual void EndContainer(HtmlHelper html)
{
html.ViewContext.Writer.Write(CurrentContainer.ToString(TagRenderMode.EndTag));
IsContainerOpen = false;
}
protected virtual void StartRow(HtmlHelper html)
{
CurrentRow = new TagBuilder("div");
CurrentRow.AddCssClass("row");
html.ViewContext.Writer.Write(CurrentRow.ToString(TagRenderMode.StartTag));
IsRowOpen = true;
}
protected virtual void EndRow(HtmlHelper html)
{
html.ViewContext.Writer.Write(CurrentRow.ToString(TagRenderMode.EndTag));
IsRowOpen = false;
}
protected virtual bool IsHeroTag(string templateTag)
{
return templateTag == SiteDisplayOptions.Hero;
}
}
public static class SiteDisplayOptions
{
public const string Hero = "Hero";
public const string FullWidth = "FullWidth";
public const string TwoThirdsWidth = "TwoThirdsWidth";
public const string HalfWidth = "HalfWidth";
public const string OneThirdWidth = "OneThirdWidth";
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment