SortableJS / ngx-sortablejs

Angular 2+ binding to SortableJS. Previously known as angular-sortablejs
https://sortablejs.github.io/ngx-sortablejs/
MIT License
467 stars 160 forks source link

ERROR TypeError: Cannot read property 'option' of undefined at ngx-sortablejs.js:203 #172

Open liwei511 opened 5 years ago

liwei511 commented 5 years ago

Cannot read property 'option' of undefined

liwei511 commented 5 years ago

this.sortableInstance is undefined。 what is sortableInstance?

dvose commented 5 years ago

I ran into this issue using an older build of angular-sortablejs. The error seems to be related to a new minor release of sortablejs 1.10.0. In my case, downgrading to sortablejs 1.7.0 fixed it.

"angular-sortablejs": "^2.7.0",
"sortablejs": "~1.7.0",
codekrafter commented 4 years ago

I am getting the same error in 3.1.4

blackbaud-conorwright commented 4 years ago

I am also seeing this in 3.14 with sortablejs version 1.10.0. It looks like the ngOnChanges method is firing before the create method resolves and creates the sortableInstance.

Everything is working fine after the error, it's just an initial issue. Should be fixable in the package by updating the ngOnChanges function to only execute the option change when the instance exists: image

However, I don't have an alternative for the consumer side, so the console gets filled with this error on load.

blackbaud-conorwright commented 4 years ago

I made a quick PR to hopefully help with resolving this ^

dylanhouston7 commented 4 years ago

I would really appreciate it if this got fixed sooner rather than later.

TheGameKnave commented 3 years ago

@blackbaud-conorwright I don't see anywhere that the sortableInstance is defined in order to check against it from within my component.

dmmishchenko commented 1 year ago

Issue still exist in 11.1.0 version, do you find a way to solve it?

AntoineB05 commented 2 months ago

I solved the issue by change the way I pass the option to the [sortablejsOptions] directive. html: <div sortablejs [sortablejsOptions]="getSortableOption(someContexts)">...<div>

The wrong way to implement getSortableOption function:

getSortableOption(someContexts): Sortable.Options {
    return {
        //... define the options with the context
     };
  }

The good way to implement getSortableOption function:

sortableOptionMap = new Map<string, Sortable.Options>(); 
getSortableOption(someContexts): Sortable.Options {
    const optionKey = // optionKeyWithSomeContext;
    if (!this.sortableOptionMap.has(optionKey)) {
      this.sortableOptionMap.set(optionKey, {
        //... define the options with the context
      });
    }
    return this.sortableOptionMap.get(optionKey);
  }

Of course, if you don't need someContexts with the SortableOption you can define your option in a variable and bind it directly in the template <div sortablejs [sortablejsOptions]="sortableOption">...<div>

The only important thing is to not change the ref of the option you pass to the [sortablejsOptions] directive too frequently (in the wrong way it was changed at each change detection cycle)