9

I'm trying to create a dropdown item in a Bootstrap navbar using Angular 6. My code is working when I test it online :

<nav class="navbar bg-light navbar-light navbar-expand">
<ul class="navbar-nav">
  <li class="nav-item dropdown" >
    <a class="nav-link dropdown-toggle" data-toggle="dropdown">Page1</a>
    <div class="dropdown-menu">
      <a class="dropdown-item" href="#">Page1.1</a>
    </div>
  </li>
  <li><a class="nav-link" href="#">Page2</a></li>
</ul>
</nav>

But the dropdown does not work with Angular 6. I've used the following method in order to use Bootstrap with Angular :

ng add @ng-bootstrap/schematics

And everything works fine except for that dropdown item !

3
  • Can you please tell me which version of bootstrap are you using? Commented Jun 27, 2018 at 5:46
  • Also requesting you to please add "node_modules/bootstrap/dist/css/bootstrap.min.css" inside styles array in angular.json file Commented Jun 27, 2018 at 5:53
  • You can try angular dropdown instead of bootstrap. You can refer to the following link. It is multi-functional npmjs.com/package/@ng-select/ng-select Commented Feb 3, 2019 at 6:41

8 Answers 8

26

I have came across the same problem earlier and I found as below:

  1. html should be binded with the class container in bootstrap as mentioned in Bootstrap Layout
  2. Dropdowns are built on a third party library Popper.js as mentioned in Bootstrap Dropdown

As far as I know from your problem that you haven't refer to the required javascript i.e. util.js, bootstrap.js, popper.js or minified version.

Here, I have done nothing much, just refer the required javascript files in the index file

<script src="https://code.jquery.com/jquery-3.2.1.slim.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.12.9/umd/popper.min.js"></script>
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0/js/bootstrap.min.js"></script>

And I created a nav component and design as required like this:

<div class="container">
    <!-- Content here -->
    <ul class="nav nav-pills">
        <li class="nav-item">
            <a class="nav-link active" href="#">Active</a>
        </li>
        <li class="nav-item dropdown">
            <a class="nav-link dropdown-toggle" data-toggle="dropdown" href="#" role="button" aria-haspopup="true" aria-expanded="false">Dropdown</a>
            <div class="dropdown-menu">
                <a class="dropdown-item" href="#">Action</a>
                <a class="dropdown-item" href="#">Another action</a>
                <a class="dropdown-item" href="#">Something else here</a>
                <div class="dropdown-divider"></div>
                <a class="dropdown-item" href="#">Separated link</a>
            </div>
        </li>
        <li class="nav-item">
            <a class="nav-link" href="#">Link</a>
        </li>
        <li class="nav-item">
            <a class="nav-link disabled" href="#">Disabled</a>
        </li>
    </ul>
</div

The working demo can be found here. Hope this helps you.

Sign up to request clarification or add additional context in comments.

3 Comments

"html should be binded with the class container" That was it! Thanks
2nd step (addition of 3 libraries) worked for me. Many thanks!
No, we use angular that avoid use jquery
10

I have faced the same issue of bootstrap, but I got the solution. If you are using Angular 6, then no need to add popper.js for bootstrap. You need to add bootstrap 4 and then add rxjs-compat.

npm install rxjs-compat

And add ngx-bootstrap to perform dropdown action. Install the ngx-bootstrap,

npm install ngx-bootstrap --save

now we need to add the dropdown module from ngx-bootstrap in your application using following code

import { BrowserModule } from '@angular/platform-browser';
import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';

import { BsDropdownModule } from 'ngx-bootstrap/dropdown';
import { TooltipModule } from 'ngx-bootstrap/tooltip';
import { ModalModule } from 'ngx-bootstrap/modal';
import { AppComponent } from './app.component';

@NgModule({
 declarations: [
   AppComponent
 ],
 imports: [
   BrowserModule,
   CommonModule,
   BsDropdownModule.forRoot(),
   TooltipModule.forRoot(),
   ModalModule.forRoot()
 ],
 providers: [],
 bootstrap: [AppComponent]
})
export class AppModule { }

then I did some changes in your code and it's working fine for me.

<nav class="navbar navbar-default">
<ul class="nav navbar-nav">
  <li class="dropdown" dropdown >
    <a dropdownToggle role="button"> <!-- {2} -->
        Page1<span class="caret"></span></a>
    <div *dropdownMenu class="dropdown-menu">
      <a class="dropdown-item" href="#">Page1.1</a>
    </div>
  </li>
  <li><a class="nav-link" href="#">Page2</a></li>
</ul>
</nav>

1 Comment

why you added rxjs-compat? for me it worked without it.
6

The answer of @Rushikesh Salunke is great but at the time i saw it i was already using @ng-bootstrap library, not ngx, and this is what i found from the docs.

First, import the NgbDropdown Module into the component where you want to use it.

import { NgbDropdown} from '@ng-bootstrap/ng-bootstrap';

Then modify your .html as follows:

<div ngbDropdown class="d-inline-block">
  <button class="btn btn-outline-primary" id="dropdownBasic1" ngbDropdownToggle>Toggle dropdown</button>
  <div ngbDropdownMenu aria-labelledby="dropdownBasic1">
    <button class="dropdown-item">Action - 1</button>
    <button class="dropdown-item">Another Action</button>
    <button class="dropdown-item">Something else is here</button>
  </div>
</div>

You can see other use cases here.

Comments

2

Here you go...

I did below changes -

1. app.component.html

<p>
  Start editing to see some magic happen :)
