Underline active navbar links in bootstrap 4 - css

I'm upgrading a website from bootstrap 3 to 4 (beta). The css I used to underline active navbar links is no longer working. Instead of underlining the item, it underlines the full width of the page. How can I underline active nav items in bootstrap 4?
Bootstrap 3 css
.navbar-default .navbar-nav > .active:after {
position: absolute;
bottom: 0;
left: 0;
width: 100%;
content: " ";
border-bottom: 5px solid #5BC0EB;
}
Attempted Bootstrap 4 css
.navbar-light .navbar-nav .active::after {
position: absolute;
bottom: 0;
left: 0;
width: 100%;
content: " ";
border-bottom: 5px solid #5BC0EB;
}
HTML
<nav class="navbar fixed-top navbar-light bg-light navbar-expand-md">
<div class="container">
<a class="navbar-brand" href="#">My Website</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarCollapse" aria-controls="navbarCollapse"
aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse justify-content-end" id="main-nav-collapse">
<ul class="navbar-nav">
<li class="nav-item active"><a class="nav-link" href="#about">About</a></li>
<li class="nav-item"><a class="nav-link" href="#classes">Classes</a></li>
<li class="nav-item"><a class="nav-link" href="#gallery">Gallery</a></li>
<li class="nav-item"><a class="nav-link" href="#events">Events</a></li>
<li class="nav-item"><a class="nav-link" href="#contact">Contact</a></li>
<li class="nav-item"><a class="nav-link" href="#offers">Offers</a></li>
</ul>
</div>
</div>
</nav>

This happened because of your positioning.
Try to set relative position to your li and set after to a tag inside li which will be absolute positioned like below
.navbar-nav > li {
float: left;
position: relative;
}
.navbar-light .navbar-nav .active a::after {
border-bottom: 5px solid #5bc0eb;
bottom: -10px;
content: " ";
left: 0;
position: absolute;
right: 0;
}
Hope it helps.

Related

Setting margin to auto in a flexbox

I was following along the tutorial on youtube link and I got stuck in this part that's using margin-top: auto in a flexbox to push the last child to bottom. Can you please point out what's not working here?
.navbar {
width: 5rem;
height: 100vh;
position: fixed;
background-color: var(--bg-primary);
}
.navbar-nav {
list-style: none;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
align-items: center;
}
.nav-item:last-child {
margin-top: auto;
}
<nav class="navbar">
<ul class="navbar-nav">
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
</ul>
</nav>
This works as expected, the last <li> is pushed to the bottom of the parent, but since the parent (.navbar-nav) has the same height, you don't see the element moving.
Increasing the .navbar-nav height will enable the <li> to move down:
.navbar-nav {
...
height: 100vh;
}
.navbar {
width: 5rem;
height: 100vh;
position: fixed;
background-color: var(--bg-primary);
}
.navbar-nav {
height: 100vh;
list-style: none;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
align-items: center;
}
.nav-item:last-child {
margin-top: auto;
}
<nav class="navbar">
<ul class="navbar-nav">
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
</ul>
</nav>
you should add height: 100%; either
.navbar {
width: 5rem;
height: 100%;
position: fixed;
background-color: var(--bg-primary);
}
.navbar-nav {
list-style: none;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
align-items: center;
height:100%;
}
.nav-item:last-child {
margin-top: auto;
}
<nav class="navbar">
<ul class="navbar-nav">
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
</ul>
</nav>
After setting the height of 100vh to .navbar-nav, you can use flex:1 on 2nd child to make sure it takes the free space around. This will automatically push the last child to the bottom. In this case you even don't need to bother about using margin's to place elements inside the flex-container at different positions. flexbox properties and flex-item properties takes care of positioning our flex-items.
Code Modifications:
.navbar-nav{
height:100vh;
}
.nav-item:nth-child(2) {
flex:1;
}
.navbar {
width: 5rem;
height: 100vh;
position: fixed;
background-color: teal;
}
.navbar-nav {
list-style: none;
padding: 0;
margin: 0;
display: flex;
flex-direction: column;
align-items: center;
height:98vh;
}
.nav-item:nth-child(2) {
flex:1;
}
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width">
<title>JS Bin</title>
</head>
<body>
<nav class="navbar">
<ul class="navbar-nav">
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
<li class="nav-item">
<a class="nav-link" href="" >
<span class="link-text">Cats</span>
</a>
</li>
</ul>
</nav>
</body>
</html>
Note: The fundamental issue with margin-top not working is already covered in the above answers. Obviously the height issue with flex-container .navbar-nav div

Bootstrap 4 hover on navbar links causes flickering

