wenzhixin / multiple-select

A jQuery plugin to select multiple elements with checkboxes :)
http://multiple-select.wenzhixin.net.cn
MIT License
1.91k stars 652 forks source link

Scroll problem if more than 199 elements #552

Open tcivera opened 4 years ago

tcivera commented 4 years ago

When the select has more than 199 elements/options, the vertical scroll stops to work.

tcivera commented 4 years ago

The problem seems to be in the VirtualScroll class. Commenting the line _this.initDOM(_this.rows) inside the onScroll function, seems to work correctly:

var onScroll = function onScroll() { if (_this.lastCluster !== (_this.lastCluster = _this.getNum())) { //_this.initDOM(_this.rows);

      _this.callback();
    }
  };
the-jiveman commented 4 years ago

I can confirm the same problem on my end. Populating the array with 199 items or less, there is no scroll issue.

Edit: I think I identified the problem (at least in my situation). It's related to dropdown elements being HIDDEN when multipleSelect initializes. If the multipleSelect is initialized BEFORE the wrapping element is displayed, the height is not calculated correctly WHEN the dropdowns have 200 or more items.

Calling $('#mySelect').multipleSelect('refresh'); at some point after the elements are visible seems to fix the issue without having to modify the multipleSelect library itself.

Here's a JSFiddle example that demonstrates the problem.

$(function() {
   $('select').multipleSelect();

   // here I'm revealing the container that has the dropdowns
   // and after it's done showing, I refresh the multipleSelect
   $('#btn').click(() => $('#wrapper').show(function() {
      $('select').multipleSelect('refresh');    
   }));
})

It's not an ideal solution, but it's a workaround. If someone knows a better way, please let me know.

tcivera commented 4 years ago

Thanks 'the-jiveman' for the solution. Sorry, I didn't realize that with commenting the line only the first 199 items were displayed. I have the select in a hidden tab, so, it works adding the refresh when the first time the tab is shown.

It seems that problem is that the height is not calculated correctly in the getRowsHeight() function in the VirtualScroll class:

          var nodes = this.contentEl.children;
          var node = nodes[Math.floor(nodes.length / 2)];          
          this.itemHeight = node.offsetHeight;  //The offsetHeight returns 0 because the item (li) is not visible.
the-jiveman commented 4 years ago

Yes @tcivera, I found the same lines of code to be the culprit, but didn't have the time to try and fix it at the source, as I needed to move ahead with my project. I really want to use Multiple Select in my project, as it's the cleanest looking and well documented multi-select control I found, so I hope the real fix comes coon. In the meantime, I may have to deal with it using the refresh workaround.

ghiscoding commented 5 months ago

FYI, this is probably caused by the Virtual Scroll which used to be 200 but was later increased to 2000 in this commit a3d87566 , also worth to know that the v-scroll is calculated from CLUSTER_BLOCKS * BLOCK_ROWS which is now equal to 2000. So I'm assuming that you no longer have the problem since the increase

https://github.com/wenzhixin/multiple-select/blob/cd6c057769970efccda2c4ba4f46d19bdc83dfe9/src/constants/index.js#L2-L3