Loading...
Area: Optimizely CMS
Applies to versions: 12 and higher
Other versions:

Preview rendering for blocks

Recommended reading 
Note: This documentation is for the preview version of the upcoming release of CMS 12/Commerce 14/Search & Navigation 14. Features included here might not be complete, and might be changed before becoming available in the public release. This documentation is provided for evaluation purposes only.

This topic describes how to create a view and controller for previewing blocks in Optimizely. The preview adds on-page editing functionality, and a realistic view of what the block will look like when added to content areas with different widths.

How it works

Shared blocks are rendered in the context of a page, such as inside a content area. Like pages, you can edit blocks in the All Properties view, but to preview and edit block in the On-Page Editing view, you can create a preview page used to render blocks in edit view. A block template is typically a partial template like a view component, or a partial view. The rendering is using the built-in Preview tag in the EPiServer.Framework.Web namespace.

Creating a block preview template

The following example creates these components to build a preview that you can use for all blocks:

  • A block preview model
  • A preview controller
  • A preview view

See Page types and templates, and Block types and templates, for information on how to create page types, controllers and views.

Block preview model

Example: The block preview model with a content area. Note: The PageViewModel is a pattern from the Alloy sample site and is not required if the site is not based on Alloy.

namespace AlloyTemplates.Models.ViewModels
{
  public class PreviewModel : PageViewModel<SitePageData>
  {
    public PreviewModel(SitePageData currentPage, IContent previewContent)
    : base(currentPage)
    {
      PreviewContentArea = new ContentArea();
      PreviewContentArea.Items.Add(new ContentAreaItem
      {
        ContentLink = previewContent.ContentLink
      });
    }

    public ContentArea PreviewContentArea { get; set; }
  }
}

Preview controller

PreviewController inherits from the ActionControllerBase and implements IRenderTemplate<BlockData>, letting the controller render block types. The Index method is overridden and gets the start page as rendering context. A new instance of the PreviewModel is created, and the block is programmatically added to the content area. The controller has a TemplateDescriptor "Preview" tag, ensuring that it is only used for on-page editing.

Example: The preview controller. 

namespace AlloyTemplates.Controllers
{
  [TemplateDescriptor(
    Inherited = true,
    TemplateTypeCategory = TemplateTypeCategories.MvcController, //Required as controllers for blocks are registered as MvcPartialController by default
    Tags = new[] { RenderingTags.Preview, RenderingTags.Edit },
    AvailableWithoutTag = false)]
  [VisitorGroupImpersonation]
  [RequireClientResources]
  public class PreviewController : ActionControllerBase, IRenderTemplate<BlockData>, IModifyLayout
  {
    private readonly IContentLoader _contentLoader;

    public PreviewController(IContentLoader contentLoader)
    {
      _contentLoader = contentLoader;
    }

    public IActionResult Index(IContent currentContent)
    {
      //As the layout requires a page for title etc we "borrow" the start page
      var startPage = _contentLoader.Get<StartPage>(SiteDefinition.Current.StartPage);
      var model = new PreviewModel(startPage, currentContent);

      return View(model);
    }

    public void ModifyLayout(LayoutModel layoutModel)
    {
      layoutModel.HideHeader = true;
      layoutModel.HideFooter = true;
    }
  }
}

Preview view

Example: View for rendering the block in different widths depending on context.

@model PreviewModel

<div class="row">
  <div class="span12">
    @Html.PropertyFor(m => m.PreviewContentArea)
  </div>
</div>

<div class="row">
  <div class="span8">
    @Html.PropertyFor(m => m.PreviewContentArea)
  </div>
</div>

<div class="row">
  <div class="span4">
    @Html.PropertyFor(m => m.PreviewContentArea)
  </div>
</div>

The resulting outcome when editing and previewing a block in edit view.

Related topics

Do you find this information helpful? Please log in to provide feedback.

Last updated: Jul 02, 2021

Recommended reading