অ্যাংুলারজেএস-তে অন্য একটি নিয়ামককে কীভাবে আমি একটি নিয়ামককে ইনজেক্ট করব


97

আমি কৌণিকের কাছে নতুন এবং কীভাবে জিনিসগুলি করব তা নির্ধারণ করার চেষ্টা করছি ...

অ্যাঙ্গুলারজেএস ব্যবহার করে, আমি কীভাবে অন্য একটি নিয়ামকের মধ্যে ব্যবহার করতে একটি নিয়ামক ইনজেক্ট করতে পারি?

আমার কাছে নিম্নলিখিত স্নিপেট রয়েছে:

var app = angular.module("testApp", ['']);

app.controller('TestCtrl1', ['$scope', function ($scope) {
    $scope.myMethod = function () {
        console.log("TestCtrl1 - myMethod");
    }
}]);

app.controller('TestCtrl2', ['$scope', 'TestCtrl1', function ($scope, TestCtrl1) {
    TestCtrl1.myMethod();
}]);

যখন আমি এটি সম্পাদন করি তখন আমি ত্রুটিটি পাই:

Error: [$injector:unpr] Unknown provider: TestCtrl1Provider <- TestCtrl1
http://errors.angularjs.org/1.2.21/$injector/unpr?p0=TestCtrl1Provider%20%3C-%20TestCtrl1

আমি কি অন্য নিয়ামকের অভ্যন্তরে একটি নিয়ামক ব্যবহার করার চেষ্টা করা উচিত, বা আমি এটি একটি পরিষেবা করা উচিত?


4
আপনি একে অপরের মধ্যে কন্ট্রোলার ইনজেক্ট করতে পারবেন না। হ্যাঁ, TestCtrl1পরিবর্তে আপনার কোনও পরিষেবাতে পরিবর্তন করা উচিত ।
স্লি_কার্ডিনাল

হুবহু, পরিষেবাগুলি ব্যবহার করুন
মিগুয়েল মোটা

4
যদি আমার কাছে নিয়ামকের কোনও সম্পত্তি আপডেট করতে হয় যা দেখার সাথে আবদ্ধ হয়। এই সম্পত্তিটি অন্য নিয়ামকের মধ্যে ঘটে যাওয়া ইভেন্ট দ্বারা প্রভাবিত হয়।
অঙ্কিত তন্ন 14

উত্তর:


129

যদি আপনার উদ্দেশ্যটি ইতিমধ্যে অন্য কোনও উপাদানটির ইনস্ট্যান্টিয়েটেড নিয়ন্ত্রককে ধরে রাখা এবং আপনি যদি উপাদান / নির্দেশ ভিত্তিক পদ্ধতির অনুসরণ করেন তবে আপনি সর্বদা requireএকটি নির্দিষ্ট স্তরক্রম অনুসরণকারী অন্য উপাদান থেকে নিয়ামক (কোনও উপাদান উদাহরণ) করতে পারেন ।

উদাহরণ স্বরূপ:

//some container component that provides a wizard and transcludes the page components displayed in a wizard
myModule.component('wizardContainer', {
  ...,
  controller : function WizardController() {
    this.disableNext = function() { 
      //disable next step... some implementation to disable the next button hosted by the wizard
    }
  },
  ...
});

//some child component
myModule.component('onboardingStep', {
 ...,
 controller : function OnboadingStepController(){

    this.$onInit = function() {
      //.... you can access this.container.disableNext() function
    }

    this.onChange = function(val) {
      //..say some value has been changed and it is not valid i do not want wizard to enable next button so i call container's disable method i.e
      if(notIsValid(val)){
        this.container.disableNext();
      }
    }
 },
 ...,
 require : {
    container: '^^wizardContainer' //Require a wizard component's controller which exist in its parent hierarchy.
 },
 ...
});

এখন উপরোক্ত উপাদানগুলির ব্যবহারের কিছু হতে পারে:

<wizard-container ....>
<!--some stuff-->
...
<!-- some where there is this page that displays initial step via child component -->

<on-boarding-step ...>
 <!--- some stuff-->
</on-boarding-step>
...
<!--some stuff-->
</wizard-container>

