Angular를 연장하는 권장 방법은 무엇입니까?JS 컨트롤러?
비슷한 컨트롤러가 3개 있습니다.나는 이 세 개가 확장되어 그 기능을 공유하는 컨트롤러를 갖고 싶다.
컨트롤러를 확장하지 않을 수도 있지만 컨트롤러를 확장하거나 단일 컨트롤러를 여러 컨트롤러로 혼재시킬 수도 있습니다.
module.controller('CtrlImplAdvanced', ['$scope', '$controller', function ($scope, $controller) {
// Initialize the super class and extend it.
angular.extend(this, $controller('CtrlImpl', {$scope: $scope}));
… Additional extensions to create a mixin.
}]);
부모 컨트롤러가 생성되면 부모 컨트롤러에 포함된 로직도 실행됩니다.$ 내용은 $controller()를 참조하십시오$scope
값을 전달해야 합니다.하다
@mwaren, 당신의 관심사는 Angular dependency injection에 의해 자동으로 처리된다.$scope를 주입하기만 하면 됩니다.단, 필요에 따라 주입된 다른 값을 덮어쓸 수도 있습니다.다음 예를 들어 보겠습니다.
(function(angular) {
var module = angular.module('stackoverflow.example',[]);
module.controller('simpleController', function($scope, $document) {
this.getOrigin = function() {
return $document[0].location.origin;
};
});
module.controller('complexController', function($scope, $controller) {
angular.extend(this, $controller('simpleController', {$scope: $scope}));
});
})(angular);
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.3.15/angular.js"></script>
<div ng-app="stackoverflow.example">
<div ng-controller="complexController as C">
<span><b>Origin from Controller:</b> {{C.getOrigin()}}</span>
</div>
</div>
$document는 complexController' $document가 생성될 때 simpleController로 전달되지 않지만, 우리는 $document를 대신 주입합니다.
자바스크립트, 여기 입니다. '', '데모하다', '데모하다'를 합니다.$injector
function Parent($scope) {
$scope.name = 'Human';
$scope.clickParent = function() {
$scope.name = 'Clicked from base controller';
}
}
function Child($scope, $injector) {
$injector.invoke(Parent, this, {$scope: $scope});
$scope.name = 'Human Child';
$scope.clickChild = function(){
$scope.clickParent();
}
}
Child.prototype = Object.create(Parent.prototype);
★★★★★★★★★★★★★★★를 사용하는 경우controllerAs
권장에서는 기존의 패턴을 .
function BaseCtrl() {
this.name = 'foobar';
}
BaseCtrl.prototype.parentMethod = function () {
//body
};
function ChildCtrl() {
BaseCtrl.call(this);
this.name = 'baz';
}
ChildCtrl.prototype = Object.create(BaseCtrl.prototype);
ChildCtrl.prototype.childMethod = function () {
this.parentMethod();
//body
};
app.controller('BaseCtrl', BaseCtrl);
app.controller('ChildCtrl', ChildCtrl);
또 다른 방법은 기본 컨트롤러가 되는 "추상" 컨스트럭터 함수만 작성하는 것입니다.
function BaseController() {
this.click = function () {
//some actions here
};
}
module.controller('ChildCtrl', ['$scope', function ($scope) {
BaseController.call($scope);
$scope.anotherClick = function () {
//other actions
};
}]);
글쎄요, 무엇을 달성하고 싶은지는 잘 모르겠습니다만, 보통은 서비스를 이용하는 것이 좋습니다.또한 Angular의 Scope 상속 특성을 사용하여 컨트롤러 간에 코드를 공유할 수 있습니다.
<body ng-controller="ParentCtrl">
<div ng-controller="FirstChildCtrl"></div>
<div ng-controller="SecondChildCtrl"></div>
</body>
function ParentCtrl($scope) {
$scope.fx = function() {
alert("Hello World");
});
}
function FirstChildCtrl($scope) {
// $scope.fx() is available here
}
function SecondChildCtrl($scope) {
// $scope.fx() is available here
}
컨트롤러를 확장하지 않습니다.동일한 기본 기능을 수행하는 경우 해당 기능을 서비스로 이동해야 합니다.이 서비스는 컨트롤러에 주입할 수 있습니다.
이 기사에서 얻은 또 하나의 좋은 해결책은 다음과 같습니다.
// base controller containing common functions for add/edit controllers
module.controller('Diary.BaseAddEditController', function ($scope, SomeService) {
$scope.diaryEntry = {};
$scope.saveDiaryEntry = function () {
SomeService.SaveDiaryEntry($scope.diaryEntry);
};
// add any other shared functionality here.
}])
module.controller('Diary.AddDiaryController', function ($scope, $controller) {
// instantiate base controller
$controller('Diary.BaseAddEditController', { $scope: $scope });
}])
module.controller('Diary.EditDiaryController', function ($scope, $routeParams, DiaryService, $controller) {
// instantiate base controller
$controller('Diary.BaseAddEditController', { $scope: $scope });
DiaryService.GetDiaryEntry($routeParams.id).success(function (data) {
$scope.diaryEntry = data;
});
}]);
주입하는 것만으로 모든 컨트롤러에서 서비스를 생성하고 동작을 상속할 수 있습니다.
app.service("reusableCode", function() {
var reusableCode = {};
reusableCode.commonMethod = function() {
alert('Hello, World!');
};
return reusableCode;
});
다음으로 위의 재사용 가능한 코드서비스에서 확장하는 컨트롤러에서 다음을 수행합니다.
app.controller('MainCtrl', function($scope, reusableCode) {
angular.extend($scope, reusableCode);
// now you can access all the properties of reusableCode in this $scope
$scope.commonMethod()
});
데모 플런커: http://plnkr.co/edit/EQtj6I0X08xprE8D0n5b?p=preview
다음과 같은 것을 시험해 볼 수 있습니다(테스트하지 않았습니다.
function baseController(callback){
return function($scope){
$scope.baseMethod = function(){
console.log('base method');
}
callback.apply(this, arguments);
}
}
app.controller('childController', baseController(function(){
}));
서비스, 공장 또는 공급자를 통해 확장할 수 있습니다.동일하지만 유연성의 정도가 다릅니다.
여기에서는 팩토리를 사용한 예를 나타냅니다.http://jsfiddle.net/aaaflyvw/6KVtj/2/
angular.module('myApp',[])
.factory('myFactory', function() {
var myFactory = {
save: function () {
// saving ...
},
store: function () {
// storing ...
}
};
return myFactory;
})
.controller('myController', function($scope, myFactory) {
$scope.myFactory = myFactory;
myFactory.save(); // here you can use the save function
});
여기서도 스토어 기능을 사용할 수 있습니다.
<div ng-controller="myController">
<input ng-blur="myFactory.store()" />
</div>
$controller('ParentController', {$scope:$scope} 예)를 직접 사용할 수 있습니다.
module.controller('Parent', ['$scope', function ($scope) {
//code
}])
module.controller('CtrlImplAdvanced', ['$scope', '$controller', function ($scope, $controller) {
//extend parent controller
$controller('CtrlImpl', {$scope: $scope});
}]);
Angular "as" 구문을 플레인 JavaScript 상속과 조합하여 사용할 수 있습니다.
자세한 것은, http://blogs.microsoft.co.il/oric/2015/01/01/base-controller-angularjs/ 를 참조해 주세요.
이를 위해 함수를 작성했습니다.
function extendController(baseController, extension) {
return [
'$scope', '$injector',
function($scope, $injector) {
$injector.invoke(baseController, this, { $scope: $scope });
$injector.invoke(extension, this, { $scope: $scope });
}
]
}
다음과 같이 사용할 수 있습니다.
function() {
var BaseController = [
'$scope', '$http', // etc.
function($scope, $http, // etc.
$scope.myFunction = function() {
//
}
// etc.
}
];
app.controller('myController',
extendController(BaseController,
['$scope', '$filter', // etc.
function($scope, $filter /* etc. */)
$scope.myOtherFunction = function() {
//
}
// etc.
}]
)
);
}();
장점:
- 기본 컨트롤러를 등록할 필요가 없습니다.
- 어떤 컨트롤러도 $controller 또는 $injector 서비스에 대해 알 필요가 없습니다.
- 이는 angular의 배열 주입 구문과 잘 연동됩니다. javascript를 최소화할 경우 필수적입니다.
- 기본 컨트롤러에 추가 가능한 서비스를 쉽게 추가할 수 있으며, 모든 하위 컨트롤러에 추가 및 전달해야 하는 번거로움도 없습니다.
단점:
- 베이스 컨트롤러는 변수로 정의해야 합니다.이는 글로벌스코프를 오염시킬 위험이 있습니다.사용 예에서는 모든 것을 익명의 자가 실행 함수로 래핑하여 이를 피했지만, 이는 모든 하위 컨트롤러를 동일한 파일로 선언해야 한다는 것을 의미합니다.
- 이 패턴은 html에서 직접 인스턴스화된 컨트롤러에서는 잘 동작하지만 $controller() 서비스를 통해 코드에서 작성하는 컨트롤러에서는 그다지 좋지 않습니다.이는 인젝터에 의존하기 때문에 호출 코드에서 서비스 이외의 파라미터를 직접 삽입할 수 없기 때문입니다.
컨트롤러를 확장하는 것은 잘못된 관행이라고 생각합니다.차라리 공유 논리를 서비스에 넣으세요.Javascript의 확장 객체는 다소 복잡해지는 경향이 있습니다.상속을 이용하시려면 타이프스크립트를 추천합니다.하지만 제 관점에서는 씬 컨트롤러가 더 나은 방법입니다.
언급URL : https://stackoverflow.com/questions/16539999/whats-the-recommended-way-to-extend-angularjs-controllers
'it-source' 카테고리의 다른 글
.getJ에서 인코딩을 설정하는 방법SON jQuery (0) | 2023.03.17 |
---|---|
visualvm 및 JMX를 사용한 리모트 감시 (0) | 2023.03.17 |
React.js 구성 요소 확장 (0) | 2023.03.17 |
'useState' 후크를 사용할 때 React DevTools를 사용하여 React 다중 상태의 '필드' 이름을 볼 수 있는 방법이 있습니까? (0) | 2023.03.17 |
각도 JS 사용자 지정 구분 기호 (0) | 2023.03.17 |