</p>
<nav class="navbar bg-light navbar-light navbar-expand">
<ul class="nav navbar-nav">
  <li class="dropdown" appDropdown>
    <a href="#" class="dropdown-toggle" role="button">Page1</a>
    <ul class="dropdown-menu">
      <li><a href="#">Page1.1</a></li>
      <li><a href="#">Page1.2</a></li>
      <li><a href="#">Page1.3</a></li>
    </ul>
  </li>
  <li><a class="nav-link" href="#">Page2</a></li>
</ul>
</nav>

2. app.module.ts

I have added one directive to listen click event for dropdown and imported same in app.module.ts

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { FormsModule } from '@angular/forms';

import { AppComponent } from './app.component';
import { HelloComponent } from './hello.component';

import { DropdownDirective } from './dropdown.directive';

@NgModule({
  imports:      [ BrowserModule, FormsModule ],
  declarations: [ AppComponent, HelloComponent, DropdownDirective ],
  bootstrap:    [ AppComponent ]
})
export class AppModule { }

3. dropdown.directive.ts

Added directive to listen click event

import { Directive, HostListener, ElementRef, Renderer2 } from "@angular/core";

@Directive({
  selector: '[appDropdown]'
})

export class DropdownDirective {
  manageDropdown : boolean = false;

  constructor(private elementRef: ElementRef, private renderer: Renderer2)   {

  }

  @HostListener('click') openDropdown(eventData: Event) {
    if(!this.manageDropdown) {
      this.renderer.addClass(this.elementRef.nativeElement,'open');
      this.manageDropdown = !this.manageDropdown;
    } else {
      this.renderer.removeClass(this.elementRef.nativeElement, 'open');
      this.manageDropdown = !this.manageDropdown;
    }
  }
}

4. angular.json

Requesting you to do "npm install --save bootstrap@3" and do below changes in angular.json file.

"styles": [
              "src/styles.css",
              "../node_modules/bootstrap/dist/css/bootstrap.min.css"
            ],
            "scripts": [
              "../node_modules/bootstrap/dist/js/bootstrap.min.js"
            ]

Note - For your reference please visit reference link. You can see the dropdown demo.

1 Comment

please use bootstrap 4 because this is the version in the question.
0

When you do everything right and follow the examples given, and it doesn't seem to work, it can be that you forgot to import Bootstrap Module.

You can do this by this line to your main module in which you intend to use the component:

import { NgbModule } from '@ng-bootstrap/ng-bootstrap'

@NgModule({
  declarations: [MyComponent],
  imports: [
    NgbModule
  ],
  exports: [MyComponent]
})

Comments

0

Step 1: install ng-bootstrap

ng add @ng-bootstrap/ng-bootstrap

Step 2: Add ng-bootstrap module to your component module file

import { NgModule } from '@angular/core';
import { BrowserModule } from '@angular/platform-browser';
import { NgbModule } from '@ng-bootstrap/ng-bootstrap';

...

@NgModule({
  imports: [BrowserModule, NgbModule],
  ...
})

Step 3: In your component view file add the following code:

<div class="col">
    <div ngbDropdown class="d-inline-block">
      <button class="btn btn-outline-primary" id="dropdownBasic1" ngbDropdownToggle>Toggle dropdown</button>
      <div ngbDropdownMenu aria-labelledby="dropdownBasic1">
        <button ngbDropdownItem>Action - 1</button>
        <button ngbDropdownItem>Another Action</button>
        <button ngbDropdownItem>Something else is here</button>
      </div>
    </div>
  </div>

Ref: ng-bootstrap Docs

Comments

-1

For anyone who is looking for solution with bootstrap 4.4.1 and Angular 9+, i solved by creating custom directive with following host listener. just adding show to parent li was not doing anything

 @HostListener('click', ['$event']) onClick(event) {
         if (this.el.nativeElement.classList.contains('show')) {
            this.renderer.removeClass(this.el.nativeElement, 'show');
            this.renderer.setAttribute(this.el.nativeElement.childNodes[0], 'aria-expanded', 'false')
            this.renderer.removeClass(this.el.nativeElement.childNodes[1], 'show')

        } else {
            this.renderer.addClass(this.el.nativeElement, 'show')
            this.renderer.setAttribute(this.el.nativeElement.childNodes[0], 'aria-expanded', 'true')
            this.renderer.addClass(this.el.nativeElement.childNodes[1], 'show')
        }
    }

Comments

-1
<script src="https://code.jquery.com/jquery-3.3.1.slim.min.js"
integrity="sha384-q8i/X+965DzO0rT7abK41JStQIAqVgRVzpbzo5smXKp4YfRvH+8abtTE1Pi6jizo"
crossorigin="anonymous"></script>


<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.7/umd/popper.min.js"
integrity="sha384-UO2eT0CpHqdSJQ6hJty5KVphtPhzWj9WO1clHTMGa3JDZwrnQq4sF86dIHNDz0W1"
crossorigin="anonymous"></script>


<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.3.1/js/bootstrap.min.js"
integrity="sha384-JjSmVgyd0p3pXB1rRibZUAYoIIy6OrQ6VrjIEaFf/nJGzIxFDsf4x0xIM+B07jRM"
crossorigin="anonymous"></script>

Adding this in index.html before closing body tag. This works for me.

 <ul class="navbar-nav navbar-right">
        <li class="nav-item dropdown">
            <a class="nav-link dropdown-toggle" role="button" data-toggle="dropdown" aria-haspopup="true"
                aria-expanded="false">
                Manage Data
            </a>
            <div class="dropdown-menu" aria-labelledby="navbarDropdown">
                <a class="dropdown-item" href="">Save Data</a>
                <a class="dropdown-item" href="">Fetch Data</a>
            </div>
        </li>
    </ul>

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.