Bootstrap 5 has one of the most comprehensive form systems of any CSS framework. Every form element — input, select, checkbox, radio, range, file — gets consistent styling that works across browsers.
Basic Form Structure
The fundamental pattern: wrap each field in mb-3, pair a form-label with a form-control:
<form>
<div class="mb-3">
<label for="name" class="form-label">Full Name</label>
<input type="text" class="form-control" id="name" placeholder="Gagan Singh">
</div>
<div class="mb-3">
<label for="email" class="form-label">Email Address</label>
<input type="email" class="form-control" id="email" placeholder="you@example.com">
<div class="form-text">We'll never share your email.</div>
</div>
<div class="mb-3">
<label for="message" class="form-label">Message</label>
<textarea class="form-control" id="message" rows="4"
placeholder="Your message..."></textarea>
</div>
<button type="submit" class="btn btn-primary">Submit</button>
</form>
form-text under an input produces small muted helper text. The for/id pair links label to input for accessibility.
Input Sizes
<input class="form-control form-control-sm" placeholder="Small input">
<input class="form-control" placeholder="Default input">
<input class="form-control form-control-lg" placeholder="Large input">
Select Dropdown
<div class="mb-3">
<label class="form-label">Framework</label>
<select class="form-select">
<option selected disabled value="">Choose a framework...</option>
<option>Angular 21</option>
<option>Bootstrap 5</option>
<option>React 19</option>
<option>Next.js 15</option>
</select>
</div>
<!-- Multiple select -->
<select class="form-select" multiple>
<option>Angular</option>
<option>Bootstrap</option>
<option>React</option>
</select>
Checkboxes and Radio Buttons
<!-- Checkboxes -->
<div class="mb-3">
<label class="form-label">Frameworks</label>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="cb1" checked>
<label class="form-check-label" for="cb1">Angular 21</label>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="cb2">
<label class="form-check-label" for="cb2">Bootstrap 5</label>
</div>
<div class="form-check">
<input class="form-check-input" type="checkbox" id="cb3" disabled>
<label class="form-check-label text-muted" for="cb3">Vue (disabled)</label>
</div>
</div>
<!-- Radio buttons -->
<div class="mb-3">
<label class="form-label">Plan</label>
<div class="form-check">
<input class="form-check-input" type="radio" name="plan" id="r1" value="free">
<label class="form-check-label" for="r1">Free</label>
</div>
<div class="form-check">
<input class="form-check-input" type="radio" name="plan" id="r2" value="pro" checked>
<label class="form-check-label" for="r2">Pro — $29</label>
</div>
</div>
<!-- Inline checkboxes -->
<div class="mb-3">
<div class="form-check form-check-inline">
<input class="form-check-input" type="checkbox" id="i1">
<label class="form-check-label" for="i1">Angular</label>
</div>
<div class="form-check form-check-inline">
<input class="form-check-input" type="checkbox" id="i2">
<label class="form-check-label" for="i2">React</label>
</div>
</div>
<!-- Toggle switch -->
<div class="form-check form-switch">
<input class="form-check-input" type="checkbox" id="darkToggle">
<label class="form-check-label" for="darkToggle">Dark Mode</label>
</div>
Input Groups
Attach prefixes, suffixes and buttons to inputs:
<!-- Text prefix -->
<div class="input-group mb-3">
<span class="input-group-text">https://</span>
<input type="text" class="form-control" placeholder="yoursite.com">
</div>
<!-- Text suffix -->
<div class="input-group mb-3">
<input type="text" class="form-control" placeholder="Amount">
<span class="input-group-text">.00</span>
<span class="input-group-text">USD</span>
</div>
<!-- Button -->
<div class="input-group mb-3">
<input type="text" class="form-control" placeholder="Search components...">
<button class="btn text-white" style="background:#fd4766;">Search</button>
</div>
<!-- Button left -->
<div class="input-group mb-3">
<button class="btn btn-outline-secondary dropdown-toggle" data-bs-toggle="dropdown">
Filter
</button>
<ul class="dropdown-menu">
<li><a class="dropdown-item" href="#">Angular</a></li>
<li><a class="dropdown-item" href="#">React</a></li>
</ul>
<input type="text" class="form-control" placeholder="Search...">
</div>
Floating Labels
Labels that animate to the top of the input when focused:
<div class="form-floating mb-3">
<input type="email" class="form-control" id="floatEmail"
placeholder="name@example.com">
<label for="floatEmail">Email address</label>
</div>
<div class="form-floating mb-3">
<input type="password" class="form-control" id="floatPwd"
placeholder="Password">
<label for="floatPwd">Password</label>
</div>
<div class="form-floating mb-3">
<select class="form-select" id="floatSelect">
<option selected disabled>Choose...</option>
<option>Angular</option>
<option>React</option>
</select>
<label for="floatSelect">Framework</label>
</div>
The placeholder attribute is required for floating labels to animate — it can be an empty string.
Form Validation
<form class="needs-validation" novalidate id="validationForm">
<div class="mb-3">
<label class="form-label">Email</label>
<input type="email" class="form-control" required
placeholder="you@example.com">
<div class="valid-feedback">Looks good!</div>
<div class="invalid-feedback">Please provide a valid email.</div>
</div>
<div class="mb-3">
<label class="form-label">Template</label>
<select class="form-select" required>
<option value="">Choose a template...</option>
<option>Marvel Dashboard — $29</option>
<option>PORTO Bootstrap — $19</option>
</select>
<div class="invalid-feedback">Please select a template.</div>
</div>
<div class="form-check mb-3">
<input class="form-check-input" type="checkbox" id="terms" required>
<label class="form-check-label" for="terms">
I agree to the <a href="#" style="color:#fd4766;">terms</a>
</label>
<div class="invalid-feedback">You must agree before submitting.</div>
</div>
<button type="submit" class="btn text-white" style="background:#fd4766;">Submit</button>
</form>
<script>
document.getElementById('validationForm').addEventListener('submit', function(e) {
if (!this.checkValidity()) {
e.preventDefault()
e.stopPropagation()
}
this.classList.add('was-validated')
})
</script>
Horizontal Form Layout
<form>
<div class="row mb-3">
<label class="col-sm-3 col-form-label">Email</label>
<div class="col-sm-9">
<input type="email" class="form-control" placeholder="you@example.com">
</div>
</div>
<div class="row mb-3">
<label class="col-sm-3 col-form-label">Password</label>
<div class="col-sm-9">
<input type="password" class="form-control" placeholder="••••••••">
</div>
</div>
<div class="row">
<div class="col-sm-9 offset-sm-3">
<button type="submit" class="btn text-white" style="background:#fd4766;">Sign In</button>
</div>
</div>
</form>
Inline Form
<form class="d-flex gap-2 align-items-center flex-wrap">
<label class="visually-hidden" for="inlineEmail">Email</label>
<input type="email" class="form-control" id="inlineEmail"
placeholder="Email" style="max-width:220px;">
<label class="visually-hidden" for="inlinePwd">Password</label>
<input type="password" class="form-control" id="inlinePwd"
placeholder="Password" style="max-width:160px;">
<div class="form-check mb-0">
<input class="form-check-input" type="checkbox" id="inlineRemember">
<label class="form-check-label" for="inlineRemember">Remember me</label>
</div>
<button type="submit" class="btn text-white" style="background:#fd4766;">Sign In</button>
</form>
visually-hidden hides labels from view but keeps them accessible for screen readers — important for inline forms where labels are implied by placeholders.
Disabled and Readonly
<input class="form-control" value="Disabled input" disabled>
<input class="form-control" value="Read-only value" readonly>
<input class="form-control bg-light" value="Read-only plain" readonly>
readonly inputs keep their value in form submissions. disabled inputs are excluded from form data.
Frequently Asked Questions
Need a Full Bootstrap 5 Admin Dashboard?
Get a complete Angular 21 + Bootstrap 5 dashboard with 50+ components — built by the same team behind BootstrapPlanet.
Browse Templates →Use code FIRST30 for 30% off your first purchase.