MVC DropDownList look and feel
Asked Answered
A

1

1

So I'm creating a site using MVC, and my DropDownLists and DropDownListFors do not look the same as the other input elements on the page. I tried setting their class to be the same "form-control", and even tried adding my own class in the css that has pretty much the same properties called "mydropdown" and using that - neither had an effect.

So I found this very handy thread answered by Joseph Woodward that I just tried....

I'm using VB instead of C# so I had to translate it. This is my translated BootstrapHtml:

Public Class BootstrapHtml

    Public Function Dropdown(id As String, selectListItems As List(Of SelectListItem), label As String) As MvcHtmlString

        Dim button = New TagBuilder("button")
        button.Attributes.Add("id", id)
        button.Attributes.Add("type", "button")
        button.Attributes.Add("data-toggle", "dropdown")

        button.AddCssClass("btn")
        button.AddCssClass("btn-default")
        button.AddCssClass("dropdown-toggle")

        button.SetInnerText(label)
        button.InnerHtml += " " + BuildCaret()

        Dim wrapper = New TagBuilder("div")
        wrapper.AddCssClass("dropdown")
        wrapper.InnerHtml += button.ToString
        wrapper.InnerHtml += BuildDropdown(id, selectListItems)

        Return New MvcHtmlString(wrapper.ToString)

    End Function

    Private Function BuildCaret() As String

        Dim caret = New TagBuilder("span")
        caret.AddCssClass("caret")

        Return caret.ToString

    End Function

    Private Function BuildDropdown(id As String, items As IEnumerable(Of SelectListItem)) As String

        Dim list = New TagBuilder("ul")
        list.Attributes.Add("class", "dropdown-menu")
        list.Attributes.Add("role", "menu")
        list.Attributes.Add("aria-labelledby", id)

        Dim listItem = New TagBuilder("li")
        listItem.Attributes.Add("role", "presentation")

        For Each x In items
            list.InnerHtml += "<li role=\presentation\>" & BuildListRow(x) & "</li>"
        Next

        Return list.ToString

    End Function

    Private Function BuildListRow(item As SelectListItem) As String

        Dim anchor = New TagBuilder("a")
        anchor.Attributes.Add("role", "menuitem")
        anchor.Attributes.Add("tabindex", "-1")
        anchor.Attributes.Add("href", item.Value)

        anchor.SetInnerText(item.Text)
        Return anchor.ToString

    End Function

End Class

The one thing I'm not sure I got right was the string concatenation in the For Each loop....

In any case, in my view I tried using

@BootstrapHtml.Dropdown("typecombo", TypeList, "Dropdown")

but it gave me a code error:

Reference to a non-shared member requires an object reference.

So I added a declaration in the code section at the top:

Dim newDropDown As BootstrapHtml = New BootstrapHtml

And my line in the view now looks like this:

@newDropDown = BootstrapHtml.Dropdown("typecombo", TypeList, "Dropdown")

So now my site runs with no errors, however when I go to this page, instead of a dropdown list I am seeing the string, which is this:

[myproject].BootstrapHtml = BootstrapHtml.Dropdown("typecombo", TypeList, "Dropdown")

So, I guess first off is the string translation in my class correct (as mentioned above)? And if it is, why am I seeing the string on my page instead of an actual drop down?

Thank you!!

Adulterer answered 24/12, 2016 at 22:37 Comment(0)
B
4

Based on linked post the Dropdown method should be static. which in Vb.Net is Shared keyword ie

Public Class BootstrapHtml

    Public Shared Function Dropdown(id As String, selectListItems As List(Of SelectListItem), label As String) As MvcHtmlString
        '''other code removed for brevity
    End Function

End Class

Actually, all the functions in that class should be shared. That is what caused the reference error you mentioned.

With that you should then be able to call it like in the example.

@BootstrapHtml.Dropdown("typecombo", TypeList, "Dropdown")
Bein answered 24/12, 2016 at 23:23 Comment(2)
+1. A slight note however. Keyword is Shared for VB.NET not Static. Or the Class could be made into a Module if all methods are static. This could prove useful.Skeptic
Good to know that 'Static' in C# is 'Shared' in VB - thanks, @Jinx88909!Adulterer

© 2022 - 2024 — McMap. All rights reserved.