Javascript 为什么我的组件绑定在其控制器中未定义?

Javascript 为什么我的组件绑定在其控制器中未定义?,javascript,angularjs,angularjs-1.5,Javascript,Angularjs,Angularjs 1.5,我在写一个简单的角度分量。我将一个参数作为绑定传递,并在屏幕上显示其值。一切正常:我可以看到屏幕上显示的参数 组成部分: var app = angular.module("test", []); app.component("test", { bindings: { "contactId": "<" }, controllerAs: "model", controller: () => { //output: 'contact id from con

我在写一个简单的角度分量。我将一个参数作为绑定传递,并在屏幕上显示其值。一切正常:我可以看到屏幕上显示的参数

组成部分:

var app = angular.module("test", []);
app.component("test", {
  bindings: {
    "contactId": "<"
  },
  controllerAs: "model",
  controller: () => {
    //output: 'contact id from controller: undefined'
    console.log(`contact id from controller: ${this.contactId}`);
  },
  template: "<div>Contact id from view: {{model.contactId}}</div>"
});
var-app=angular.module(“测试”,[]);
应用程序组件(“测试”{
绑定:{

“联系人ID”:"当使用angular的组件时,有一点控制器没有通过内部链接进行连接。如果您试图在控制器的构造函数中执行此操作,则没有链接到绑定。组件API公开了一些生命周期挂钩,您可以定义这些挂钩,这些挂钩将在特定时间触发。您正在寻找或者
$onInit
钩子

$onInit()-在构造元素上的所有控制器并初始化其绑定之后(以及在此元素上的指令的前置和后置链接函数之前),调用每个控制器。这是放置控制器初始化代码的好地方


根据文档-

关键字这似乎不适用于箭头功能,这适用于

controller: function() {
   alert('contact id from controller: ' + this.contactId);
}
使用箭头功能时,这似乎是指窗口对象,因为

arrow函数不会创建它自己的上下文,而是创建它自己的上下文 捕获封闭上下文的此值


contactId
的值可在控制器中的
$scope
上找到:

var app = angular.module("test", []);
app.component("test", {
  bindings: {
    "contactId": "<"
  },
  controllerAs: "model",
  controller: ($scope) => {
    var model = $scope.model;
    alert(`contact id from controller: ${model.contactId}`);
  },
  template: "<div>Contact id from view: {{model.contactId}}</div>"
});
var-app=angular.module(“测试”,[]);
应用程序组件(“测试”{
绑定:{

“contactId”:“确保在HTML中使用连字符进行绑定,在Javascript中使用camelCase进行绑定

app.component("test", {
  bindings: {
    "myContactId": "<"
  }
}

<test my-contact-id="8"></test>
app.component(“测试”{
绑定:{

“myContactId”:“这可能不是最佳实践,但您可以更轻松地访问这些值:

$scope.$ctrl.contactId
您可以在$scope内获取属性$ctrl中的所有绑定


我希望它能帮助你

我会建议一些你真正需要的改变,以避免这些不寻常的错误

app.component("test", {
  bindings: {
    "myContactId": "<"
  },
  controller:function(){
   var self=this;
   this.$onInit=function(){
    // do all your initializations here.
    // create a local scope object for this component only. always update that scope with bindings. and use that in views also.

       self.myScopeObject=self.myContactId
   }
  },
   template:'<p>{{$ctrl.myScopeObject}}</p>'
 }

<test my-contact-id="8"></test>
app.component(“测试”{
绑定:{

“myContactId”:“对于那些使用指令的人,假设组件,如果指定了绑定{},那么将这些相同的参数添加到作用域{}工作:

/*bindings: {
    modalInstance: '<',
    resolve: '<'
},*/
scope: {
    modalInstance: '<',
    resolve: '<'
},
/*绑定:{

modalInstance:“我将添加另一个答案,作为@jusopi和已接受答案的后续,仅针对那些可能遇到我问题的人。对于组件,即使在
$onInit
钩子之后,我的数据仍然为空,因为仍然没有收到来自服务器的值。为了抵消这一点(虽然可能有更好的方法来处理这种情况),我还利用了
$onChanges
钩子。
$onChanges
将在传递时返回已更改的数据,您可以解析该信息,或者简单地将绑定称为
this.contactId
,然后它将被更新


更多详细信息请参见:

代码中有两个问题导致“未定义”错误

  • 如上所述,首先应该到达$onInit生命周期钩子,当所有绑定完成时,将触发onInit
  • 从官方文件:

    $onInit()-在一个控制器上的所有控制器之后对每个控制器调用 元素已构造并已初始化其绑定(和 在此基础上的指令的前置和后置链接功能之前 元素)。这是一个放置初始化代码的好地方 控制器

  • 您可能遇到的第二个问题是,当使用“()=>”箭头符号作为控制器函数的参数时,控制器将无法到达lifecyclehook
  • 问题是箭头符号没有自己的作用域,而是使用它的封闭作用域。 这意味着当使用“this”时,将引用窗口对象而不是组件。
    这么说吧。$onInit()将在窗口上被调用,并且不会被激发,因为它在窗口上不存在。

    为什么我们在使用箭头函数样式时不能使用此关键字?您可以将此
    与箭头函数样式一起使用,但我认为在这种情况下,
    此.contactId
    还不可用,原因是@jusopi提到的。如果您如果有API方法,例如someController.prototype.someMethod,
    应该具有您期望的功能。正如@jusopi所提到的,执行顺序不会在构造函数中填充
    (非原型)正如预期的那样。我尝试了一个超时,但它不起作用。正如我前面所说,arrow函数不创建它自己的这个上下文,而是捕获封闭上下文的this值。因此,使用arrow函数,它指的是窗口对象,而不是控制器。很有趣。我没有意识到-谢谢!在这种情况下,不管有趣与否Action语法,
    $scope
    注入将解决OP提出的问题。用户1058612-感谢您的示例,学到了很多。不过,您确实尝试过(希望如此)正如你所说的-不适用于我。有没有可能是1.7.9的问题-这个版本有更改,但我是新来的。任何帮助都可以-谢谢你,我认为你是对的,应该使用
    $onInit
    。这对我很有效:`var vm=this;vm.$onInit=function(){console.log('loaded on init');console.log('vm',vm.YOUR_绑定);console.log('defyes',angular.isDefined(vm.YOUR_绑定));}ode>ng if
    指令,以确保在组件初始化之前拥有数据(例如
    )修复了该问题。“…在一个元素上的所有控制器都已构造完成后
     bindings:{
          value:'@',
          object:'<', // also known as one-way
          twoWay:'='
        }
    
    /*bindings: {
        modalInstance: '<',
        resolve: '<'
    },*/
    scope: {
        modalInstance: '<',
        resolve: '<'
    },