Skip to content

Commit b5c64c4

Browse files
authored
Merge pull request #10 from stephenprater/fix-vertical-split-window
fix: improve vertical split behavior for claude terminal
2 parents d1dbc6b + 156cd48 commit b5c64c4

7 files changed

Lines changed: 80 additions & 21 deletions

File tree

CHANGELOG.md

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,14 @@ All notable changes to this project will be documented in this file.
55
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
66
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
77

8+
## [Unreleased]
9+
10+
### Added
11+
- New `split_ratio` config option to replace `height_ratio` for better handling of both horizontal and vertical splits
12+
13+
### Fixed
14+
- Fixed vertical split behavior when the window position is set to a vertical split command
15+
816
## [0.4.2] - 2025-03-03
917

1018
### Changed

README.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -95,8 +95,8 @@ The plugin can be configured by passing a table to the `setup` function. Here's
9595
require("claude-code").setup({
9696
-- Terminal window settings
9797
window = {
98-
height_ratio = 0.3, -- Percentage of screen height for the terminal window
99-
position = "botright", -- Position of the window: "botright", "topleft", etc.
98+
split_ratio = 0.3, -- Percentage of screen for the terminal window (height for horizontal, width for vertical splits)
99+
position = "botright", -- Position of the window: "botright", "topleft", "vertical", "rightbelow vsplit", etc.
100100
enter_insert = true, -- Whether to enter insert mode when opening Claude Code
101101
hide_numbers = true, -- Hide line numbers in the terminal window
102102
hide_signcolumn = true, -- Hide the sign column in the terminal window

doc/claude-code.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -90,8 +90,8 @@ default configuration:
9090
require("claude-code").setup({
9191
-- Terminal window settings
9292
window = {
93-
height_ratio = 0.3, -- Percentage of screen height for the terminal window
94-
position = "botright", -- Position of the window: "botright", "topleft", etc.
93+
split_ratio = 0.3, -- Percentage of screen for the terminal window (height or width)
94+
position = "botright", -- Position of the window: "botright", "topleft", "vertical", "vsplit", etc.
9595
enter_insert = true, -- Whether to enter insert mode when opening Claude Code
9696
hide_numbers = true, -- Hide line numbers in the terminal window
9797
hide_signcolumn = true, -- Hide the sign column in the terminal window

lua/claude-code/config.lua

Lines changed: 15 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ local M = {}
88

99
--- ClaudeCodeWindow class for window configuration
1010
-- @table ClaudeCodeWindow
11-
-- @field height_ratio number Percentage of screen height for the terminal window
11+
-- @field split_ratio number Percentage of screen for the terminal window (height for horizontal, width for vertical splits)
1212
-- @field position string Position of the window: "botright", "topleft", "vertical", etc.
1313
-- @field enter_insert boolean Whether to enter insert mode when opening Claude Code
1414
-- @field hide_numbers boolean Hide line numbers in the terminal window
@@ -49,7 +49,8 @@ local M = {}
4949
M.default_config = {
5050
-- Terminal window settings
5151
window = {
52-
height_ratio = 0.3, -- Percentage of screen height for the terminal window
52+
split_ratio = 0.3, -- Percentage of screen for the terminal window (height or width)
53+
height_ratio = 0.3, -- DEPRECATED: Use split_ratio instead
5354
position = 'botright', -- Position of the window: "botright", "topleft", "vertical", etc.
5455
enter_insert = true, -- Whether to enter insert mode when opening Claude Code
5556
hide_numbers = true, -- Hide line numbers in the terminal window
@@ -90,11 +91,11 @@ local function validate_config(config)
9091
end
9192

9293
if
93-
type(config.window.height_ratio) ~= 'number'
94-
or config.window.height_ratio <= 0
95-
or config.window.height_ratio > 1
94+
type(config.window.split_ratio) ~= 'number'
95+
or config.window.split_ratio <= 0
96+
or config.window.split_ratio > 1
9697
then
97-
return false, 'window.height_ratio must be a number between 0 and 1'
98+
return false, 'window.split_ratio must be a number between 0 and 1'
9899
end
99100

100101
if type(config.window.position) ~= 'string' then
@@ -187,6 +188,14 @@ end
187188
--- @param silent? boolean Set to true to suppress error notifications (for tests)
188189
--- @return ClaudeCodeConfig
189190
function M.parse_config(user_config, silent)
191+
-- Handle backward compatibility first
192+
if user_config and user_config.window then
193+
if user_config.window.height_ratio and not user_config.window.split_ratio then
194+
-- Copy height_ratio to split_ratio for backward compatibility
195+
user_config.window.split_ratio = user_config.window.height_ratio
196+
end
197+
end
198+
190199
local config = vim.tbl_deep_extend('force', {}, M.default_config, user_config or {})
191200

192201
local valid, err = validate_config(config)

lua/claude-code/terminal.lua

Lines changed: 32 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,36 @@ M.terminal = {
1515
saved_updatetime = nil,
1616
}
1717

18+
--- Create a split window according to the specified position configuration
19+
--- @param position string Window position configuration
20+
--- @param config table Plugin configuration containing window settings
21+
--- @param existing_bufnr number|nil Buffer number of existing buffer to show in the split (optional)
22+
--- @private
23+
local function create_split(position, config, existing_bufnr)
24+
local is_vertical = position:match('vsplit') or position:match('vertical')
25+
26+
-- Create the window with the user's specified command
27+
-- If the command already contains 'split' or 'vsplit', use it as is
28+
if position:match('split') then
29+
vim.cmd(position)
30+
else
31+
-- Otherwise append 'split'
32+
vim.cmd(position .. ' split')
33+
end
34+
35+
-- If we have an existing buffer to display, switch to it
36+
if existing_bufnr then
37+
vim.cmd('buffer ' .. existing_bufnr)
38+
end
39+
40+
-- Resize the window appropriately based on split type
41+
if is_vertical then
42+
vim.cmd('vertical resize ' .. math.floor(vim.o.columns * config.window.split_ratio))
43+
else
44+
vim.cmd('resize ' .. math.floor(vim.o.lines * config.window.split_ratio))
45+
end
46+
end
47+
1848
--- Set up function to force insert mode when entering the Claude Code window
1949
--- @param claude_code table The main plugin module
2050
function M.force_insert_mode(claude_code)
@@ -48,18 +78,15 @@ function M.toggle(claude_code, config, git)
4878
end
4979
else
5080
-- Claude Code buffer exists but is not visible, open it in a split
51-
vim.cmd(config.window.position .. ' split')
52-
vim.cmd('resize ' .. math.floor(vim.o.lines * config.window.height_ratio))
53-
vim.cmd('buffer ' .. bufnr)
81+
create_split(config.window.position, config, bufnr)
5482
-- Force insert mode more aggressively
5583
vim.schedule(function()
5684
vim.cmd 'stopinsert | startinsert'
5785
end)
5886
end
5987
else
6088
-- Claude Code is not running, start it in a new split
61-
vim.cmd(config.window.position .. ' split')
62-
vim.cmd('resize ' .. math.floor(vim.o.lines * config.window.height_ratio))
89+
create_split(config.window.position, config)
6390

6491
-- Determine if we should use the git root directory
6592
local cmd = 'terminal ' .. config.command

tests/spec/config_spec.lua

Lines changed: 20 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -15,28 +15,43 @@ describe('config', function()
1515
it('should merge user config with default config', function()
1616
local user_config = {
1717
window = {
18-
height_ratio = 0.5,
18+
split_ratio = 0.5,
1919
},
2020
}
2121
local result = config.parse_config(user_config, true) -- silent mode
22-
assert.are.equal(0.5, result.window.height_ratio)
22+
assert.are.equal(0.5, result.window.split_ratio)
2323

2424
-- Other values should be set to defaults
2525
assert.are.equal('botright', result.window.position)
2626
assert.are.equal(true, result.window.enter_insert)
2727
end)
2828

2929
it('should validate config values', function()
30-
-- This config has an invalid height_ratio (should be between 0 and 1)
30+
-- This config has an invalid split_ratio (should be between 0 and 1)
3131
local invalid_config = {
3232
window = {
33-
height_ratio = 2,
33+
split_ratio = 2,
3434
},
3535
}
3636

3737
-- When validation fails, it should return the default config
3838
local result = config.parse_config(invalid_config, true) -- silent mode
39-
assert.are.equal(config.default_config.window.height_ratio, result.window.height_ratio)
39+
assert.are.equal(config.default_config.window.split_ratio, result.window.split_ratio)
40+
end)
41+
42+
it('should maintain backward compatibility with height_ratio', function()
43+
-- Config using the legacy height_ratio instead of split_ratio
44+
local legacy_config = {
45+
window = {
46+
height_ratio = 0.7,
47+
-- split_ratio not specified
48+
},
49+
}
50+
51+
local result = config.parse_config(legacy_config, true) -- silent mode
52+
53+
-- split_ratio should be set to the height_ratio value
54+
assert.are.equal(0.7, result.window.split_ratio)
4055
end)
4156
end)
4257
end)

tests/spec/terminal_spec.lua

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ describe('terminal module', function()
7070
command = 'claude',
7171
window = {
7272
position = 'botright',
73-
height_ratio = 0.5,
73+
split_ratio = 0.5,
7474
enter_insert = true,
7575
hide_numbers = true,
7676
hide_signcolumn = true,

0 commit comments

Comments
 (0)