diff --git a/lua/telescope/pickers.lua b/lua/telescope/pickers.lua index 04b1ccf..2681c8b 100644 --- a/lua/telescope/pickers.lua +++ b/lua/telescope/pickers.lua @@ -126,7 +126,8 @@ function Picker:new(opts) obj.scroller = p_scroller.create( - get_default(opts.scroll_strategy, config.values.scroll_strategy) + get_default(opts.scroll_strategy, config.values.scroll_strategy), + obj.sorting_strategy ) return obj diff --git a/lua/telescope/pickers/scroller.lua b/lua/telescope/pickers/scroller.lua index f4c90ff..d9e5a64 100644 --- a/lua/telescope/pickers/scroller.lua +++ b/lua/telescope/pickers/scroller.lua @@ -1,10 +1,33 @@ - local scroller = {} -scroller.create = function(strategy) +local calc_count_fn = function(sorting_strategy) + if sorting_strategy == 'ascending' then + return function(a, b) return math.min(a, b) end + else + return function(a, b, row) + if a == b or not row then + return math.max(a, b) + else + local x = a - b + if row < x then + return math.max(a, b) - 1, true + elseif row == a then + return x, true + else + return math.max(a, b) + end + end + end + end +end + +scroller.create = function(strategy, sorting_strategy) + local calc_count = calc_count_fn(sorting_strategy) + if strategy == 'cycle' then return function(max_results, num_results, row) - local count = math.min(max_results, num_results) + local count, b = calc_count(max_results, num_results, row) + if b then return count end if row >= count then return 0 @@ -16,7 +39,7 @@ scroller.create = function(strategy) end elseif strategy == 'limit' or strategy == nil then return function(max_results, num_results, row) - local count = math.min(max_results, num_results) + local count = calc_count(max_results, num_results) if row >= count then return count - 1 diff --git a/lua/tests/automated/scroller_spec.lua b/lua/tests/automated/scroller_spec.lua index 7889573..f47edda 100644 --- a/lua/tests/automated/scroller_spec.lua +++ b/lua/tests/automated/scroller_spec.lua @@ -5,8 +5,8 @@ local eq = assert.are.same describe('scroller', function() local max_results = 10 - describe('cycle', function() - local cycle_scroller = p_scroller.create('cycle') + describe('ascending cycle', function() + local cycle_scroller = p_scroller.create('cycle', 'ascending') it('should return values within the max results', function() eq(5, cycle_scroller(max_results, max_results, 5)) @@ -29,8 +29,8 @@ describe('scroller', function() end) end) - describe('other', function() - local limit_scroller = p_scroller.create('limit') + describe('ascending limit', function() + local limit_scroller = p_scroller.create('limit', 'ascending') it('should return values within the max results', function() eq(5, limit_scroller(max_results, max_results, 5)) @@ -44,7 +44,7 @@ describe('scroller', function() eq(0, limit_scroller(max_results, max_results, -1)) end) - it('should cycle you to 0 when you go past the results', function() + it('should not cycle you to 0 when you go past the results', function() eq(max_results - 1, limit_scroller(max_results, max_results, max_results + 1)) end) @@ -53,4 +53,53 @@ describe('scroller', function() eq(current - 1, limit_scroller(max_results, current, 7)) end) end) + + describe('descending cycle', function() + local cycle_scroller = p_scroller.create('cycle', 'descending') + + it('should return values within the max results', function() + eq(5, cycle_scroller(max_results, max_results, 5)) + end) + + it('should return max_results - 1 at 0', function() + eq(0, cycle_scroller(max_results, max_results, 0)) + end) + + it('should cycle you to the bot when you go below 0', function() + eq(max_results - 1, cycle_scroller(max_results, max_results, -1)) + end) + + it('should cycle you to 0 when you go past the results', function() + eq(0, cycle_scroller(max_results, max_results, max_results + 1)) + end) + + it('should cycle when current results is less than max_results', function() + eq(9, cycle_scroller(max_results, 5, 4)) + end) + end) + + describe('descending limit', function() + local limit_scroller = p_scroller.create('limit', 'descending') + + it('should return values within the max results', function() + eq(5, limit_scroller(max_results, max_results, 5)) + end) + + it('should return 0 at 0', function() + eq(0, limit_scroller(max_results, max_results, 0)) + end) + + it('should not cycle', function() + eq(0, limit_scroller(max_results, max_results, -1)) + end) + + it('should not cycle you to 0 when you go past the results', function() + eq(max_results - 1, limit_scroller(max_results, max_results, max_results + 1)) + end) + + it('should stay at current results when current results is less than max_results', function() + local current = 5 + eq(current - 1, limit_scroller(max_results, current, 4)) + end) + end) end)