How to pass a object into directive controller in AngularJs - angularjs

I have a directive called dealEngine which has template and controller and is working fine.
however as you can see I'm trying to collect the object from attribute and pass it into my controller! so far I either get undefined or "string".
(function () {
'use strict';
angular
.module('app')
.directive('dealEngine', dealEngine)
.controller("dealEngineCtrl", dealEngineCtrl);
dealEngine.$inject = ['$state'];
function dealEngine($state) {
return {
restrict: 'E',
replace: 'true',
cache:'false',
controller: 'dealEngineCtrl',
templateUrl: 'directives/deal/deal.html',
scope:{
"deal":"="
}
};
}
dealEngineCtrl.$inject = ['$scope','$attrs', '$element'];
function dealEngineCtrl($scope, $attrs, $element) {
console.log($attrs.deal); //this returns "vm.deal" string!!!
console.log($scope.deal); //this returns undefined!!!
}
})();

Related

Angular directive not triggered on dynamic element

I have a directive (DirectiveA), which makes an $http call and creates a new html code.
directiveA
(function(){
angular.module('app').directive('directiveA', directiveA);
})();
(function(){
angular.module('app').controller('DirectiveAController', DirectiveAController);
})();
function directiveA($timeout){
return {
restrict: 'E',
scope: {
url:'#'
},
template: '<div ng-if="template" ng-bind-html="template"></div>',
link: function ( scope, element, attrs ) {
scope.element = element;
},
controller: DirectiveAController
};
}
directiveA.$inject = ['$timeout']
function DirectiveAController($scope, $http, $sce){
$http.get(`${$scope.url}`).then(function(res){
if(res.success){
$scope.template = $sce.trustAsHtml(res.template);
}
});
}
DirectiveAController.$inject = ['$scope', '$http','$sce'];
this works fine.
On the new created element, i want to capture the click function using another directive.
Directive 2
(function(){
angular.module('mcq').directive('captureClick', captureClick);
})();
function captureClick($timeout, $compile){
return {
link: function ( scope, element, attrs ) {
console.log("i am called") // Working on page load but not on dynamic element
scope.element = element;
},
};
}
captureClick.$inject = ['$timeout', '$compile'];
response.template
<button capture-click></button>
Rendered a dummy element of response.template (as static content) and the directive works. How can i get it work on dynamically rendered element.
Using compile my directive is picked up.
(function(){
angular.module('app').directive('directiveA', directiveA);
})();
(function(){
angular.module('app').controller('DirectiveAController', DirectiveAController);
})();
function directiveA($timeout){
return {
restrict: 'E',
scope: {
url:'#'
},
template: '',
link: function ( scope, element, attrs ) {
scope.element = element;
},
controller: DirectiveAController
};
}
directiveA.$inject = ['$timeout']
function DirectiveAController($scope, $http, $sce, $compile){
$http.get(`${$scope.url}`).then(function(res){
if(res.success){
var com = $compile(res.template)($scope);
$scope.element.append(com[0].outerHTML);
}
});
}
DirectiveAController.$inject = ['$scope', '$http','$sce', '$compile'];
Note sure, this is the correct way and has any cons

Angular directive controller scope

I'm trying to develop a directive that has it's own controller so it can collect the data it need's from the API and be injected anywhere.
Here's what I got so far:
(function () {
'use strict';
angular
.module('app.hostelsmg.bookings')
.directive('bookingsChart', bookingsChart);
function bookingsChart() {
return {
restrict: 'E',
scope: true,
controller: [function(){
$scope.test = 'Hi there!';
}],
compile: function(tElem, attrs){
tElem.html('{{test}}');
return function(scope, elems, attrs){
}
}
}
}
})();
So what I'd like, is the directive to get data from it's own controller. So far I couldn't get it to work that way.
Does anyone know how?
You can use something like this
function bookingsChart() {
return {
restrict: 'E',
scope: true,
controller: ['$scope', 'yourservice', function ($scope, yourservice) {
$scope.data = []; //bind this data to your view
$scope.getServiceData = function (count) {
//your service call
yourservice.getServiceData(count).then(function (data) {
$scope.data = data; //sets data in $scope.data variable
});
}
}],
link: function (scope, elements, attributes) {
//if you want to pass any parameters from your UI to your service method
scope.getServiceData(attributes.count); //calls the getServiceData in controller defined above
}
}
}

How to watch controller asynchronous data in angular directive