I want to make my navbar links have a darker background color whenever I hover my mouse over them. It is working OK, but when I change padding (to 0px in this case) it starts to flicker: (View on full screen for better effect)
Also, the image link is not the same height as the other links(And when collapsed, it has this right blank space), and I can't get it in same line using the current styling rules.
**Edit: It's caused by the padding:0px!important, but that's because I do not want the hovering background to take the entire height. How to make the hovering background with less height?
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.0/js/bootstrap.min.js"></script>
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css" rel="stylesheet"/>
<style>
.navbar {
min-height: 80px;
font-size: 0.8rem;
font-weight:500;
}
.navbar-brand {
padding: 0 15px;
height: 80px;
line-height: 80px;
}
.navbar-toggle {
/* (80px - button height 34px) / 2 = 23px */
margin-top: 23px;
padding: 9px 10px !important;
}
#media (min-width: 768px) {
.navbar-nav > li > a {
/* (80px - line-height of 27px) / 2 = 26.5px */
padding-top: 26.5px;
padding-bottom: 26.5px;
line-height: 27px;
}
}
.bottom-space {
margin-bottom: 20px;
}
#navbar_logged_in > a:link {
color: white ;
}
#navbar_logged_in > a:hover {
opacity:0.7 ;
}
#navbar_logged_in > a:visited {
color: white ;
}
#navbar_logged_in > li.nav-link{
color:white;
}
.nav-pills .nav-link.active, .nav-pills .show > .nav-link{
background-color: #17A2B8;
}
body {
padding-top: 110px;
}
.main-nav a:hover {
background-color: #0D47A1!important;
padding: 0px!important;
}
</style>
<nav id="navbar_logged_in" class="navbar navbar-expand-lg navbar-light bottom-space fixed-top" style="background: linear-gradient(to right, #3399ff , #1a8cff, #0080ff, #0073e6);">
<div class="container">
<a class="navbar-brand mx-auto" href="#">
Logo
</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarTogglerDemo02" aria-controls="navbarTogglerDemo02" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse text-right" id="navbarTogglerDemo02">
<ul class="navbar-nav ml-auto mt-2 mt-lg-0">
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white;margin-right:25px;">
<img class="img-circle" src="Image" alt="Image" width="35" height="35" style="border-radius: 50%!important;">
</a>
</li>
<li class="nav-item main-nav">
<a id="homepage_link" class="nav-link" href="#" style="color:white">Homepage</a>
</li>
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white">About</a>
</li>
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white">Log Out</a>
</li>
</ul>
</div>
</div>
</nav>
What's causing that? How can I fix it?
Thanks
The flickering is caused because when you hover, you are removing the padding, which pulls the element out from under the cursor. This then stops the hover and reapplies the padding which puts it back under the cursor, triggering the hover state. Rinse and repeat.
To stop the flicker, you need these two styles to work together:
#media (min-width: 768px) {
.navbar-nav > li > a {
padding-top: 26.5px;
padding-bottom: 26.5px;
line-height: 27px;
}
}
.main-nav a:hover {
background-color: #0D47A1!important;
padding: 0px!important;
}
If you want the hovering background to take less height, replace the part that you don't want the background on with margin. This might look like:
#media (min-width: 768px) {
.navbar-nav > li > a {
padding: 6.5px 8px; /* top/bottom, sides */
margin: 20px 0px;
line-height: 27px;
}
}
.main-nav a:hover {
background-color: #0D47A1!important;
}
In short, don't make your box size change on hover, and if you don't want background, use margin instead of padding
The padding in the hover is causing the problem: padding: 10px!important;
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.0/js/bootstrap.min.js"></script>
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.0/css/bootstrap.min.css" rel="stylesheet"/>
<style>
.navbar {
min-height: 80px;
font-size: 0.8rem;
font-weight:500;
}
.navbar-brand {
padding: 0 15px;
height: 80px;
line-height: 80px;
}
.navbar-toggle {
/* (80px - button height 34px) / 2 = 23px */
margin-top: 23px;
padding: 9px 10px !important;
}
#media (min-width: 768px) {
.navbar-nav > li > a {
/* (80px - line-height of 27px) / 2 = 26.5px */
padding-top: 26.5px;
padding-bottom: 26.5px;
line-height: 27px;
}
}
.bottom-space {
margin-bottom: 20px;
}
#navbar_logged_in > a:link {
color: white ;
}
#navbar_logged_in > a:hover {
opacity:0.7 ;
}
#navbar_logged_in > a:visited {
color: white ;
}
#navbar_logged_in > li.nav-link{
color:white;
}
.nav-pills .nav-link.active, .nav-pills .show > .nav-link{
background-color: #17A2B8;
}
body {
padding-top: 110px;
}
.main-nav a:hover {
background-color: #0D47A1!important;
}
</style>
<nav id="navbar_logged_in" class="navbar navbar-expand-lg navbar-light bottom-space fixed-top" style="background: linear-gradient(to right, #3399ff , #1a8cff, #0080ff, #0073e6);">
<div class="container">
<a class="navbar-brand mx-auto" href="#">
Logo
</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarTogglerDemo02" aria-controls="navbarTogglerDemo02" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse text-right" id="navbarTogglerDemo02">
<ul class="navbar-nav ml-auto mt-2 mt-lg-0">
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white;margin-right:25px;">
<img class="img-circle" src="Image" alt="Image" width="35" height="35" style="border-radius: 50%!important;">
</a>
</li>
<li class="nav-item main-nav">
<a id="homepage_link" class="nav-link" href="#" style="color:white">Homepage</a>
</li>
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white">About</a>
</li>
<li class="nav-item main-nav">
<a class="nav-link" href="#" style="color:white">Log Out</a>
</li>
</ul>
</div>
</div>
</nav>

