読者です 読者をやめる 読者になる 読者になる

ASP.NET MVC - input要素のplaceholder属性に使うHtmlHelperの拡張メソッドを作ってみた

気持ち今さら感はありますが、input要素のplaceholder属性にテキストを出力するためのHtmlHelperの拡張メソッドを作ってみました。正直なところやってみて作りました!というほどではなかったんですが、まあ試してみたかったんです、ということで。

モデルのプロパティに対する表示名は、DisplayAttributeのNameプロパティとDisplayNameForメソッドを使えばいい感じに出力できます。そんなノリでできないかなと思って調べてみたところ、DisplayAttributeのPromtプロパティがそれっぽいかな?使っていいかな?と。MVCのソースも調べてみるとこのプロパティの値はModelMetadataのWatermarkプロパティから取得できそうかなと。

ということで作ってみた拡張メソッドがこちらです。

public static class PlaceholderExtesions {
    // placeholder属性用の文字列を取得
    public static MvcHtmlString PlaceholderFor<TModel, TValue>(
        this HtmlHelper<TModel> htmlHelper,
        Expression<Func<TModel, TValue>> expression) {

        // モデルのメタデータを取得
        var metadata = ModelMetadata.FromLambdaExpression(expression, htmlHelper.ViewData);

        // メタデータのウォーターマークを使う
        // html属性として使うと想定してエンコード
        return new MvcHtmlString(HttpUtility.HtmlAttributeEncode(metadata.Watermark));
    }
}

それでは使ってみます。まずはモデルを用意します。

// モデル
public class TestFormModel {
    // Promptにplaceholder属性に出力したい文字列を指定
    [Display(Name = "メールアドレス", Prompt = "メールアドレスを入力してください")]
    public string Mail { get; set; }
}

作ったHtmlHelperの拡張メソッドはこんな感じで使います。長いので適当に改行しています。

<input type="text"
    name="@Html.NameFor(model => model.Mail)"
    value="@Html.ValueFor(model => model.Mail)"
    placeholder="@Html.PlaceholderFor(model => model.Mail)" />

するとこんなhtmlが出力されると。

<input type="text" name="Mail" value="" placeholder="メールアドレスを入力してください" />

いい感じ。