13

I am generating HTML textbox through the html helper and TagBuilder.

we have the method TagBuilder.Attributes.Add("key","value")

but for HTML5 required attribute does not need value to be passed, so if i pass empty string then the output with value of required = ""

So how do i add required attribute without passing the value?

 public static IHtmlString AppTextBox(this HtmlHelper helper, string model)
    {
        var input = new TagBuilder("input");
        input.Attributes.Add("class", "form-control");
        input.Attributes.Add("ng-model", model);

        input.Attributes.Add("required","");

        return new MvcHtmlString(input.ToString(TagRenderMode.Normal));
    }
Erik Philips
  • 53,428
  • 11
  • 128
  • 150
Srini
  • 708
  • 1
  • 8
  • 23

3 Answers3

13

It's also valid to pass the name of the attribute as the value:

input.Attributes.Add("required", "required");
Henk Mollema
  • 44,194
  • 12
  • 93
  • 104
5

I've tested on MVC 5, not sure about older versions but the following does what you want.

tagBuilder.MergeAttribute("required", string.Empty);
benembery
  • 666
  • 7
  • 20
  • Might be a bit nit-picking but this results in `` not `` So yes, it works, but I'd still like to be able to add the plain attribute with no value. – René Sackers Oct 15 '21 at 08:18
0

Not sure if you still need an answer to this, but in the end I ended up writing a new class that derives from the base MVC tag builder. It's nothing too complex and I suspect there may be a few edge cases that this doesn't handle too well, but from the unit tests I have so far, it's pretty solid.

internal class ValuelessAttributeTagBuilder : System.Web.Mvc.TagBuilder
{
    public List<string> ValuelessAttributes { get; private set; } 

    public ValuelessAttributeTagBuilder(string tagName) : base(tagName)
    {
        ValuelessAttributes = new List<string>();
    }

    public void AddValuelessAttribute(string value)
    {
        if(ValuelessAttributes.Contains(value))
            ValuelessAttributes.Add(value);
    }

    /// <summary>
    /// Renders the HTML tag by using the specified render mode.
    /// </summary>
    /// 
    /// <returns>
    /// The rendered HTML tag.
    /// </returns>
    /// <param name="renderMode">The render mode.</param>
    public string ToString(TagRenderMode renderMode)
    {
        var sb = new StringBuilder();
        switch (renderMode)
        {
            case TagRenderMode.StartTag:
                sb.Append('<').Append(this.TagName);
                AppendAttributes(sb);
                AppendValuelessAttributes(sb);
                sb.Append('>');
                break;
            case TagRenderMode.EndTag:
                sb.Append("</").Append(this.TagName).Append('>');
                break;
            case TagRenderMode.SelfClosing:
                sb.Append('<').Append(this.TagName);
                AppendAttributes(sb);
                AppendValuelessAttributes(sb);
                sb.Append(" />");
                break;
            default:
                sb.Append('<').Append(this.TagName);
                AppendAttributes(sb);
                AppendValuelessAttributes(sb);
                sb.Append('>').Append(this.InnerHtml).Append("</").Append(this.TagName).Append('>');
                break;
        }
        return sb.ToString();
    }

    private void AppendAttributes(StringBuilder sb)
    {
        foreach (KeyValuePair<string, string> keyValuePair in (IEnumerable<KeyValuePair<string, string>>)this.Attributes)
        {
            string key = keyValuePair.Key;
            if (!string.Equals(key, "id", StringComparison.Ordinal) || !string.IsNullOrEmpty(keyValuePair.Value))
            {
                string str = HttpUtility.HtmlAttributeEncode(keyValuePair.Value);
                sb.Append(' ').Append(key).Append("=\"").Append(str).Append('"');
            }
        }
    }

    private void AppendValuelessAttributes(StringBuilder sb)
    {
        foreach (var v in ValuelessAttributes)
        {
            var str = HttpUtility.HtmlAttributeEncode(v);
            sb.Append(' ').Append(str);
        }
    }
}
Jak Hammond
  • 1,460
  • 3
  • 11
  • 24