How to align Bootstrap 4 navbar items to bottom

I'm trying to align the text of the navbar items lowerin bootstrap 4. My idea was to align them to the bottom of the ul and then position the ul but I seem to fail to do both. The goal is to have the text (approximately) at the same height of the brand like this:
I have found some questions but most of them are for bootstrap 3 or don't work for some reason I don't understand.
This is example html:
<nav class="navbar navbar-expand-md navbar-dark bg-primary fixed-top">
<a class="navbar-brand" style="font-family: sans-serif; font-weight: 800; font-style: italic; font-size:xx-large;">Brand</a>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarResponsive" aria-controls="navbarResponsive" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="myNavbar">
<ul class="navbar-nav ml-auto">
<li class="nav-item" >
<p style="vertical-align:bottom;" >Test</p>
</li>
<li class="nav-item<?php addActiveClass('/index.php'); ?>">
<a class="nav-link" href="index.php">Test</a>
</li>
<li class="nav-item d-none d-md-block"><img src="" id="profileImage" height="40" width="40" style="margin-right: 10px; border-radius: 5px;"></li>
</ul>
</div>
I use this bootstrap theme and example css:
.navbar
{
padding:0rem 0.75rem;
}
.navbar-brand
{
padding: 0;
margin:0;
}
.navbar-nav > li
{
line-height: 36px;
padding: 0;
margin: 0;
background: red;
}
.navbar-nav > li > a
{
padding: 0;
margin: 0;
background: red;
vertical-align: bottom;
}
.navbar-nav > li > p
{
padding: 0;
margin: 0;
background: yellow;
vertical-align: bottom;
}
A complete example is available here:
https://jsfiddle.net/d6n5z3gb/8/
Add align-items-end to the navbar-nav to align the items to the bottom...
<ul class="navbar-nav align-items-end ml-auto">
<li class="nav-item" >
</li>
</ul>
And, remove the custom line-height...
.navbar-nav > li > a
{
padding: 0;
margin: 0;
background: red;
vertical-align: bottom;
}
Update on Codeply: https://www.codeply.com/go/usR58ejrtg

Keep main nav item hover CSS when hovering over dropdown

