Join the Stack Overflow Community
Stack Overflow is a community of 4.7 million programmers, just like you, helping each other.
Join them; it only takes a minute:
Sign up

Using the example mentioned here, how can I invoke the modal window using JavaScript instead of clicking a button?

I am new to AngularJS and tried searching the documentation here and here without luck.

Thanks

share|improve this question
up vote 61 down vote accepted

OK, so first of all the http://angular-ui.github.io/bootstrap/ has a <modal> directive and the $dialog service and both of those can be used to open modal windows.

The difference is that with the <modal> directive content of a modal is embedded in a hosting template (one that triggers modal window opening). The $dialog service is far more flexible and allow you to load modal's content from a separate file as well as trigger modal windows from any place in AngularJS code (this being a controller, a service or another directive).

Not sure what you mean exactly by "using JavaScript code" but assuming that you mean any place in AngularJS code the $dialog service is probably a way to go.

It is very easy to use and in its simplest form you could just write:

$dialog.dialog({}).open('modalContent.html');  

To illustrate that it can be really triggered by any JavaScript code here is a version that triggers modal with a timer, 3 seconds after a controller was instantiated:

function DialogDemoCtrl($scope, $timeout, $dialog){
  $timeout(function(){
    $dialog.dialog({}).open('modalContent.html');  
  }, 3000);  
}

This can be seen in action in this plunk: http://plnkr.co/edit/u9HHaRlHnko492WDtmRU?p=preview

Finally, here is the full reference documentation to the $dialog service described here: https://github.com/angular-ui/bootstrap/blob/master/src/dialog/README.md

share|improve this answer
    
@AhmadAlfy yes, there are some options that allow you to control visual aspects of the modal. But more importantly it has many super-powers and allows you to treat $dialogs almost like AngularJS routes, pass data between the main window and the modal (and back) etc. – pkozlowski.opensource Apr 28 '13 at 18:34
    
That readme link is broken – adam0101 Aug 26 '13 at 22:42
25  
Seems like $dialog has been replaced by a rewritten version of $modal: github.com/angular-ui/bootstrap/tree/… – Per Quested Aronsson Sep 17 '13 at 13:36
1  
1  
For those, like me, going back to Bootstrap 2.3.2 and Angular-UI-Bootstrap 0.5.0, I think the latest docs on the now defunct $dialog would be over here: github.com/angular-ui/bootstrap/commit/… – FOR Dec 27 '13 at 14:11

To make angular ui $modal work with bootstrap 3 you need to overwrite the styles

.modal {
    display: block;
}
.modal-body:before,
.modal-body:after {
    display: table;
    content: " ";
}
.modal-header:before,
.modal-header:after {
    display: table;
    content: " ";
}

(The last ones are necessary if you use custom directives) and encapsulate the html with

<div class="modal-dialog">
  <div class="modal-content">
    <div class="modal-header">
      <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
      <h4 class="modal-title">Modal title</h4>
    </div>
    <div class="modal-body">
      ...
    </div>
    <div class="modal-footer">
      <button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
      <button type="button" class="btn btn-primary">Save changes</button>
    </div>
  </div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
share|improve this answer

Open modal windows with passing data to dialog

In case if someone interests to pass data to dialog:

app.controller('ModalCtrl', function($scope,  $modal) {

      $scope.name = 'theNameHasBeenPassed';

      $scope.showModal = function() {

        $scope.opts = {
        backdrop: true,
        backdropClick: true,
        dialogFade: false,
        keyboard: true,
        templateUrl : 'modalContent.html',
        controller : ModalInstanceCtrl,
        resolve: {} // empty storage
          };


        $scope.opts.resolve.item = function() {
            return angular.copy(
                                {name: $scope.name}
                          ); // pass name to resolve storage
        }

          var modalInstance = $modal.open($scope.opts);

          modalInstance.result.then(function(){
            //on ok button press 
          },function(){
            //on cancel button press
            console.log("Modal Closed");
          });
      };                   
})

