Joel G Mathew
Joel G Mathew

Reputation: 8061

Bootstrap closed.bs.alert doesnt fire when alert is being dynamically created

I have a page where I let the user search for information, and it displays an alert at the top stating that he is searching. He is then shown a filtered result. If he clicks the alert dismiss button, the main page is to be reloaded.

However I find that the dismissed event closed.bs.alert is never fired.

My javascript code:

$("document").ready(function () {
    $('body').on('click', '#mainsearch', function (event) {
        url = window.location.href;
        console.log('Clicked');
        SearchPatients();

    });


    $('body').on('closed.bs.alert', "#srpatalert", function () {
        console.log('Closed alert');
        window.location.href = "/appointments/patients";
    });

    $(function () {
        $('#srpatalert').on('closed.bs.alert', function () {
            console.log('Closed alert');
            window.location.href = "/appointments/patients";
        });
    });


});


function SearchPatients() {
    var srmsgpre = `
    <div id="srpatalert" class="mr-3 alert alert-info alert-dismissible fade show" role="alert">
        <strong>Searching For`;
    var srmcl = ' </strong>';
    var srmsgpost = `       
        <button type="button" class="close" data-dismiss="alert" aria-label="Close">
            <span aria-hidden="true">&times;</span>
        </button>
    </div>
    `;
    var breadcrumb = `
        <li class="breadcrumb-item">
            <a href="/appointments">Home</a>
        </li>
        <li class="breadcrumb-item">
            <a href="/appointments/patients">Patients</a>
        </li>
        <li class="breadcrumb-item active" aria-current="page">Search results</li>`;

    var srstr = $("#searchterm").val();
    sralmsg = srmsgpre + 'Patients:' + srmcl + srstr + srmsgpost;
    $('#presearch').html(sralmsg);
    return true;
}

My html code:

<!doctype html>
<html lang="en">

<head>
    <!-- Required meta tags -->
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">

    <!-- Bootstrap CSS -->
    <link rel="stylesheet" href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css">   
    <title>Show Patients</title>
</head>

<body>
    <div id="navbar">
        <nav class="navbar navbar-expand-lg navbar-light bg-light">
    <a class="navbar-brand" href="#">

        Patients


        </a>
    <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
        <span class="navbar-toggler-icon"></span>
    </button>

    <div class="collapse navbar-collapse" id="navbarSupportedContent">
        <ul class="navbar-nav mr-auto">
            <li class="nav-item active">
                <a class="nav-link" href="/appointments">Home
                    <!-- <span class="sr-only">(current)</span> -->
                </a>
            </li>

            <li class="nav-item dropdown">
                <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true"
                    aria-expanded="false">
                    Doctor
                </a>
                <div class="dropdown-menu" aria-labelledby="navbarDropdown">
                    <a class="dropdown-item" href="/appointments/doctors">View Doctors</a>
                    <a class="dropdown-item" href="/appointments/createdoctor">Add Doctor</a>                 

                </div>
            </li>


            <li class="nav-item dropdown">
                <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true"
                    aria-expanded="false">
                    Patients
                </a>
                <div class="dropdown-menu" aria-labelledby="navbarDropdown">
                    <a class="dropdown-item" href="/appointments/patients">View Patients</a>
                    <a class="dropdown-item" href="/appointments/createpatient">Add Patient</a>            
                </div>
            </li>

            <li class="nav-item">
                <a class="nav-link" href="/appointments/getappointment">Appointments

                </a>
            </li>

            <li class="nav-item dropdown">
                <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
                    Welcome, joel
                </a>
                <div class="dropdown-menu" aria-labelledby="navbarDropdown">
                    <a class="dropdown-item" href="/accounts/logout/?next=/appointments/patients">Logout</a>
                    <a class="dropdown-item" href="#">My Profile</a>
                    <div class="dropdown-divider"></div>
                    <a class="dropdown-item" href="/appointments/myappointments">My Appointments</a>
                </div>
            </li>


            <!-- <li class="nav-item">
                <a class="nav-link disabled" href="#">Disabled</a>
            </li> -->
        </ul>
        <!-- <form class="form-inline my-2 my-lg-0"> -->
            <div class="form-inline my-2 my-lg-0">
                <div id="presearch"></div>
                <input id="searchterm" class="form-control mr-sm-2" type="search" placeholder="Search" aria-label="Search">
                <button id="mainsearch" type="button" class="btn btn-success">Search</button>
            </div>
        <!-- </form> -->
    </div>