I define a directive in angular 1.4,which receives a scope parameter “b”:
(function() {
'use strict';
angular
.module('m')
.directive('mydirective', mydirective);
/** #ngInject */
function mydirective() {
var directive = {
restrict: 'E',
templateUrl: 'app/components/mydirective/mydirective.html',
scope: {
b: '='
},
controller: MydirectiveController,
controllerAs: 'vm',
bindToController: true
};
return directive;
/** #ngInject */
function MydirectiveController($scope, $state) {
var vm = this;
//here How to watch the parameter b to refresh the directive html result?
}
in html page:
<mydirective b="ctrl.b"></myupl>
in the business controller, b is got from an angular resource
PayService.getBusinessNumber().then(function(results){
vm.b = {business_id: results.no};
});
in index.route.js which define the route and the business controller,
$stateProvider
.state('payShowInfo', {
url: '/payShowInfo',
templateUrl: 'app/pay_show_info.html',
controller: 'PayShowController',
controllerAs: 'ctrl'
});
my problem is , When the directive loaded, the parameter “b” is undefined,  How to watch controller asynchronous data in angular directive? and then use the new value of “b” to refresh the html page?
If you define the directive parameter as "=", you mean that you will have two way data binding. So if you change the value in the controller, you will have the change reflected in the view.
angular.module('nib', [])
.directive('mydirective', function ($timeout) {
return {
restrict: 'E',
scope: {
b: '='
},
link: function ($scope, element, attrs) {
},
template: '<div>Test: {{b}}</div>'
};
})
.controller('ctrl',function($scope){
$scope.click = function(){ // emulating asynchronous request
$scope.test = 'testing';
}
})
See in the plnkr below:
http://plnkr.co/3qs1NpU1aIhKzxyCMXjh?p=preview

Custom directive should pass function to parent scope?

I have a search box which I want to use as a custom directive. This is the code for it :
(function(angular) {
'use strict';
angular.module('searchApp', [])
.directive('searchBox', function () {
return {
restrict: 'E',
transclude: true,
scope: {
'btnclick': '&onClick'
},
link: function(scope, elem, attrs) {
});
});
},
templateUrl: 'search-box.html'
}
});
})(window.angular);
In the link part, I need a function that has some JSON data. And then, a directive should have a controller that invokes that function and passes it to the parent scope.
Please show me code for the link function and the controller.

Angular call directive function from template

I'm new to angular and can't figure out how to call a directive function from the template. I have some fuctionality that will be reused throught the app and figured I would just make a directive with all the functionlity needed, that can easily be shared accross different modules. While searching for answers I came across this post: how-to-call-a-method-defined-in-an-angularjs-directive
which seems like a good solution. However, I can't seem to figure out why my directive method showPolicy() is not being called.
// controller:
(function(){
'use strict';
angular.module('releaseAppsModule')
.controller('releaseAppsController', releaseAppsController);
releaseAppsController.$inject = ['$rootScope',
'storageFactory',
'releaseAppsFactory',
'$modal',
'$translate',
'getIconFactory',
'$scope',
'$filter'];
function releaseAppsController($rootScope, storageFactory, releaseAppsFactory, $modal, $translate, getIconFactory, $scope, $filter) {
var vm = this;
vm.policyControl = {};
...
// controller template:
<tr ng-repeat="policyRelease in regionRelease.policyReleases | orderBy:vm.orderByField:vm.reverseSort" ng-if="policyRelease.status == 'NEW' || policyRelease.status == 'SCHEDULED'">
<td>
<policy control="vm.policyControl" release-item="policyRelease" class="release-apps-app-btn app-release-data"></policy>
</td>
// directive:
(function(){
'use strict';
angular.module('myApp')
.directive('policy', policy)
function policy() {
var directive = {
restrict: 'E',
link: link,
replace: true,
scope: {
releaseItem: '=',
control: '='
},
template: '<a ng-click="vm.policyControl.showPolicy({releaseItem: releaseItem});">{{ releaseItem.policy.name }}</a>'
};
return directive;
function link(scope, el, attr) {
scope.internalControl = scope.control || {};
scope.internalControl.showPolicy = function (releaseData) {
...
} // showPolicy
scope.internalControl.showPolicyModal = function(response, releaseData) {
...
} // showPolicyModal
} // link
} // policy
})();
In your template, you're trying to call vm.policyControl.showPolicy() which is undefined on your current directive scope, as Angular is attempting to find
[directiveScope].vm.policyControl.showPolicy()
You'll need to change the ng-click function to internalControl.showPolicy(), as that is referencing the actual object that the directive's scope has available.

Resources