অনেক উপায়ে আপনি সেট আপ করতে পারেন হয় প্রয়োজন

(উপসর্গ নেই) - বর্তমান উপাদানটিতে প্রয়োজনীয় নিয়ামক সন্ধান করুন। যদি পাওয়া না যায় তবে একটি ত্রুটি নিক্ষেপ করুন।

? - প্রয়োজনীয় নিয়ামকটি সনাক্ত করার চেষ্টা করুন বা পাওয়া না গেলে লিঙ্কটি fn এ নাল পাস করুন।

। - উপাদান এবং এর পিতামাতার অনুসন্ধান করে প্রয়োজনীয় নিয়ামক সন্ধান করুন। যদি পাওয়া না যায় তবে একটি ত্রুটি নিক্ষেপ করুন।

^^ - উপাদানটির পিতামাতাকে অনুসন্ধান করে প্রয়োজনীয় নিয়ামক সন্ধান করুন। যদি পাওয়া না যায় তবে একটি ত্রুটি নিক্ষেপ করুন।

? ^ - উপাদান এবং তার পিতামাতাদের অনুসন্ধান করে প্রয়োজনীয় নিয়ামকটি সনাক্ত করার চেষ্টা করুন বা যদি খুঁজে পাওয়া না যায় তবে লিংকটিতে নাল পাস করুন।

? ^^ - উপাদানটির পিতামাতার অনুসন্ধান করে প্রয়োজনীয় নিয়ামকটি সনাক্ত করার চেষ্টা করুন বা খুঁজে পাওয়া না গেলে লিঙ্কটি নাল পাস করুন।



পুরানো উত্তর:

$controllerঅন্য নিয়ামকের ভিতরে কোনও নিয়ামক ইনস্ট্যান্ট করতে আপনাকে পরিষেবা ইনজেক্ট করতে হবে। তবে সচেতন থাকুন যা এর ফলে কিছু নকশার সমস্যা হতে পারে। আপনি সর্বদা পুনরায় ব্যবহারযোগ্য পরিষেবাগুলি তৈরি করতে পারেন যা একক দায়িত্ব অনুসরণ করে এবং আপনার প্রয়োজনমতো কন্ট্রোলারে ইনজেক্ট করে।

উদাহরণ:

app.controller('TestCtrl2', ['$scope', '$controller', function ($scope, $controller) {
   var testCtrl1ViewModel = $scope.$new(); //You need to supply a scope while instantiating.
   //Provide the scope, you can also do $scope.$new(true) in order to create an isolated scope.
   //In this case it is the child scope of this scope.
   $controller('TestCtrl1',{$scope : testCtrl1ViewModel });
   testCtrl1ViewModel.myMethod(); //And call the method on the newScope.
}]);

যে কোনও ক্ষেত্রে আপনি কল করতে পারবেন না TestCtrl1.myMethod()কারণ আপনি পদ্ধতিটি সংযোজনকারী হিসাবে রেখেছেন $scopeএবং না control

আপনি যদি নিয়ামকটি ভাগ করে নিচ্ছেন তবে সর্বদা এটি করা ভাল -

.controller('TestCtrl1', ['$log', function ($log) {
    this.myMethod = function () {
        $log.debug("TestCtrl1 - myMethod");
    }
}]);

এবং গ্রাস করার সময়:

.controller('TestCtrl2', ['$scope', '$controller', function ($scope, $controller) {
     var testCtrl1ViewModel = $controller('TestCtrl1');
     testCtrl1ViewModel.myMethod();
}]);

প্রথম ক্ষেত্রে সত্যই $scopeআপনার ভিউ মডেল, এবং দ্বিতীয় ক্ষেত্রে এটি নিয়ামক উদাহরণ নিজেই।


4
এবং এটি নিয়ন্ত্রণকারীর সরবরাহিত কার্যকারিতার উপর নির্ভর করে, আপনি যদি এমন একটি ভিউ মডেলের মতো তৈরি করে থাকেন যা আপনাকে উপাদানটি জুড়ে ভাগ করে নিতে হবে তবে এটি ঠিক আছে তবে যদি এটি কোনও পরিষেবা সরবরাহকারীর কার্যকারিতা বেশি করে থাকে তবে আমি কেবল একটি পরিষেবা তৈরি করে যাব ।
পিএসএল