</nav>

    </div>


    <nav aria-label="breadcrumb">
        <ol id="breadcrumb" class="breadcrumb">

    <li class="breadcrumb-item">
        <a href="/appointments">Home</a>
    </li>
    <li class="breadcrumb-item">
        <a href="/appointments/patients">Patients</a>
    </li>
    <li class="breadcrumb-item active" aria-current="page">Show Patients</li>

        </ol>
    </nav>


<div id="containerblock" class="container-fluid">
    <div class="row">

    <div class="col-sm-3 card-deck">
    <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
            <div id="id" style="display: none;">13 </div>
            <h2 class="card-title">
                <a href="/appointments/patient/13">Epra Peter</a>
                </a>
            </h2>
            <h6 class="card-subtitle mb-2 text-muted">Age 45</h6>
            <p class="card-text">Mobile 0000</p>
            <p class="card-text">Place </p>
            <div id="docbtngp" class="d-flex flex-row">

                <a href="/appointments/patient/edit/13" class="btn btn-primary mr-1">
                    <i class="fas fa-user-edit"></i>
                </a>            
                <a href="/appointments/patient/calendar/13" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar"></i>
                </a>                
                <a href="/appointments/patient/appointment/add/13" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar-plus"></i>
                </a>


                <a href="/appointments/patient/remove/13" class="btn btn-danger mr-1">
                    <i class="fas fa-trash-alt"></i>
                </a>


            </div>
        </div>
    </div>
    </div>

    <div class="col-sm-3 card-deck">
    <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
            <div id="id" style="display: none;">11 </div>
            <h2 class="card-title">
                <a href="/appointments/patient/11">Jeffy Kelly</a>
                </a>
            </h2>
            <h6 class="card-subtitle mb-2 text-muted">Age 5</h6>
            <p class="card-text">Mobile 0000</p>
            <p class="card-text">Place </p>
            <div id="docbtngp" class="d-flex flex-row">

                <a href="/appointments/patient/edit/11" class="btn btn-primary mr-1">
                    <i class="fas fa-user-edit"></i>
                </a>            
                <a href="/appointments/patient/calendar/11" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar"></i>
                </a>                
                <a href="/appointments/patient/appointment/add/11" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar-plus"></i>
                </a>


                <a href="/appointments/patient/remove/11" class="btn btn-danger mr-1">
                    <i class="fas fa-trash-alt"></i>
                </a>


            </div>
        </div>
    </div>
    </div>

    <div class="col-sm-3 card-deck">
    <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
            <div id="id" style="display: none;">15 </div>
            <h2 class="card-title">
                <a href="/appointments/patient/15">Ramu Pillai</a>
                </a>
            </h2>
            <h6 class="card-subtitle mb-2 text-muted">Age 50</h6>
            <p class="card-text">Mobile 0000</p>
            <p class="card-text">Place </p>
            <div id="docbtngp" class="d-flex flex-row">

                <a href="/appointments/patient/edit/15" class="btn btn-primary mr-1">
                    <i class="fas fa-user-edit"></i>
                </a>            
                <a href="/appointments/patient/calendar/15" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar"></i>
                </a>                
                <a href="/appointments/patient/appointment/add/15" class="btn btn-primary mr-1">
                    <i class="fas fa-calendar-plus"></i>
                </a>


                <a href="/appointments/patient/remove/15" class="btn btn-danger mr-1">
                    <i class="fas fa-trash-alt"></i>
                </a>


            </div>
        </div>
    </div>
    </div>

    </div>
    <div class="menu pmd-floating-action pmd-lg" role="navigation">
        <a href="/appointments/patient/add" class="pmd-floating-action-btn btn btn-sm pmd-btn-fab pmd-btn-raised pmd-ripple-effect btn-default pmd-lg"
            data-title="Add a new patient">
            <span class="pmd-floating-hidden"></span>
            <i class="material-icons">add</i>
        </a>

    </div>

    <div id="messages">

    </div>
</div>


    <!-- Optional JavaScript -->

    <!-- jQuery first, then Popper.js, then Bootstrap JS -->

    <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/js/bootstrap.min.js"></script>   

</body>

</html>

JSFiddle: JSFiddle

As you can see above, I tried two different approaches. I'm not able to get the closed.bs.alert event to fire.

Upvotes: 0

Views: 2183

Answers (2)

You Old Fool
You Old Fool

Reputation: 22941

As discussed in comments on the accepted answer above, the closed event does not properly bubble even if you use a delegated event and attach the handler to parent. A bit of discussion on this here.

Also, it's important to note that there is a distinct difference between close and closed, which is that the latter fires after the alert has been removed. In some applications this difference may be significant, such as when you need to resize other elements based on changes to the dom.

With that in mind, if you absolutely need to use the closed event, you must dynamically add your handler anytime the alert is created. This could be done in your example code immediately after:

