@functions @helpers
Большинство хелперов в asp.net mvc 3 это методы-расширения класса System.Web.Mvc.HtmlHelper.
Однако не всегда удобно создавать отдельный статический класс для 2-3 хелперов необходимых в одной вьюшке. И совсем неудобно создавать хелперы возвращающие большие блоки html-кода: ни подсветки синтаксиса, ни интеллисенса, ни прочих плюшек.
Для решения этих проблем в Razor есть два замечательных блока. Они позволяют создавать хелперы непосредственно в .cshtml-файлах.
Блок @functions
Razor-страничка это класс, наследуемый от System.Web.Mvc.WebViewPage<TModel>. Обычно используется только его метод void Execute(), который и генерирует html-код
Блок @functions позволяет добавить свои методы, свойства, поля и т.д.
@functions
{
string HelloWorld()
{
return "Hello world";
}
string Now
{
get { return DateTime.Now.ToString("dd MMMM"); }
}
class SomeClass
{
...
}
}
Такой подход может сильно упросить код. Допустим у нас есть некий enum:
enum State
{
Created,
ProcessingStage1,
ProcessingStage2,
Accepted,
Rejected
}
и в зависимости от статуса нам нужны разные картинки и цвет рамки:
@functions
{
enum State
{
Created,
ProcessingStage1,
ProcessingStage2,
Accepted,
Rejected
}
string GetStateImg(State state)
{
switch (state)
{
case State.Created:
return "created.png";
case State.ProcessingStage1:
case State.ProcessingStage2:
return "processing.png";
case State.Accepted:
return "accepted.png";
case State.Rejected:
return "rejected.png";
default:
return "";
}
}
string GetStateBorderColor(State state)
{
switch (state)
{
case State.Accepted:
return "green";
case State.Rejected:
return "red";
default:
return "yellow";
}
}
public static int SomeFunc(int a, int b)
{
return a + b;
}
}
в результате получает возможность делать так:
<div class="border @(GetStateBorderColor(State.Accepted))">
<img src="~/images/@(GetStateImg(State.Accepted))" />
...
</div>
Разумеется, методы GetStateImg и GetStateBorderColor можно было вынести куда-то в .cs код в какой-то хелпер-класс, но куда логичнее держать хелперы необходимые только одной вьюшке в этой же вьюшке.
Блок @helpers
У блока @functions есть небольшой недостаток: подразумеваются, что этот блок должен содержать обычные функции/свойства класса и, как следствие, нельзя вставлять html в тело функции пользуясь всеми радостями Razor.
Для этой задачи используется блок @helpers.
объявляем хелпер:
@helper Email(string address, string name = null)
{
<a href="mailto:@(address)">@(name ?? address)</a>
}
и используем
@Email("google@gmail.ru")
И самое замечательное
можно собрать часто используемые хелперы и функции в один .cshtml-файл, назвать его, к примеру, Helpers.cshtml, положить его в AppCode и тогда в любой вьюшке можно написать так:
@Helpers.Email("some state")
P.S разумеется, методы должны быть public и static, чтобы можно было использовать их из других классов