Bootstrap 5 MultiSelect component for ASP.NET Core with TagHelper and HtmlHelper support. Includes embedded CSS/JS files, localization support (6 languages), pagination functionality, and comprehensive form validation integration.
$ dotnet add package BootstrapMultiSelect.MVCA .NET Core MVC library providing TagHelper and HtmlHelper extensions for the Bootstrap MultiSelect jQuery plugin.
Install the package via NuGet:
dotnet add package BootstrapMultiSelect.MVC
Or via Package Manager Console:
Install-Package BootstrapMultiSelect.MVC
After installation, all CSS and JavaScript files are automatically available via ASP.NET Core's Static Web Assets feature.
Important: Files are NOT physically copied to your wwwroot folder. They are:
~/lib/bootstrap-multiselect/ URLsThis is the same behavior as Bootstrap, jQuery, and other standard NuGet packages.
Simply add the script and style references in your _Layout.cshtml:
<!DOCTYPE html>
<html>
<head>
<!-- Bootstrap MultiSelect CSS -->
<link rel="stylesheet" href="~/lib/bootstrap-multiselect/css/bootstrap-multiselect.min.css" />
</head>
<body>
<!-- Your content -->
<!-- Required: jQuery and Bootstrap -->
<script src="~/lib/jquery/dist/jquery.min.js"></script>
<script src="~/lib/bootstrap/dist/js/bootstrap.bundle.min.js"></script>
<!-- Bootstrap MultiSelect JS -->
<script src="~/lib/bootstrap-multiselect/js/bootstrap-multiselect.min.js"></script>
<!-- Optional: Language file -->
<script src="~/lib/bootstrap-multiselect/langs/jquery-bootstrap-multiselect.it.min.js"></script>
</body>
</html>
That's it! The files are available immediately - no build required, no manual copying needed.
Files not found (404)?
dotnet list packageapp.UseStaticFiles() is in your Program.cs~/lib/bootstrap-multiselect/...Note: You will NOT see a wwwroot/lib/bootstrap-multiselect folder in your project - this is normal and correct!
The library supports multiple languages through lang files. Available languages:
To set a language globally for all multiselect instances, you must use the lang property:
<!-- Load plugin -->
<script src="~/lib/bootstrap-multiselect/js/bootstrap-multiselect.min.js"></script>
<!-- Load Italian translations (optional but recommended) -->
<script src="~/lib/bootstrap-multiselect/langs/jquery-bootstrap-multiselect.it.min.js"></script>
<!-- Set Italian as global default -->
<script>
$.fn.bootstrapMultiSelect.lang = 'it';
</script>
Now all multiselect instances will use Italian text automatically.
Note: Loading the language file provides the translations, but you still need to set $.fn.bootstrapMultiSelect.lang = 'it' to apply them globally.
In your _Layout.cshtml:
@using System.Globalization
@{
var culture = CultureInfo.CurrentCulture.TwoLetterISOLanguageName;
}
<script src="~/lib/bootstrap-multiselect/js/bootstrap-multiselect.min.js"></script>
@if (culture != "en")
{
<!-- Language is automatically set when the file is loaded -->
<script src="~/lib/bootstrap-multiselect/langs/jquery-bootstrap-multiselect.@(culture).min.js"></script>
<!-- Set a global default -->
<script>
$.fn.bootstrapMultiSelect.lang = '@(culture)';
</script>
}
You can override the global language for specific instances:
Tag Helper:
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
lang="it"
placeholder="Seleziona elementi..." />
HTML Helper:
@Html.MultiSelectFor(m => m.SelectedItems, Model.AvailableItems, new MultiSelectConfig
{
Lang = "it",
Placeholder = "Seleziona elementi..."
})
When determining which text to display:
placeholder="Custom text")Language files are automatically available via Static Web Assets at: ~/lib/bootstrap-multiselect/langs/
jquery-bootstrap-multiselect.it.min.js - Italianjquery-bootstrap-multiselect.es.min.js - Spanishjquery-bootstrap-multiselect.fr.min.js - Frenchjquery-bootstrap-multiselect.de.min.js - Germanjquery-bootstrap-multiselect.pt.min.js - PortugueseAdd the tag helper to your _ViewImports.cshtml:
@addTagHelper *, BootstrapMultiSelect.MVC
Then use in your views:
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
placeholder="Select items..."
max-selection="3"
theme="primary"
search="true"
select-all="true" />
| Attribute | Type | Default | Description |
|---|---|---|---|
asp-for | ModelExpression | (required) | The model property to bind |
asp-items | IEnumerable<SelectListItem> | (required) | The items to display |
placeholder | string | "Select items..." | Placeholder text |
max-selection | int | 0 | Maximum items (0 = unlimited) |
select-all | bool | true | Show select all buttons |
search | bool | true | Enable search |
width | string | "100%" | Dropdown width |
theme | string | "primary" | Bootstrap theme |
close-on-select | bool | false | Close on select |
button-class | string | null | Custom button class |
search-placeholder | string | "Search..." | Search placeholder |
select-all-text | string | "Select All" | Select all button text |
deselect-all-text | string | "Deselect All" | Deselect all button text |
no-results-text | string | "No results found" | No results message |
max-height | string | "300px" | Max dropdown height |
items-selected-text | string | "items selected" | Text for multiple selection count |
lang | string | null | Language code (e.g., "it", "es", "fr") |
enable-pagination | bool | false | Enable pagination for long lists |
items-per-page | int | 10 | Number of items per page |
pagination-position | string | "bottom" | Pagination position ("top", "bottom", "both") |
pagination-prev-text | string | "Previous" | Previous button text |
pagination-next-text | string | "Next" | Next button text |
pagination-info-text | string | "Page {current} of {total}" | Pagination info template |
Add the namespace to your view or _ViewImports.cshtml:
@using BootstrapMultiSelect.MVC.HtmlHelpers
@using BootstrapMultiSelect.MVC.Models
Then use in your views:
@Html.MultiSelectFor(m => m.SelectedItems, Model.AvailableItems, new MultiSelectConfig
{
Placeholder = "Select items...",
MaxSelection = 3,
Theme = "primary",
Search = true,
SelectAll = true
})
Or without model binding:
@Html.MultiSelect("selectedItems", Model.AvailableItems, new MultiSelectConfig
{
Placeholder = "Choose items...",
Theme = "success"
})
Model:
public class MyViewModel
{
public List<string> SelectedItems { get; set; } = new List<string>();
public List<SelectListItem> AvailableItems { get; set; }
}
Controller:
public IActionResult Index()
{
var model = new MyViewModel
{
AvailableItems = new List<SelectListItem>
{
new SelectListItem { Value = "1", Text = "Item 1" },
new SelectListItem { Value = "2", Text = "Item 2" },
new SelectListItem { Value = "3", Text = "Item 3" },
new SelectListItem { Value = "4", Text = "Item 4" }
}
};
return View(model);
}
View (Tag Helper):
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
placeholder="Select items..."
theme="primary" />
View (HTML Helper):
@Html.MultiSelectFor(m => m.SelectedItems, Model.AvailableItems, new MultiSelectConfig
{
Placeholder = "Select items...",
Theme = "primary"
})
var model = new MyViewModel
{
SelectedItems = new List<string> { "1", "3" }, // Pre-select items 1 and 3
AvailableItems = new List<SelectListItem>
{
new SelectListItem { Value = "1", Text = "Item 1" },
new SelectListItem { Value = "2", Text = "Item 2" },
new SelectListItem { Value = "3", Text = "Item 3" }
}
};
var model = new MyViewModel
{
AvailableItems = new List<SelectListItem>
{
new SelectListItem { Value = "1", Text = "Item 1" },
new SelectListItem { Value = "2", Text = "Item 2 (Disabled)", Disabled = true },
new SelectListItem { Value = "3", Text = "Item 3" }
}
};
var model = new MyViewModel
{
AvailableItems = new List<SelectListItem>
{
new SelectListItem { Value = "html", Text = "HTML", Group = "Frontend" },
new SelectListItem { Value = "css", Text = "CSS", Group = "Frontend" },
new SelectListItem { Value = "js", Text = "JavaScript", Group = "Frontend" },
new SelectListItem { Value = "csharp", Text = "C#", Group = "Backend" },
new SelectListItem { Value = "python", Text = "Python", Group = "Backend" }
}
};
Tag Helper:
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
max-selection="3"
placeholder="Select up to 3 items..." />
HTML Helper:
@Html.MultiSelectFor(m => m.SelectedItems, Model.AvailableItems, new MultiSelectConfig
{
MaxSelection = 3,
Placeholder = "Select up to 3 items..."
})
Tag Helper:
<multiselect asp-for="SelectedCities"
asp-items="ViewBag.Cities"
placeholder="Select cities..."
enable-search="true"
enable-pagination="true"
items-per-page="8"
pagination-position="bottom" />
HTML Helper:
@Html.MultiSelectFor(m => m.SelectedCities, ViewBag.Cities, new MultiSelectConfig
{
Placeholder = "Select cities...",
EnableSearch = true,
EnablePagination = true,
ItemsPerPage = 8,
PaginationPosition = "bottom"
})
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
theme="success"
button-class="btn-success"
width="300px"
max-height="200px" />
Tag Helper (Italian):
<multiselect asp-for="SelectedItems"
asp-items="Model.AvailableItems"
lang="it" />
<!-- All text will be in Italian: "Seleziona elementi...", "Cerca...", etc. -->
HTML Helper (Spanish):
@Html.MultiSelectFor(m => m.SelectedItems, Model.AvailableItems, new MultiSelectConfig
{
Lang = "es"
})
<!-- All text will be in Spanish: "Seleccionar elementos...", "Buscar...", etc. -->
Global Language in Layout:
<!-- _Layout.cshtml -->
<script src="~/lib/bootstrap-multiselect/js/bootstrap-multiselect.min.js"></script>
<script src="~/lib/bootstrap-multiselect/langs/jquery-bootstrap-multiselect.it.min.js"></script>
<!-- Italian is now automatically set as the global language -->
<!-- Now all multiselect instances in all views will use Italian -->
Dynamic Language Based on User Culture:
@using System.Globalization
@{
var culture = CultureInfo.CurrentCulture.TwoLetterISOLanguageName;
}
<script src="~/lib/bootstrap-multiselect/js/bootstrap-multiselect.min.js"></script>
@if (culture != "en")
{
<!-- Automatically sets the language when loaded -->
<script src="~/lib/bootstrap-multiselect/langs/jquery-bootstrap-multiselect.@(culture).min.js"></script>
}
<!-- Automatically uses user's language (it, es, fr, de, pt) -->
MIT License
Paolo Gaetano
Contributions, issues, and feature requests are welcome!
git checkout -b feature/AmazingFeature)git commit -m 'Add some AmazingFeature')git push origin feature/AmazingFeature)See CONTRIBUTING.md for detailed guidelines.