Asp.net

在 ASP.NET Core MVC 中嵌套 TagHelper

  • January 11, 2019

ASP.NET Core TagHelper 文件提供了以下範例:

public class WebsiteContext
{
   public Version Version { get; set; }
   public int CopyrightYear { get; set; }
   public bool Approved { get; set; }
   public int TagsToShow { get; set; }
}

[TargetElement("website-information")]
public class WebsiteInformationTagHelper : TagHelper
{
   public WebsiteContext Info { get; set; }

   public override void Process(TagHelperContext context, TagHelperOutput output)
   {
       output.TagName = "section";
       output.Content.SetContent(
           $@"<ul><li><strong>Version:</strong> {Info.Version}</li>
           <li><strong>Copyright Year:</strong> {Info.CopyrightYear}</li>
           <li><strong>Approved:</strong> {Info.Approved}</li>
           <li><strong>Number of tags to show:</strong> {Info.TagsToShow}</li></ul>");
       output.TagMode = TagMode.StartTagAndEndTag;
   }
}

然後可以在 Razor .cshtml 中使用它,如下所示:

<website-information info="new WebsiteContext {
   Version = new Version(1, 3),
   CopyrightYear = 1790,
   Approved = true,
   TagsToShow = 131 }"/>

這將生成以下 HTML:

<section>
   <ul>
       <li><strong>Version:</strong> 1.3</li>
       <li><strong>Copyright Year:</strong> 1790</li>
       <li><strong>Approved:</strong> true</li>
       <li><strong>Number of tags to show:</strong> 131 </li>
   </ul>
</section>

這是非常難看的標籤助手語法。有沒有辦法嵌套另一個標籤助手並獲得完整的智能感知,以便網站資訊的唯一允許的孩子可以是上下文?請參見下面的範例:

<website-information>
   <context version="1.3" copyright="1790" approved tags-to-show="131"/>
</website-information>

在我的案例中,網站資訊元素已經有很多屬性,我想添加一個或多個單獨的嵌套元素。

更新

我在 ASP.NET GitHub 頁面上提出了這個建議,以便為 TagHelpers 實現這個功能。

您當然可以嵌套標籤助手,儘管視圖組件、部分視圖或顯示模板等其他選項可能更適合 OP 描述的場景。

這可能是一個非常簡單的標籤助手:

[HtmlTargetElement("child-tag", ParentTag="parent-tag")]
public class ChildTagHelper : TagHelper
{
   public string Message { get; set; }

   public override void Process(TagHelperContext context, TagHelperOutput output)
   {
       // Create parent div
       output.TagName = "span";
       output.Content.SetContent(Message);
       output.TagMode = TagMode.StartTagAndEndTag;     
   }
}

這也可以是另一個簡單的標籤助手:

[HtmlTargetElement("parent-tag")]
[RestrictChildren("child-tag")]
public class ParentTagHelper: TagHelper
{
   public string Title { get; set; }

   public override async Task ProcessAsync(TagHelperContext context, TagHelperOutput output)
   {            
       output.TagName = "div";

       // Add some specific parent helper html
       var header = new TagBuilder("h1");
       header.Attributes.Add("class", "parent-title");
       header.InnerHtml.Append(this.Title);
       output.PreContent.SetContent(header);

       // Set the inner contents of this helper(Will process any nested tag helpers or any other piece of razor code)
       output.Content.SetContent(await output.GetChildContentAsync());            
   }
}

在剃刀視圖中,您可以編寫以下內容:

<parent-tag title="My Title">
   <child-tag message="This is the nested tag helper" />
</parent-tag>

這將呈現為:

<div>
   <h1 class="parent-title">My Title</h1>
   <span>This is the nested tag helper</span>
</div>

您可以選擇強制標籤助手以特定方式嵌套:

  • 在父標籤助手中使用[RestrictChildren("child-tag", "another-tag")]以限制允許的嵌套標籤助手
  • 在聲明子標籤助手時使用該ParentTag參數以強制標籤嵌套在特定父標籤內[HtmlTargetElement("child-tag", ParentTag = "parent-tag")]

引用自:https://stackoverflow.com/questions/32692857