2015-04-17 2 views
0

Использование директив, которые я закончил, застрял, когда мне нужно было иметь несколько областей. Я создаю приложение для визуализации данных с Mongoose Node, Express и D3JS.Как бороться с более чем одной областью в Угловой директиве?

Вот директива

angular.module('prodsChart', []) 
.controller('businessCtrl', ['$scope','$http', 'BusinessSrv', 'Products', function($scope, $http, $location, BusinessSrv, Products) { 

    Products.get() 
     .success(function(data) { 
      $scope.products = data; 
     }); 

    BusinessSrv.getTotal() 
     .success(function(data) { 
      $scope.businessSales = data; 
     }); 
}]) 

.directive('saleProd', [ 
    function() { 
     return { 
      restrict: 'E', 
      link: function (scope, element) { 

      // Building the chart here 

      } 

И HTML:

<sale-prod></sale-prod> 

Хорошо ли вводить таким образом услуги в директиве?

Теперь у меня есть 2 набора данных в двух $ -области. Как использовать их в директиве?

+1

Более предпочтительным является использование общей службы между контроллерами и директивами – IvanMalenko

+0

@IvanMalenko Я обновил мой Вопрос: должен ли я так поступать? Но тогда, как мне получить доступ к 2 наборам данных в Директиве? Прежде чем я использовал изолированную область действия, но на самом деле не нуждался в ней, так как мне не нужна двусторонняя привязка данных. – adnpwd

+0

Не уверен, правильно ли я понял вопрос, но мне кажется, что вы можете создать 2 разных объекта для хранения данных и затем привязать эти объекты к области видимости. 'Сфера.dataObject1 = {someData: firstData, moreData: secondData} '. Вы можете создать столько объектов, сколько хотите. – BobDoleForPresident

ответ

0

В директиве 1-го и 2-го порядка находится область действия контроллера и наборы данных контроллера, переданные в директивы в качестве атрибутов. В 1-м примере директива может изменять данные контроллера. Во втором примере директива использует данные контроллеров как строки и создает 2 объекта 'productsObj' и 'salesObj' и не может изменять область родителя. Это зависит от того, как вы обрабатываете атрибуты в директиве и как их переносить в нее. Просто нажмите на элементы в разделе «Список продуктов (директивы)», и вы увидите результат.

первый: http://plnkr.co/edit/v46oEGHvUnxMNYsKAeaW?p=preview

var directive = function() { 
    return { 
     restrict: 'E', 
     replace: true, 
     templateUrl: 'directive-template.html', 
     scope: { 
      products: '=', 
      sales: '=' 
     } 
    }; 
}; 

HTML:

<div ng-controller="BusinessController as BusinessCtrl"> 
    <sale-prod products="BusinessCtrl.products" sales="BusinessCtrl.sales"></sale-prod> 
</div> 

второй: http://plnkr.co/edit/7CyIsqBNLbeZjyfbkGo9?p=preview

var directive = function() { 
    return { 
     restrict: 'E', 
     replace: true, 
     templateUrl: 'directive-template.html', 
     scope: { 
      products: '@', 
      sales: '@' 
     }, 
     link: function(scope, element, attrs) { 
      attrs.$observe('products', function(newVal) { 
       scope.productsObj = angular.fromJson(newVal); 
      }); 

      attrs.$observe('sales', function(newVal) { 
       scope.salesObj = angular.fromJson(newVal); 
      }); 
     } 
    }; 
}; 

HTML:

<div ng-controller="BusinessController as BusinessCtrl"> 
    <sale-prod products="{{BusinessCtrl.products}}" sales="{{BusinessCtrl.sales}}"></sale-prod> 
</div> 

3-й пример - это всего лишь фрагмент кода, в котором показано, как ввести службу в директиву и контроллер. Я добавляю, потому что в вас, например я не видел инъекции службы в директиве:

(function(undefined) { 
    var app = angular.module('prodsChart', []); 

    var controller = function($scope, Business, Products) { 
     // controller logic 
    }; 

    var directive = function(Business) { 
     return { 
      restrict: 'E', 
      link: function(scope, element, attrs) { 
       // here you can use all Business service logic 
      } 
     }; 
    }; 

    var serviceBusiness = function() { 
     // business service logic 
    }; 

    var serviceProducts = function() { 
     // products service logic 
    }; 

    app.controller('BusinessController', ['$scope', 'Business', 'Products', controller]) 
     .directive('saleProd', ['Business', directive]) 
     .service('Business', serviceBusiness) 
     .service('Products', serviceProducts); 
})(); 

HTML:

<div ng-controller="BusinessController as BusinessCtrl"></div> 
<sale-prod></sale-prod> 
+0

Спасибо за этот подробный ответ, это очень помогает. Просто последнее, когда вы пишете '', он использует массив из контроллера, но у меня уже есть все мои данные в $ scope. Нужно ли мне передавать данные таким образом, или я могу использовать $ scope в директиве? – adnpwd

+0

@adnpwd Вам нужно узнать больше о областях и иерархиях областей. Прочтите эту статью https://docs.angularjs.org/guide/scope. Короче говоря, области директив и контроллеров ссылаются на разные модели. Вы также можете использовать этот ресурс, чтобы узнать больше http://www.youtube.com/channel/UCbn1OgGei-DV7aSRo_HaAiw – IvanMalenko

1

Вы можете вводить $rootScope в вашу директиву:

angular.module('prodsChart', []) 
    .directive('saleProd', ['$rootScope', function ($rootScope) { 
    // your code here 
}]); 

, а затем использовать его везде в пределах директивы.

+0

На самом деле я попытался ввести «$ rootScope», но я не смог получить данные. Я пробовал это в функции ссылок, без результата: 'var toto = $ rootScope.businessSales; console.log (toto); ' – adnpwd

+0

Вы уверены, что привязываете свойство' businessSales' к '$ rootScope' до функции ссылки? –

+0

Не уверен, что вы имеете в виду, свойство 'businessSales' задано в контроллере в отдельном модуле – adnpwd

0

Вы можете ввести Сервис в директиву и использовать его для переноса данных через приложение или использовать $emit.

Менее элегантное решение будет использовать .value() и иметь дело с ним повсюду в вашем приложении.