I am using Bootstrap 4, and have created a navigation that has a large dropdown menu, using animate.css for the dropdown CSS animation and a CSS transition on the main navigation element (underline).
Is it possible to keep the main navigation underlined when a user hovers over the sub-menu/dropdown? In this case, keep the "Services" main nav element underlined when mousing over the dropdown. I'd like to keep it pure CSS if possible, but if not, open to using jQuery.
Here's the HTML of my navigation:
<nav class="navbar navbar-expand-lg navbar-light" role="navigation">
<div class="navbar-brand">
Logo
</div>
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#global-navbar">
<span class="navbar-toggler-icon"></span>
</button>
<div class="collapse navbar-collapse" id="global-navbar">
<ul class="nav navbar-nav ml-auto">
<li class="nav-item dropdown">
<a class="nav-link main-nav-link" href="#" #*role="button" data-toggle="dropdown"*#>
Services
<span class="navigation-underline animated slideInLeft"></span>
</a>
<div class="dropdown-menu animated fadeIn">
<div class="container">
<div class="row">
<div class="col-md-3">
<ul class="nav flex-column">
<li class="nav-item">
<a class="nav-link" href="#">Service 1</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 2</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 3</a>
</li>
</ul>
</div>
<div class="col-md-3">
<ul class="nav flex-column">
<li class="nav-item">
<a class="nav-link" href="#">Service 4</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 5</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 6</a>
</li>
</ul>
</div>
<div class="col-md-3">
<ul class="nav flex-column">
<li class="nav-item">
<a class="nav-link" href="#">Service 7</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 8</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 9</a>
</li>
</ul>
</div>
<div class="col-md-3 border-right-0">
<ul class="nav flex-column">
<li class="nav-item">
<a class="nav-link" href="#">Service 10</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 11</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Service 12</a>
</li>
</ul>
</div>
</div>
</div>
</div>
</li>
<!-- more <li>s -->
</ul>
</div>
</nav>
Here's my CSS:
#media screen and (min-width: 992px) {
/* Link column styling */
.navbar .dropdown-menu div[class*="col"] { margin-top: 1em; margin-bottom: 1em; border-right: 1px solid #ffffff; }
.navbar .dropdown-menu { border: none; background-color: #e5e5e5 !important; }
.navbar { font-size: .9em; padding-top: 0px; padding-bottom: 0px; }
.navbar .navbar-brand { padding-top: 0; padding-bottom: 0; }
/* Add padding to keep hover working when mousing to menu */
.navbar .nav-item { padding: .75em .5em 0 .5em; margin: 0 .25em; }
/* Dropdown full width */
.navbar .dropdown { position: static; }
.navbar .dropdown-menu { width: 100%; left: 0; right: 0; /* Height of nav-item --> */ top: 67px; border-radius: 0; }
.navbar .dropdown-menu .dropdown-menu-heading { padding-left: .5em; text-transform: uppercase; font-weight: 700; color: #424242; }
/* Show dropdown menu on hover */
.navbar .dropdown:hover .dropdown-menu,
.navbar .dropdown .dropdown-menu:hover { -webkit-animation-duration: .3s; animation-duration: .3s; -webkit-animation-delay: .3s; animation-delay: .3s; display: block; }
/* Less padding on dropdown menu items and links */
.navbar .navbar-nav .nav.flex-column .nav-link { padding-top: 2px; }
.navbar .dropdown .dropdown-menu .flex-column li.nav-item { padding: 0; }
/* Animate border-bottom for links */
.navbar .navbar-nav .nav-link.main-nav-link::after { content: ''; display: block; width: 0%; height: 2px; background: #eb2b2c; transition: width .3s; }
.navbar .navbar-nav .nav-link.main-nav-link:hover::after { width: 100%; }
}
Since the .nav-item .dropdown element gets an additional .show class when is clicked, you can maintain the underlined effect with the following css:
.nav-item.dropdown.show > .nav-link::after {
width: 100%;
}
Alternatively, you could also use this one:
.nav-item.dropdown:hover > .nav-link::after {
width: 100%;
}
However, as there is a gap between the .nav-link and the .dropdown-menu, the :hover state is not set while the cursor is moving between the menu item and the dropdown.

How to achieve this menu layout? With full-height borders and the dropdown-menu properly aligned with the menu border bottom?

I want to have a menu like below, where:
the border-bottom of the menu is next to the orange background without any white space, and this border-bottom occupy the full-width, without any white space at left or right
the logo have a full height border right and and each menu item also have
full-height borders
Also the "Item" that has a dropdown menu i want that when is open it is aligned with the gray border-bottom of the navbar.
For that im using the code below, but Im not achieving this layout, I have a working example with the layout Im getting "http://jsfiddle.net/4606qqux/". Do you know how to fix the code to achieve the above layout?
HTML:
<div class="container-fluid px-0">
<nav class="navbar navbar-expand-md navbar-light">
Logo
<button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#main_nav" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
<span class="navbar-toggler-icon"></span>
</button>
<div class="menu_container">
<div class="collapse navbar-collapse" id="main_nav">
<ul class="navbar-nav ml-auto d-flex align-items-lg-center">
<li class="nav-item">
<a class="nav-link" href="#">Item 0</a>
</li>
<li class="nav-item">
<a class="nav-link" href="#">Item 1</a>
</li>
<li class="nav-item dropdown">
<a class="nav-link dropdown-toggle" href="#" id="userDropdown" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
<i class="fa fa-user" aria-hidden="true"></i> Jan
</a>
<div class="dropdown-menu" aria-labelledby="userDropdown">
<a class="dropdown-item" href="#">Edit Profile</a>
<div class="dropdown-divider"></div>
<a class="dropdown-item" href="#">logout</a>
</div>
</li>
</ul>
</div>
</div>
</nav>
</div>
CSS
.menu_container {
position: relative;
width: 100%;
border-bottom:1px solid gray;
}
div.dropdown-menu {
left: auto;
right: 0;
}
section {
background-color: orange;
height: 300px;
width: 100%;
}
.nav-item {
border-left: 1px solid gray;
}
.navbar{
border-right: 1px solid gray;
}
.logo{
border-right:1px solid gray;
}
From what I understood this is what you are after:
.logo {
border-right:1px solid gray;
height: 40px;
border-bottom: 1px solid gray;
padding-left: 20px;
padding-right: 20px;
line-height: 40px;
}
.dropdown-menu {
border-radius: 0;
border: 1px solid gray;
margin-top: 0;
}
Here is the updated fiddle:
http://jsfiddle.net/4606qqux/1/
Here is an even-more-updated-fiddle without padding around the top navigation element:
http://jsfiddle.net/4606qqux/2/

Resources