Reputation: 1377
I am using AngularJS UI Bootstrap's accordion. I am using ng-repeat
with filter inside the accordion. Now the problem is that I cannot access the filtered variable outside <accordion>
. If I ditch the accordion and use simple HTML it works fine.
<div ng-app="myApp">
<div ng-controller="AccordionCtrl">
<div>outside accordion{{filteredCampaigns}}</div>
<input type="text" ng-model="q" placeholder="filter" />
<accordion class="accordion" close-others="true">
<div>inside accordion{{filteredCampaigns}}</div>
<accordion-group ng-repeat="campaign in filteredCampaigns=(campaigns | filter:q)">
<accordion-heading>
<h3>{{campaign.title}}</h3>
</accordion-heading>
<p>{{campaign.content}}</p>
</accordion-group>
</accordion>
</div>
</div>
<script>
var app = angular.module('myApp', ['ui.bootstrap']);
app.controller('AccordionCtrl', ['$scope',
function ($scope) {
$scope.campaigns = [{
title: "Test1",
content: "file1.html"
}, {
title: "Test2",
content: "file2.html"
}, {
title: "Test3",
content: "file3.html"
}];
}]);
</script>
I have also created the fiddle here
Upvotes: 2
Views: 1674
Reputation: 34217
This is becuase the sub-directives comes with angular-ui
have child scopes that does not reflect this new filteredCampaigns
variable to the controller's scope.
1) define an object to contain the filteredCampaigns
dynamic variable
$scope.context = {};
2) change your accordion-group
to:
<accordion-group ng-repeat="campaign in context.filteredCampaigns=(campaigns | filter:q)">
<script>
var app = angular.module('myApp', ['ui.bootstrap']);
app.controller('AccordionCtrl', ['$scope',
function ($scope) {
$scope.context = {};
$scope.campaigns = [{
title: "Test1",
content: "file1.html"
}, {
title: "Test2",
content: "file2.html"
}, {
title: "Test3",
content: "file3.html"
}];
}]);
</script>
<div ng-app="myApp">
<div ng-controller="AccordionCtrl">
<div>outside accordion {{context.filteredCampaigns}} </div>
<input type="text" ng-model="q" placeholder="filter" />
<accordion class="accordion" close-others="true">
<div>inside accordion{{context.filteredCampaigns}}</div>
<accordion-group ng-repeat="campaign in context.filteredCampaigns=(campaigns | filter:q)">
<accordion-heading>
<h3>{{campaign.title}}</h3>
</accordion-heading>
<p>{{campaign.content}}</p>
</accordion-group>
</accordion>
</div>
</div>
Controller as
,i would recommend using Controller as
since it will give you more controll of what's defined on the controller's scope and what's not
<script>
var app = angular.module('myApp', ['ui.bootstrap']);
app.controller('AccordionCtrl', ['$scope',
function () {
var vm = this;
vm.campaigns = [{
title: "Test1",
content: "file1.html"
}, {
title: "Test2",
content: "file2.html"
}, {
title: "Test3",
content: "file3.html"
}];
}]);
</script>
<div ng-app="myApp">
<div ng-controller="AccordionCtrl as vm">
<div>outside accordion {{vm.filteredCampaigns}} </div>
<input type="text" ng-model="q" placeholder="filter" />
<accordion class="accordion" close-others="true">
<div>inside accordion{{vm.filteredCampaigns}}</div>
<accordion-group ng-repeat="campaign in vm.filteredCampaigns=(vm.campaigns | filter:q)">
<accordion-heading>
<h3>{{campaign.title}}</h3>
</accordion-heading>
<p>{{campaign.content}}</p>
</accordion-group>
</accordion>
</div>
</div>
Upvotes: 4
Reputation: 1758
<accordion>
creates an isolated scope and the filteredCampaigns
are only available in that scope, not in the parent scope. To add it to the parent scope, you use $parent
:
ng-repeat="campaign in $parent.filteredCampaigns=(campaigns | filter:q)">
Another solution would be creating an creating an object an object in the parent scope with a parameter for the filteredCampaings:
// AccordionCtrl
$scope.filteredValues = {
filteredCampaings: []
};
ng-repeat="campaign in filteredValues.filteredCampaigns=(campaigns | filter:q)"
Upvotes: 1
Reputation: 17064
Since you're using it outside of the ng-repeat
, you can't see that variable as ng-repeat
creates its own scope.
You can use the controller and use the filter manually to retrieve the filtered objects:
$scope.getFilteredCampaings = function () {
$scope.filteredCampaigns = $filter('filter')($scope.campaigns, $scope.q);
return $scope.filteredCampaigns;
}
Upvotes: 0