Skip to content

Commit

Permalink
feat: pinned buffers stay visible
Browse files Browse the repository at this point in the history
  • Loading branch information
Iron-E committed Apr 1, 2023
1 parent 74a78ac commit f0bb65f
Show file tree
Hide file tree
Showing 2 changed files with 39 additions and 27 deletions.
42 changes: 26 additions & 16 deletions lua/barbar/layout.lua
Original file line number Diff line number Diff line change
Expand Up @@ -26,13 +26,13 @@ local SLASH_LEN = #'/'
local SPACE_LEN = #' '

--- @class barbar.layout.data
--- @field actual_width integer the `used_width` plus the `padding_width` allocated to each buffer
--- @field actual_width integer the `base_widths_sum` plus the `padding_width` allocated to each buffer
--- @field base_widths integer[] the minimum amount of space taken up by each buffer
--- @field buffers_width integer the amount of space available to be taken up by buffers
--- @field padding_width integer the amount of padding used on each side of each buffer
--- @field tabpages_width integer the amount of space taken up by the tabpage indicator
--- @field pinned_widths integer[] the minimum amount of space taken up by each pinned buffer
--- @field scroll_max integer the maximum position which can be scrolled to
--- @field used_width integer the sum of the `base_widths`
--- @field tabpages_width integer the amount of space taken up by the tabpage indicator

--- @class barbar.Layout
--- @field buffers integer[] different from `state.buffers` in that the `hide` option is respected. Only updated when calling `calculate_buffers_width`.
Expand All @@ -44,24 +44,27 @@ function Layout.calculate()
local available_width = get_option'columns'
available_width = available_width - state.offset.width

local used_width, base_widths = Layout.calculate_buffers_width()
local pinned_widths_sum, pinned_widths, base_widths_sum, base_widths = Layout.calculate_buffers_width()
local tabpages_width = Layout.calculate_tabpages_width()

local buffers_width = available_width - tabpages_width
local remaining_width = max(0, buffers_width - used_width)
local pinned_width = pinned_widths_sum + (#pinned_widths * config.options.minimum_padding * SIDES_OF_BUFFER)
local buffers_width = available_width - pinned_width - tabpages_width

local remaining_width = max(0, buffers_width - base_widths_sum)
local remaining_width_per_buffer = floor(remaining_width / #base_widths)
local remaining_padding_per_buffer = floor(remaining_width_per_buffer / SIDES_OF_BUFFER)
local padding_width = max(config.options.minimum_padding, min(remaining_padding_per_buffer, config.options.maximum_padding))
local actual_width = used_width + (#base_widths * padding_width * SIDES_OF_BUFFER)
local actual_width = base_widths_sum + (#base_widths * padding_width * SIDES_OF_BUFFER)

return {
actual_width = actual_width,
base_widths = base_widths,
buffers_width = buffers_width,
padding_width = padding_width,
pinned_widths = pinned_widths,
pinned_widths_sum = pinned_widths_sum,
scroll_max = max(0, actual_width - buffers_width),
tabpages_width = tabpages_width,
used_width = used_width,
}
end

Expand Down Expand Up @@ -124,28 +127,35 @@ function Layout.calculate_buffers_position_by_buffer_number()

for i, buffer_number in ipairs(Layout.buffers) do
positions[buffer_number] = current_position
local width = layout.base_widths[i] + (2 * layout.padding_width)
current_position = current_position + width
current_position = current_position + Layout.calculate_width(
layout.base_widths[i] or layout.pinned_widths[i],
layout.padding_width
)
end

return positions
end

--- Calculate the width of the buffers
--- @return integer sum, integer[] widths
--- @return integer pinned_sum, integer[] pinned_widths, integer sum, integer[] other_widths
function Layout.calculate_buffers_width()
Layout.buffers = Buffer.hide(state.buffers)

local sum = 0
local widths = {}
local pinned_sum, sum = 0, 0
local pinned_widths, other_widths = {}, {}

for i, bufnr in ipairs(Layout.buffers) do
local width = Layout.calculate_buffer_width(bufnr, i)
sum = sum + width
table_insert(widths, width)
if state.get_buffer_data(bufnr).pinned then
pinned_sum = pinned_sum + width
pinned_widths[i] = width
else
sum = sum + width
other_widths[i] = width
end
end

return sum, widths
return pinned_sum, pinned_widths, sum, other_widths
end

--- The number of characters needed to represent the tabpages.
Expand Down
24 changes: 13 additions & 11 deletions lua/barbar/render.lua
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ local defer_fn = vim.defer_fn
local get_current_buf = vim.api.nvim_get_current_buf --- @type function
local get_option = vim.api.nvim_get_option --- @type function
local has = vim.fn.has --- @type function
local list_extend = vim.list_extend
local list_tabpages = vim.api.nvim_list_tabpages --- @type function
local list_wins = vim.api.nvim_list_wins --- @type function
local set_current_win = vim.api.nvim_set_current_win --- @type function
Expand Down Expand Up @@ -526,6 +527,7 @@ local function generate_tabline(bufnrs, refocus)
local accumulated_width = 0 --- the amount of width that has been accumulated while iterating
local current_buffer_index = nil --- @type nil|integer
local groups = {} --- @type barbar.render.group[]
local pinned_items = {} --- @type barbar.render.group[]

for i, bufnr in ipairs(bufnrs) do
local activity = Buffer.activities[Buffer.get_activity(bufnr)]
Expand All @@ -536,7 +538,7 @@ local function generate_tabline(bufnrs, refocus)
)
local buffer_name = buffer_data.name or '[no name]'

buffer_data.real_width = Layout.calculate_width(layout.base_widths[i], layout.padding_width)
buffer_data.real_width = Layout.calculate_width(layout.base_widths[i] or layout.pinned_widths[i], layout.padding_width)
buffer_data.real_position = accumulated_width

local icons_option = state.icons(bufnr, activity)
Expand Down Expand Up @@ -628,7 +630,8 @@ local function generate_tabline(bufnrs, refocus)
local group = { --- @type barbar.render.group
items = {left_separator, padding, buffer_index, buffer_number, icon, jump_letter, name},
position = buffer_data.position or accumulated_width,
width = buffer_data.width or Layout.calculate_width(layout.base_widths[i], layout.padding_width)
--- @diagnostic disable-next-line: assign-type-mismatch it is assigned just earlier
width = buffer_data.width or buffer_data.real_width,
}

Buffer.for_each_counted_enabled_diagnostic(bufnr, icons_option.diagnostics, function(count, idx, option)
Expand Down Expand Up @@ -657,6 +660,11 @@ local function generate_tabline(bufnrs, refocus)
end
end

if buffer_data.pinned then
list_extend(pinned_items, group.items)
goto continue -- HACK: there is no `continue` keyword
end

accumulated_width = accumulated_width + group.width

local scroll_current = min(scroll.current, layout.scroll_max)
Expand Down Expand Up @@ -715,15 +723,9 @@ local function generate_tabline(bufnrs, refocus)
end
end

-- TODO: put pinned buffers here
-- if #scroll_locked.left > 0 then
-- local items = scroll_locked.left[1].items
-- for i = #scroll_locked.left, 2, -1 do
-- list_extend(items, scroll_locked.left[i].items)
-- end
--
-- result = result .. items_to_string(items)
-- end
if #pinned_items > 0 then
result = result .. items_to_string(pinned_items)
end

-- Render bufferline string
result = result .. items_to_string(bufferline_items)
Expand Down

0 comments on commit f0bb65f

Please sign in to comment.