Home » Javascript » Controller variables don't update when using them in another controller of an mdPanel passed in via locals

Controller variables don't update when using them in another controller of an mdPanel passed in via locals

Posted by: admin November 1, 2017 Leave a comment

Questions:

I have a method in a controller called showFilterMenu(e) which opens up an $mdPanel and passes the locals this.allOptions and this.selectedOptions in.

class MainController{
    constructor(){
        this.filterPanelRef;
        this.allOptions = ['A', 'B', 'C'];
        this.selectedOptions = [];
        this.filter = () => {
            // do some logic to filter down a list using this.selectedOptions against this.allOptions.
        }
    }

    showFilterMenu(e){
        this.filterPanelRef = this.$mdPanel.create({
            attachTo: angular.element(document.body),
            controller: 'filterController',
            controllerAs: 'filterCtrl',
            bindToController: true, //redundant since default is true
            template: require('./filter/filter.html'),
            locals: {
                allOptions: this.allOptions,
                selectedOptions: this.selectedOptions,
                filter: this.filter
            },
            clickOutsideToClose: true,
            escapeToClose: true,
            focusOnOpen: true
        });

        this.filterPanelRef.open();
    }
}

In my filter template file I make use of a directive, so I continue to pass through the locals from the MainController:

<multi-select-filter
    options="filterCtrl.allOptions"
    selected-options="filterCtrl.selectedOptions"
    on-filter="filterCtrl.filter">   
</multi-select-filter>

My directive has the following options set:

//...
restrict = 'E';
template = MultiSelectFilterHtml;
controller = 'multiSelectFilterController';
controllerAs = 'multiSelectFilterCtrl';
bindToController = true;
replace = true;
scope = {
    selectedOptions: '=',
    options: '=',
    onFilter: '='
};

and the MultiSelectFilterHtml looks like:

<md-input-container class="multi-select-filter" md-no-float>
    <md-select
        ng-change="multiSelectFilterCtrl.onFilter()"
        ng-model="multiSelectFilterCtrl.selectedOptions"
        multiple>
        <md-option
            ng-value="option"
            ng-repeat="option in multiSelectFilterCtrl.options>
            {{option}}
        </md-option>
    </md-select>
</md-input-container>

Everything works and initializes properly, but when selecting options in the list, they bubble back up to the filterController but then don’t change in the MainController. It’s acting like I am passing in a copy of this.allOptions and this.selectedOptions into the mdPanel.

Basically when my model updates in the multi select filter directive, I want it to be modifying the selectedOptions of the MainController, since my filter method uses that variable when filtering and right now it is always an empty array.

I must be missing something.

Answers:

It’s difficult without a jsfiddle but I think your bindings are incorrect for the onFilter binding in the multiSelectFilter directive scope, try using ‘&’ instead.

this answer should give you more information https://stackoverflow.com/a/21714971/1248388