হওয়া var testCtrl1ViewModel = $scope.$new();উচিত var testCtrl1ViewModel = $rootScope.$new();? দেখুন: ডকস.আঙ্গুলারজস.আর / গাইড
কনট্রোলার

উপরের উদাহরণে আপনি নির্দেশিকা নিয়ামকের উপর ধারক অ্যাক্সেস করছেন তবে আমি এটি কাজ করতে পারি না। আমি নিজেই নির্দেশে আমার লিঙ্ক ফাংশনে চতুর্থ প্যারামিটারের মাধ্যমে প্রয়োজনীয় নিয়ন্ত্রকদের অ্যাক্সেস করতে পারি। তবে তারা উপরের উদাহরণের মতো নির্দেশিকা নিয়ন্ত্রকের কাছে আবদ্ধ নয়। অন্য কেউ এই সমস্যা আছে?
সম্মি

33

আপনি যে প্রশ্নটি জিজ্ঞাসা করবেন তা আমি পরামর্শ দিতে চাই যে কীভাবে নিয়ন্ত্রণকারীদের মধ্যে পরিষেবাগুলি ইনজেক্ট করা যায়। চর্মসার নিয়ন্ত্রকদের সাথে ফ্যাট পরিষেবাগুলি থাম্বের একটি ভাল নিয়ম, ওরফে আপনার পরিষেবা / কারখানাকে (ব্যবসায়িক যুক্তি সহ) আপনার দৃষ্টিভঙ্গিতে আঠালো করার জন্য কন্ট্রোলার ব্যবহার করুন।

কন্ট্রোলাররা রুট পরিবর্তনে আবর্জনা সংগ্রহ করে, সুতরাং উদাহরণস্বরূপ, আপনি যদি ব্যবসায়িক যুক্তি ধরে রাখার জন্য নিয়ন্ত্রণকারীদের ব্যবহার করেন যা কোনও মানকে রেন্ডার করে, যদি অ্যাপ্লিকেশন ব্যবহারকারী ব্রাউজারের পিছনে বোতামটি ক্লিক করেন তবে দুটি পৃষ্ঠায় আপনার রাজ্য হারাতে চলেছেন।

var app = angular.module("testApp", ['']);