var ModalInstanceCtrl = function($scope, $modalInstance, $modal, item) {

     $scope.item = item;

      $scope.ok = function () {
        $modalInstance.close();
      };

      $scope.cancel = function () {
        $modalInstance.dismiss('cancel');
      };
}

Demo Plunker

share|improve this answer
    
Awesome. But why you in resolve pass empty storage and then add $scope.opts.resolve.item = function() ? – Anton Manevskiy May 26 at 10:52
1  
just for code read. You can write for sure, resolve:{ item: function(){return ..} } – Maxim Shoustin May 26 at 12:28

The AngularJS Bootstrap website hasn't been updated with the latest documentation. About 3 months ago pkozlowski-opensource authored a change to separate out $modal from $dialog commit is below:

https://github.com/angular-ui/bootstrap/commit/d7a48523e437b0a94615350a59be1588dbdd86bd

In that commit he added new documentation for $modal, which can be found below:

https://github.com/angular-ui/bootstrap/blob/d7a48523e437b0a94615350a59be1588dbdd86bd/src/modal/docs/readme.md.

Hope this helps!

share|improve this answer

It's not a good way, but for me it seems the most simplest.

Add an anchor tag which contains the modal data-target and data-toggle, have an id associated with it. (Can be added mostly anywhere in the html view)

<a href="" data-toggle="modal" data-target="#myModal" id="myModalShower"></a>

Now,

Inside the angular controller, from where you want to trigger the modal just use

angular.element('#myModalShower').trigger('click');

This will mimic a click to the button based on the angular code and the modal will appear.

share|improve this answer
    
Is this actually a good practice? Is this recommended or discouraged? Using this way, how it can affect the performance? Of course writing a line of code is easier than writing a whole function But, Still – Saiyaff Farouk Jul 27 at 14:32
1  
Like I said "It's not a good way..." because it's inconsistent with the design paradigm of angular. I think it's discouraged because of that reason. For the performance part - I don't think it should cause any difference. But, again if I was the expert, I shouldn't have followed this shortcut approach. It's just a quick and dirty way to get things done. :) Do tell me if you find something regarding this. – Gagandeep Singh Jul 28 at 16:21
    
I'm new to Angular, and to get my modal up-and-running this worked very well indeed. I can come back and do it properly once I've learnt how (and this milestone deadline has passed) – VictorySaber Aug 24 at 8:28

Different version similar to the one offered by Maxim Shoustin

I liked the answer but the part that bothered me was the use of <script id="..."> as a container for the modal's template.

I wanted to place the modal's template in a hidden <div> and bind the inner html with a scope variable called modal_html_template mainly because i think it more correct (and more comfortable to process in WebStorm/PyCharm) to place the template's html inside a <div> instead of <script id="...">

this variable will be used when calling $modal({... 'template': $scope.modal_html_template, ...})

in order to bind the inner html, i created inner-html-bind which is a simple directive

check out the example plunker

<div ng-controller="ModalDemoCtrl">

    <div inner-html-bind inner-html="modal_html_template" class="hidden">
        <div class="modal-header">
            <h3>I'm a modal!</h3>
        </div>
        <div class="modal-body">
            <ul>
                <li ng-repeat="item in items">
                    <a ng-click="selected.item = item">{{ item }}</a>
                </li>
            </ul>
            Selected: <b>{{ selected.item }}</b>
        </div>
        <div class="modal-footer">
            <button class="btn btn-primary" ng-click="ok()">OK</button>
            <button class="btn btn-warning" ng-click="cancel()">Cancel</button>
        </div>
    </div>

    <button class="btn" ng-click="open()">Open me!</button>
    <div ng-show="selected">Selection from a modal: {{ selected }}</div>
</div>

inner-html-bind directive:

app.directive('innerHtmlBind', function() {
  return {
    restrict: 'A',
    scope: {
      inner_html: '=innerHtml'
    },
    link: function(scope, element, attrs) {
      scope.inner_html = element.html();
    }
  }
});
share|improve this answer
    
the links for the items don't appear in your plunker - unfortunately i'm still pretty new w/ angular to determine why. – jae Feb 14 '15 at 16:00

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.