In Play/Scala; I am confused as to why this won't compile:
@(tabNames: Seq[String])
@isActive(idx: Int) = {
@if(idx < 1) {
"active"
} else {
""
}
}
<ul class="nav nav-tabs">
@for((tab, idx) <- tabNames.zipWithIndex) {
@views.html.generic.navLi("tab" + idx.toString, tab, isActive(idx))
}
</ul>
The error reads:
found : play.twirl.api.HtmlFormat.Appendable [error] (which expands to) play.twirl.api.Html [error] required: String [error]
@views.html.generic.navLi("tab" + idx.toString, tab, isActive(idx))
It doesn't recognise the call to isActive within the call to the template and I have tried multiple variations, e.g. @isActive(idx), isActive(@idx) ${isActive(idx)} (as suggested here), etc. This template generates a navigation bar, passing in tab names and checking to see if the nav li should be active (configured by class name/JS).
It just seems that the syntax must be different when calling a function within another template call - I can't get it right.
The Play documentation is a little light in this area; while it is certainly possible and useful to declare "functions" in a twirl template, the return type seems to be locked to (effectively)
Html- i.e. your "block" (as it is referred to in the documentation) must render HTML.The quickest solution, as suggested in the documentation, is to relocate the logic into a Scala class; for something as simple as this, an
objectis the easiest way to get this done, i.e.:and:
The advantages of this approach include testability and reusability. Just be careful to avoid getting carried away with what a
ViewHelpercan do - database lookups etc are a bad idea here! :-)