app.factory('methodFactory', function () {
    return { myMethod: function () {
            console.log("methodFactory - myMethod");
    };
};

app.controller('TestCtrl1', ['$scope', 'methodFactory', function ($scope,methodFactory) {  //Comma was missing here.Now it is corrected.
    $scope.mymethod1 = methodFactory.myMethod();
}]);

app.controller('TestCtrl2', ['$scope', 'methodFactory', function ($scope, methodFactory) {
    $scope.mymethod2 = methodFactory.myMethod();
}]);

এখানে দুটি নিয়ামককে ইনজেক্ট করা কারখানার একটি কার্যকারী ডেমো রয়েছে

এছাড়াও, আমি পরিষেবাগুলি / কারখানার উপর এই টিউটোরিয়ালটি পড়ার পরামর্শ দেব


13

জেএস-এ আপনার নিয়ামকটি আমদানি / ইনজেকশন করার দরকার নেই। আপনি কেবল আপনার এইচটিএমএল এর মাধ্যমে আপনার নিয়ামক / নেস্টেড নিয়ামককে ইনজেক্ট করতে পারেন t এটি আমার পক্ষে কাজ করেছে। পছন্দ:

<div ng-controller="TestCtrl1">
    <div ng-controller="TestCtrl2">
      <!-- your code--> 
    </div> 
</div>

4
সত্য ... তবে আমি এখনও সমস্ত সাধারণ উপাদানগুলিকে একটি পরিষেবাদি হিসাবে স্থাপন এবং পরিষেবাটি নিয়ন্ত্রকের কাছে ইনজেকশনের চেয়ে ভাল অনুভব করি।
নীল

-1
<div ng-controller="TestCtrl1">
    <div ng-controller="TestCtrl2">
      <!-- your code--> 
    </div> 
</div>

এটি আমার ক্ষেত্রে সবচেয়ে ভাল কাজ করে, যেখানে TestCtrl2 এর নিজস্ব নির্দেশিকা রয়েছে।

var testCtrl2 = $controller('TestCtrl2')

এটি আমাকে স্কোপপ্রাইডার ইঞ্জেকশন ত্রুটি বলে ত্রুটি দেয়।

   var testCtrl1ViewModel = $scope.$new();
   $controller('TestCtrl1',{$scope : testCtrl1ViewModel });
   testCtrl1ViewModel.myMethod(); 

আপনার যদি 'TestCtrl1' তে দিকনির্দেশনা থাকে তবে এটি সত্যিই কাজ করে না, সেই নির্দেশিকার এখানে আসলে তৈরি করা এইটির থেকে আলাদা সুযোগ রয়েছে। আপনি 'টেস্টসিআরটিএল 1' এর দুটি উদাহরণ দিয়ে শেষ করেছেন।


-1

সবচেয়ে ভালো সমাধান:-

angular.module("myapp").controller("frstCtrl",function($scope){$scope.name="Atul Singh";}).controller("secondCtrl",function($scope){angular.extend(this, $controller('frstCtrl', {$scope:$scope}));console.log($scope);})

// এখানে আপনি এটি সম্পাদন না করেই প্রথম নিয়ন্ত্রণকারী কল পেয়েছেন


-1

আপনি $rootScopeএই জাতীয় দ্বিতীয় নিয়ামক থেকে 1 তম নিয়ামকের একটি ফাংশন / পদ্ধতি কল করতেও ব্যবহার করতে পারেন ,

.controller('ctrl1', function($rootScope, $scope) {
     $rootScope.methodOf2ndCtrl();
     //Your code here. 
})

.controller('ctrl2', function($rootScope, $scope) {
     $rootScope.methodOf2ndCtrl = function() {
     //Your code here. 
}
})

4
ডাউনভোট: এটি কেবল খারাপ কোডিং: আপনি কেবল নিজের ফাংশনটি বিশ্বব্যাপী তৈরি করছেন। আপনি কোড করতে চান এমনভাবেই কৌনিকটি পুরোপুরি ড্রপ করুন ... অন্যান্য উত্তরগুলির বেশিরভাগের পরামর্শ অনুসারে কোনও পরিষেবা ব্যবহার করুন।
হামারএনএল

এটি সুপারিশ করা হয় না। $ রুটস্কোপ কোড আনাড়ি তৈরি করে এবং দীর্ঘমেয়াদে সমস্যার দিকে পরিচালিত করে।
হর্ষিত পান্ত

-2

আপনার কোডিংয়ের জন্য টাইপস্ক্রিপ্ট ব্যবহার করুন, কারণ এটি অবজেক্ট অরিয়েন্টেড, কঠোরভাবে টাইপ করা হয়েছে এবং কোড বজায় রাখা সহজ ...

টাইপসসিপ্ট সম্পর্কে আরও তথ্যের জন্য এখানে ক্লিক করুন

টাইপসক্রিপ্ট ব্যবহার করে দুটি নিয়ামকের মধ্যে ডেটা ভাগ করতে আমি এখানে একটি সাধারণ উদাহরণ তৈরি করেছি ...

module Demo {
//create only one module for single Applicaiton
angular.module('app', []);
//Create a searvie to share the data
export class CommonService {
    sharedData: any;
    constructor() {
        this.sharedData = "send this data to Controller";
    }
}
//add Service to module app
angular.module('app').service('CommonService', CommonService);

//Create One controller for one purpose
export class FirstController {
    dataInCtrl1: any;
    //Don't forget to inject service to access data from service
    static $inject = ['CommonService']
    constructor(private commonService: CommonService) { }
    public getDataFromService() {
        this.dataInCtrl1 = this.commonService.sharedData;
    }
}
//add controller to module app
angular.module('app').controller('FirstController', FirstController);
export class SecondController {
    dataInCtrl2: any;
    static $inject = ['CommonService']
    constructor(private commonService: CommonService) { }
    public getDataFromService() {
        this.dataInCtrl2 = this.commonService.sharedData;
    }
}
angular.module('app').controller('SecondController', SecondController);

}

আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.