I am showing a form inside of a popover. The popover opens on the click of a button. The issue is that every time I click the button to open the popover, the same form gets appended to the existing popover. Here's my code:

$('.filter-node-btn').popover({     
    trigger:'click',
    html : true,
    placement: 'bottom',
    content: function() {               
        return $compile($(".filterNodeDialog").html())($scope);
    }
});

update

I found the issue while writing a jsfiddle for this problem. It worked in the fiddle but not my local environment. I am using bootstrap js 3.1.1 while for fiddle I tried bootstrap js 3.0. heres the line thats giving me issue in boostrap.js

bootstrap 3.1.1

    Popover.prototype.setContent = function () {
          ....
          $tip.find('.popover-content')[ // we use append for html objects to maintain js events 

        this.options.html ? (typeof content == 'string' ? 'html' : 'append') : 'text' ](content) 
      ...

 } 

bootstrap 3.0 the code says

 Popover.prototype.setContent = function () { 
               ....
      $tip.find('.popover-content')[this.options.html ? 'html' : 'text'](content)
 ...

 } 

If I tried replacing the older code it works in my local environment too. http://jsfiddle.net/46Z59/6/

My question is how do I fix it with the bootstrap 3.1.1 ?

有帮助吗?

解决方案

Updated Answer

Anything having to do with DOM should go into a directive and not a controller. In fact, by transitioning to a directive, your problem can be easily solved.

Placing your popover HTML into a template that is included in a directive will cause its content will be compiled by Angular automatically. In this case, a manual $compile using content extracted from the DOM by jQuery -- which seems to be at the root of the problem -- is unnecessary.

Such a directive might look like this:

.directive('myPopover', function($compile){
  return {
    restrict: 'EA',
    controller: function($scope){
        $scope.clearFilter = function(){        
          $scope.filterOption = "";
        };

        $scope.setFilterOption = function(){
            console.log("filter option :",$scope.filterOption);
            if($scope.filterOption == 'hdnodes'){ }
            else if($scope.filterOption == 'gnodes'){ }
            else if($scope.filterOption == 'clusters'){ }
            else if($scope.filterOption == 'standalones'){ }
        };
    },
    link: function(scope, elem, attrs) {
      elem.popover({    
            trigger:'click',
            html : true,
          placement: 'bottom',
            content: function() {               
                return elem.find('div');
            }
        });
    },
    templateUrl: 'fn-dialog.html'
  }
})

... where fn-dialog.html looks like this:

<!-- Button which opens popover when clicked -->
<button title="Filter" type="button" name="filter-node-btn" class="filter-node-btn">open</button>

<!-- Popover content -->
<div class="filterNodeDialog">                          
    <div class="filterCriteriaContent">    
        <form name="filterCriteriaForm">                              
            <input type="radio" name="filterOption" value="hdnodes" ng-model="filterOption" ng-change="setFilterOption();">
            <span>All HD nodes</span>           

[ the rest of the content for the popover ... ]

Plunker Demo

许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top