$('#presearch').html(sralmsg);

You could add your handler so it would look like this:

$('#presearch').html(sralmsg);
$('#srpatalert').off().on('closed.bs.alert', function () {
    console.log('Closed alert');
    window.location.href = "/appointments/patients";
});

Upvotes: 1

tao
tao

Reputation: 90113

Replace

$(function () {
    $('#srpatalert').on('closed.bs.alert', function () {
        console.log('Closed alert');
        window.location.href = "/appointments/patients";
    });
});

with

$('#navbar').on('close.bs.alert', '#srpatalert', function () {
  console.log('Closed alert');
  window.location.href = "/appointments/patients";
});

Notice that, besides delegating the event to #navbar, I also changed the event itself (from closed.bs.alert to close.bs.alert) as closed.bs.alert doesn't seem to fire in this example - I don't know why and, since it's working with close.bs.alert, I didn't investigate further.

Here's a working example:

$("document").ready(function() {
  $('body').on('click', '#mainsearch', function(event) {
    url = window.location.href;
    console.log('Clicked');
    SearchPatients();

  });

  $('#navbar').on('close.bs.alert', "#srpatalert", function() {
    console.log('Closed alert');
  });

  // don't mind next line, it's just for SO:
  $(document).on('click', 'a', e => e.preventDefault())
});

function makeAlert(category, term) {
  return $('<div />', {
    id:'srpatalert',
    class:'mr-3 alert alert-info alert-dismissible fade show',
    role: 'alert'
  }).append($('<strong />',{text:'Searching For ' + category + ': '}))
    .append($('<span />', {text: term}))
    .append($('<button />', {
        type:'button',
        class:'close',
        'data-dismiss':'alert',
        'aria-label':'Close',
        html: $('<span />',{
          'aria-hidden':true,
          html:'&times;'
        })
      }))
}

function SearchPatients() {
  sralmsg = makeAlert('Patients', $("#searchterm").val());
  $('#presearch').html(sralmsg);
  return true;
}
<link href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/css/bootstrap.min.css" rel="stylesheet" />
<script src="https://code.jquery.com/jquery-3.3.1.slim.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/popper.js/1.14.3/umd/popper.min.js"></script>
<script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.3/js/bootstrap.min.js"></script>
<div id="navbar">
  <nav class="navbar navbar-expand-lg navbar-light bg-light">
    <a class="navbar-brand" href="#">
      Patients
    </a>
    <button class="navbar-toggler" type="button" data-toggle="collapse" data-target="#navbarSupportedContent" aria-controls="navbarSupportedContent" aria-expanded="false" aria-label="Toggle navigation">
        <span class="navbar-toggler-icon"></span>
    </button>

    <div class="collapse navbar-collapse" id="navbarSupportedContent">
      <ul class="navbar-nav mr-auto">
        <li class="nav-item active">
          <a class="nav-link" href="/appointments">Home
                    <!-- <span class="sr-only">(current)</span> -->
                </a>
        </li>

        <li class="nav-item dropdown">
          <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
                    Doctor
                </a>
          <div class="dropdown-menu" aria-labelledby="navbarDropdown">
            <a class="dropdown-item" href="/appointments/doctors">View Doctors</a>
            <a class="dropdown-item" href="/appointments/createdoctor">Add Doctor</a>

          </div>
        </li>


        <li class="nav-item dropdown">
          <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
                    Patients
                </a>
          <div class="dropdown-menu" aria-labelledby="navbarDropdown">
            <a class="dropdown-item" href="/appointments/patients">View Patients</a>
            <a class="dropdown-item" href="/appointments/createpatient">Add Patient</a>
          </div>
        </li>

        <li class="nav-item">
          <a class="nav-link" href="/appointments/getappointment">Appointments

                </a>
        </li>

        <li class="nav-item dropdown">
          <a class="nav-link dropdown-toggle" href="#" id="navbarDropdown" role="button" data-toggle="dropdown" aria-haspopup="true" aria-expanded="false">
                    Welcome, joel
                </a>
          <div class="dropdown-menu" aria-labelledby="navbarDropdown">
            <a class="dropdown-item" href="/accounts/logout/?next=/appointments/patients">Logout</a>
            <a class="dropdown-item" href="#">My Profile</a>
            <div class="dropdown-divider"></div>
            <a class="dropdown-item" href="/appointments/myappointments">My Appointments</a>
          </div>
        </li>


        <!-- <li class="nav-item">
                <a class="nav-link disabled" href="#">Disabled</a>
            </li> -->
      </ul>
      <!-- <form class="form-inline my-2 my-lg-0"> -->
      <div class="form-inline my-2 my-lg-0">
        <div id="presearch"></div>
        <input id="searchterm" class="form-control mr-sm-2" type="search" placeholder="Search" aria-label="Search">
        <button id="mainsearch" type="button" class="btn btn-success">Search</button>
      </div>
      <!-- </form> -->
    </div>
  </nav>

