Autocomplete pagination issue

Hi there!

When an autocomplete list is longer than maxRenderedOptions (in this case, 100), clicking the ··· button at the bottom to go to the next page stops working once you scroll past roughly the halfway point of the list. At that point, clicking ··· jumps back to the top of the current page instead of advancing, and you cannot get any further. Paginating below that halfway point works.

To reproduce:

Set up an autocomplete source with many options and page through using the ··· button:

300 suggestions → gets stuck after the 2nd page (item 200) 500 suggestions → gets stuck after the 3rd page (item 300) 1000 suggestions → gets stuck after the 6th page (item 600) The pattern seems to be consistent that pagination stops working at the first page boundary past the halfway point of the total list.

Expected behavior:

Clicking ··· on the bottom should always advance to the next page, regardless of where you are in the list until the end of it.

Notes:

Navigating with keyboard (arrow keys / Page Down) does not seem to be affected and is working correctly. The issue is specific to clicking the bottom ··· element.

Hi, FYI you can share an example for reproduction with the demo editor on the website: Try CodeMirror with the Share button there (though you’ll have to write in JS since it doesn’t support TypeScript).

Hi there! Thanks for the info! I used the “Custom Completions” preset, and adapted it a bit, so there is at least 300 suggestions. Here is the link.

1 Like

Thanks! This indeed appears to be a bug in rangeAroundSelected. The following patch seems to fix it:

diff --git a/src/tooltip.ts b/src/tooltip.ts
index cb24e02..75c2164 100644
--- a/src/tooltip.ts
+++ b/src/tooltip.ts
@@ -55,12 +55,9 @@ function optionContent(config: Required<CompletionConfig>): OptionContentSource[
 function rangeAroundSelected(total: number, selected: number, max: number) {
   if (total <= max) return {from: 0, to: total}
   if (selected < 0) selected = 0
-  if (selected <= (total >> 1)) {
-    let off = Math.floor(selected / max)
-    return {from: off * max, to: (off + 1) * max}
-  }
-  let off = Math.floor((total - selected) / max)
-  return {from: total - (off + 1) * max, to: total - off * max}
+  let off = Math.floor(selected / max)
+  let from = Math.min(off * max, total - max)
+  return {from, to: from + max}
 }
 
 class CompletionTooltip {

We should write a test for this. I might find time for that later this week if somebody doesn’t beat me to it.

1 Like

This patch should fix this:

1 Like

Hi!

Thank you a lot for the quick reply and fix! :smiley:

I’ve tagged this in @codemirror/autocomplete 6.20.2

1 Like