aplon
aplon

Reputation: 477

Angular 1.5.7 directive two way binding of null object

I have an iscolated scope directive that shares scope with '='. We need to pass an object to the directive. When the object is passed to the directive with it's properties, the directive Works fine and the object, after beeing modified in the directive, is returned correctly to the calling view.

However, when the calling view passes the same object declared as null, even after modifying the object in the directive, the object is returned as null.

The relevant parts of the directive are shown below:

.directive("lookupCentrosDeGestion", function () {
    var _controller = ['centrosDeGestionServices', 'toastr', function (centrosDeGestionServices, toastr) {
        var dvm = this;

        ...

        dvm.rowSelected = function (item) {
            if (!dvm.centroDeGestion)
                dvm.centroDeGestion = {};
            dvm.centroDeGestion.crecodigo = angular.copy(item.crecodigo);
            dvm.centroDeGestion.crenombre = angular.copy(item.crenombre);
            dvm.centroDeGestion.divcodigo = angular.copy(item.divcodigo);
            dvm.centroDeGestion.empRazonSocial = angular.copy(item.empRazonSocial);
            dvm.centroDeGestion.empid = angular.copy(item.empid);
            dvm.centroDeGestion.prynombre = angular.copy(item.prynombre);
            dvm.centroDeGestion.prynumero = angular.copy(item.prynumero);
            dvm.centroDeGestion.unicodigo = angular.copy(item.unicodigo);
            dvm.showMainParent();
        }

        dvm.showMainParent = function () {
            dvm.view.active = dvm.view.returnTo;
        }

    }];

    return {
        restrict: 'E',
        scope: {
            view: '=',
            centroDeGestion: '=',
            centroDeProcesoId: '=',
            centroDeProcesoName: '=',
        },
        link: _link,
        controller: _controller,
        controllerAs: 'dvm',
        bindToController: true,
        templateUrl: '/hr/admin/centrosDeGestion/lookupCentrosDeGestion.html'
    };



})

If a null object is passed to the directive (dvm.centroDeGestion), I creaste a new object and then assign it's properties, however the calling view still receives null.

I would also like to assign the object directly, instead of having to assign each property, but the line dvm.centroDeGestion = angular.copy(ítem) will always return null.

Any ideas on how to resolve these issues?

Thanks in advance

Upvotes: 0

Views: 971

Answers (1)

plong0
plong0

Reputation: 2188

Notes about data-binding in general

You can only bind to a variable. Think about it in terms that you are binding to a location in memory. It is very similar to pointers in C++.

In this case, if you are trying to bind null, you are not pointing to any memory so there is no binding.

Please note that with bindings, if you re-assign the variable, you will break the binding because the caller does not know about the new variable. If you only modify the variable's properties, the caller will still have reference to it and binding will work.

To illustrate, consider this code:

var a = {};
var b = a; // aka data-binding

b.foo = 'bar'; // a.foo == 'bar' (because b === a)

b = {}; // b !== a (whoops! broken binding!)
b.baz = 'biz'; // a.baz == undefined

Looking at your implementation...

Let's say you are using this directive like so: <lookup-centros-de-gestion centro-de-gestion="foo">

An easy solution would be to have the caller initialize $scope.foo = {}; and remove the dvm.centroDeGestion={}; from the rowSelected function (because reassigning the "root" variable breaks binding! -- as in the caller still has its $scope.foo object, but it is not the same memory as the newly allocated dvm.centroDeGestion).

Another solution would be to bind to an object and set a certain property on it. ex: dvm.centroDeGestion.data={};, then to access its properties in your caller, you would use foo.data.*

Hopefully this explanation makes sense. I will try to clarify if you have any questions about it.

Upvotes: 2

Related Questions