</div>


<nav aria-label="breadcrumb">
  <ol id="breadcrumb" class="breadcrumb">

    <li class="breadcrumb-item">
      <a href="/appointments">Home</a>
    </li>
    <li class="breadcrumb-item">
      <a href="/appointments/patients">Patients</a>
    </li>
    <li class="breadcrumb-item active" aria-current="page">Show Patients</li>

  </ol>
</nav>


<div id="containerblock" class="container-fluid">
  <div class="row">

    <div class="col-sm-3 card-deck">
      <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
          <div id="id" style="display: none;">13 </div>
          <h2 class="card-title">
            <a href="/appointments/patient/13">Epra Peter</a>
          </h2>
          <h6 class="card-subtitle mb-2 text-muted">Age 45</h6>
          <p class="card-text">Mobile 0000</p>
          <p class="card-text">Place </p>
          <div id="docbtngp" class="d-flex flex-row">

            <a href="/appointments/patient/edit/13" class="btn btn-primary mr-1">
              <i class="fas fa-user-edit"></i>
            </a>
            <a href="/appointments/patient/calendar/13" class="btn btn-primary mr-1">
              <i class="fas fa-calendar"></i>
            </a>
            <a href="/appointments/patient/appointment/add/13" class="btn btn-primary mr-1">
              <i class="fas fa-calendar-plus"></i>
            </a>


            <a href="/appointments/patient/remove/13" class="btn btn-danger mr-1">
              <i class="fas fa-trash-alt"></i>
            </a>


          </div>
        </div>
      </div>
    </div>

    <div class="col-sm-3 card-deck">
      <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
          <div id="id" style="display: none;">11 </div>
          <h2 class="card-title">
            <a href="/appointments/patient/11">Jeffy Kelly</a>
          </h2>
          <h6 class="card-subtitle mb-2 text-muted">Age 5</h6>
          <p class="card-text">Mobile 0000</p>
          <p class="card-text">Place </p>
          <div id="docbtngp" class="d-flex flex-row">

            <a href="/appointments/patient/edit/11" class="btn btn-primary mr-1">
              <i class="fas fa-user-edit"></i>
            </a>
            <a href="/appointments/patient/calendar/11" class="btn btn-primary mr-1">
              <i class="fas fa-calendar"></i>
            </a>
            <a href="/appointments/patient/appointment/add/11" class="btn btn-primary mr-1">
              <i class="fas fa-calendar-plus"></i>
            </a>


            <a href="/appointments/patient/remove/11" class="btn btn-danger mr-1">
              <i class="fas fa-trash-alt"></i>
            </a>


          </div>
        </div>
      </div>
    </div>

    <div class="col-sm-3 card-deck">
      <div class="card mb-3 mr-3 ml-3 shadow bg-white rounded" style="width: 18rem;">
        <div class="card-body">
          <div id="id" style="display: none;">15 </div>
          <h2 class="card-title">
            <a href="/appointments/patient/15">Ramu Pillai</a>
          </h2>
          <h6 class="card-subtitle mb-2 text-muted">Age 50</h6>
          <p class="card-text">Mobile 0000</p>
          <p class="card-text">Place </p>
          <div id="docbtngp" class="d-flex flex-row">

            <a href="/appointments/patient/edit/15" class="btn btn-primary mr-1">
              <i class="fas fa-user-edit"></i>
            </a>
            <a href="/appointments/patient/calendar/15" class="btn btn-primary mr-1">
              <i class="fas fa-calendar"></i>
            </a>
            <a href="/appointments/patient/appointment/add/15" class="btn btn-primary mr-1">
              <i class="fas fa-calendar-plus"></i>
            </a>


            <a href="/appointments/patient/remove/15" class="btn btn-danger mr-1">
              <i class="fas fa-trash-alt"></i>
            </a>


          </div>
        </div>
      </div>
    </div>

    <div class="menu pmd-floating-action pmd-lg" role="navigation">
      <a href="/appointments/patient/add" class="pmd-floating-action-btn btn btn-sm pmd-btn-fab pmd-btn-raised pmd-ripple-effect btn-default pmd-lg" data-title="Add a new patient">
        <span class="pmd-floating-hidden"></span>
        <i class="material-icons">add</i>
      </a>

    </div>

    <div id="messages">

    </div>
  </div>

Upvotes: 2

Related Questions