Razor syntax - how to conditionally wrap some inner HTML

前端 未结 4 1895
滥情空心
滥情空心 2021-02-02 12:42

In Razor, there\'s a curious rule about only allowing closed HTML within an if block.

See:

Razor doesn't understand unclosed ht

4条回答
  •  醉梦人生
    2021-02-02 13:09

    The following code is based on the answer of @JotaBe, but simplified and extendable:

    public static class HtmlHelperExtensions
    {
        public static IDisposable BeginTag(this HtmlHelper htmlHelper, string tagName, bool condition = true, object htmlAttributes = null)
        {
            return condition ? new DisposableTagBuilder(tagName, htmlHelper.ViewContext, htmlAttributes) : null;
        }
    }
    
    public class DisposableTagBuilder : TagBuilder, IDisposable
    {
        protected readonly ViewContext viewContext;
        private bool disposed;
    
        public DisposableTagBuilder(string tagName, ViewContext viewContext, object htmlAttributes = null) : base(tagName)
        {
            this.viewContext = viewContext;
    
            if (htmlAttributes != null)
            {
                this.MergeAttributes(HtmlHelper.AnonymousObjectToHtmlAttributes(htmlAttributes));
            }
    
            this.Begin();
        }
    
        protected virtual void Begin()
        {
            this.viewContext.Writer.Write(this.ToString(TagRenderMode.StartTag));
        }
    
        protected virtual void End()
        {
            this.viewContext.Writer.Write(this.ToString(TagRenderMode.EndTag));
        }
    
        public void Dispose()
        {
            this.Dispose(true);
            GC.SuppressFinalize(this);
        }
    
        protected virtual void Dispose(bool disposing)
        {
            if (!this.disposed)
            {
                this.disposed = true;
    
                this.End();
            }
        }
    }
    

    This can be used the following way within Razor views:

    @using (Html.BeginTag("div"))
    {
        

    This paragraph is rendered within a div

    } @using (Html.BeginTag("div", false)) {

    This paragraph is rendered without the div

    } @using (Html.BeginTag("a", htmlAttributes: new { href = "#", @class = "button" })) { And a lot more is possible! }

提交回复
热议问题