angularjs comparte la configuración de datos entre los controladores

Me pregunto cuál podría ser una buena forma de compartir directivas entre controladores. Tengo, por ejemplo, dos directivas para usar en diferentes controladores con diferente configuración, la primera creo que pensé en usar como:

//html  
//js .controller('MainCtrl', function ($scope,$upload) { /*File upload config*/ $scope.onFileSelect = function($files) { for (var i = 0; i < $files.length; i++) { var file = $files[i]; $scope.upload = $upload.upload({ url: 'server/upload/url', method: 'POST', data: {myObj: $scope.myModelObj}, file: file, }).progress(function(evt) { console.log('percent: ' + parseInt(100.0 * evt.loaded / evt.total)); }).success(function(data, status, headers, config) { console.log(data); }); } }; /* Datepicker config */ $scope.showWeeks = true; $scope.minDate = new Date(); $scope.open = function($event) { $event.preventDefault(); $event.stopPropagation(); $scope.opened = true; }; $scope.dateOptions = { 'year-format': "'yy'", 'starting-day': 1 }; $scope.format = 'MMM d, yyyy'; }) .controller('IndexCtrl', function ($scope) { })

Al hacerlo puedo usar todas las funciones en el controlador de mis hijos pero no me gusta mucho debido a problemas de colisión. Como no puede usar un servicio (no puede usar $ scope en un servicio), las otras alternativas podrían ser crear otra directiva o poner el código en un bloque de ejecución, pero es bastante similar usar un controlador principal, entonces, ¿qué piensa de él? ?

ACTUALIZAR

¿Qué piensas de este enfoque?

 //outside of angular stauff function MyTest(){ this.testScope = function(){ console.log('It works'); } } //inside a controller $scope.ns = new MyTest(); //in the view 

ppp

RIUPDATE esta parece ser la mejor opción 🙂

 MyTest.call($scope); 

Considere el método descrito en esta publicación: Ampliación de controladores AngularJS utilizando el patrón de Mixin

En lugar de copiar sus métodos de un servicio, cree un controlador base que contenga esos métodos, y luego llame a extender en sus controladores derivados para mezclarlos. El ejemplo de la publicación:

 function AnimalController($scope, vocalization, color, runSpeed) { var _this = this; // Mixin instance properties. this.vocalization = vocalization; this.runSpeed = runSpeed; // Mixin instance methods. this.vocalize = function () { console.log(this.vocalization); }; // Mixin scope properties. $scope.color = color; // Mixin scope methods. $scope.run = function(){ console.log("run speed: " + _this.runSpeed ); }; } 

Ahora podemos mezclar AnimalController en DogController:

 function DogController($scope) { var _this = this; // Mixin Animal functionality into Dog. angular.extend(this, new AnimalController($scope, 'BARK BARK!', 'solid black', '35mph')); $scope.bark = function () { _this.vocalize(); // inherited from mixin. } } 

Y luego usa DogController en nuestra plantilla:

 

Dog

Los controladores en este ejemplo están todos en el espacio global y están incluidos en el marcado de la siguiente manera.

       

No lo he probado, pero no veo por qué lo siguiente no funcionaría:

 var myApp = angular.module('myApp', []) .controller('AnimalController', ['$scope', 'vocalization', 'color', 'runSpeed', function ($scope, vocalization, color, runSpeed) { /* controller code here */}]); .controller('DogController', ['$scope', '$controller', function($scope, $controller) { var _this = this; // Mixin Animal functionality into Dog. angular.extend(this, $controller('AnimalController', { $scope: scope, vocalization: 'BARK BARK!', color: 'solid black', runSpeed:'35mph' })); $scope.bark = function () { _this.vocalize(); // inherited from mixin. } }]); 

ver: documentos para el servicio $ controller

Lo que quieres es terrible.

No querrá que sus controladores sepan nada el uno del otro, y mucho menos, que uno tenga acceso a la función del otro. Puedes usar un servicio para lograr eso. En cuanto al uso de directivas, no estoy seguro de qué es exactamente lo que quiere que suceda.

En cuanto a su segunda cosa, puede hacer esto tan fácilmente

 .service('MyTestService', function(){ return { testScope: function(){ console.log('It works'); } }; }) .controller('MyController', ['$scope', 'MyTestService', function($scope, MyTestService){ $scope.testScope = MyTestService.testScope; }]) 

y en su opinión:

 

ppp

Terminé con:

 //service .service('PostUploader',function($upload){ var that = this; var fileReaderSupported = window.FileReader !== null; this.notify = null; this.success = null; this.showAlert = false; this.avatar = ''; this.onFileSelect = function($files) { var $file = $files[0]; var filename = $file.name; this.avatar = filename; var isImage = /\.(jpeg|jpg|gif|png)$/i.test(filename); if(!isImage){ this.showAlert = true; return; } this.showAlert = false; if (fileReaderSupported && $file.type.indexOf('image') > -1) { var fileReader = new FileReader(); fileReader.readAsDataURL($file); fileReader.onload = that.notify; } $upload.upload({ url :'/api/post/upload', method: 'POST', headers: {'x-ng-file-upload': 'nodeblog'}, data :null, file: $file, fileFormDataName: 'avatar' }) .success(that.success) .progress(function(evt) { }) .error(function(data, status, headers, config) { throw new Error('Upload error status: '+status); }) }; this.closeAlert = function() { this.showAlert = false; }; }) //controller /* Uploader post */ $scope.dataUrl = null; $scope.avatar = PostUploader.avatar; $scope.showAlert = PostUploader.showAlert; $scope.onFileSelect = PostUploader.onFileSelect; $scope.closeAlert = PostUploader.closeAlert; PostUploader.notify = function(e){ $timeout(function() { $scope.dataUrl = e.target.result; }); }; PostUploader.success = function(data, status, headers, config) { $timeout(function() { $scope.post.avatar = data.url; }); } $scope.$watch('avatar',function(newVal, oldVal){ if(newVal) { $scope.avatar = newVal; } }); $scope.$watch('showAlert',function(newVal, oldVal){ $scope.showAlert = newVal; $scope.dataUrl = null; }); 

Lo hice porque tengo que hacer lo mismo en la creación y publicación de publicaciones pero, en general, tengo el mismo código repetido. 🙂

Lo único bueno es que el código tiene menos lógica.

solución obvia pero shiny (puede ser)

 (function(window, angular, undefined) { 'use strict'; angular.module('ctrl.parent', []) .run(function ($rootScope) { $rootScope.test = 'My test' $rootScope.myTest = function(){ alert('It works'); } }); })(window, angular); angular.module('app',['ctrl.parent']) .controller('ChildCtrl', function($scope){ }); 

Es fácil y limpio y no ve ningún inconveniente (no es global)

ACTUALIZAR

 'use strict'; (function(window, angular, undefined) { 'use strict'; angular.module('ctrl.parent', []) .controller('ParentController',function (scope) { scope.vocalization = ''; scope.vocalize = function () { console.log(scope.vocalization); }; }); })(window, angular); angular.module('app',['ctrl.parent']) .controller('ChildCtrl', function($scope,$controller){ angular.extend($scope, new $controller('ParentController', {scope:$scope})); $scope.vocalization = 'CIP CIP'; }); 

solo un poco más ordenado y funciona CIP CIP 🙂