Skip to content

Commit

Permalink
Merge pull request #3 from Makaze/open-in-a-split
Browse files Browse the repository at this point in the history
Open in a split
  • Loading branch information
Makaze authored Apr 16, 2024
2 parents c61947e + 95c6747 commit e88b353
Show file tree
Hide file tree
Showing 4 changed files with 106 additions and 16 deletions.
31 changes: 26 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,11 @@
# watch.nvim

**`v0.2.0`**

A scrollable `watch` alternative for Neovim.

![watch nvim-demo-1](https://private-user-images.githubusercontent.com/2280429/318253065-55391feb-95c2-44bc-a235-0cc61db4ed00.gif?jwt=eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJpc3MiOiJnaXRodWIuY29tIiwiYXVkIjoicmF3LmdpdGh1YnVzZXJjb250ZW50LmNvbSIsImtleSI6ImtleTUiLCJleHAiOjE3MTI2NjI1MjcsIm5iZiI6MTcxMjY2MjIyNywicGF0aCI6Ii8yMjgwNDI5LzMxODI1MzA2NS01NTM5MWZlYi05NWMyLTQ0YmMtYTIzNS0wY2M2MWRiNGVkMDAuZ2lmP1gtQW16LUFsZ29yaXRobT1BV1M0LUhNQUMtU0hBMjU2JlgtQW16LUNyZWRlbnRpYWw9QUtJQVZDT0RZTFNBNTNQUUs0WkElMkYyMDI0MDQwOSUyRnVzLWVhc3QtMSUyRnMzJTJGYXdzNF9yZXF1ZXN0JlgtQW16LURhdGU9MjAyNDA0MDlUMTEzMDI3WiZYLUFtei1FeHBpcmVzPTMwMCZYLUFtei1TaWduYXR1cmU9NjhlYjliZWYzNDU1NmZkOWJhOWIxOTU2MzczZDI1MWEwM2U2ZTU5OTUxYWYyMjM0YWExOTY4YTZjYjYwZWFlNCZYLUFtei1TaWduZWRIZWFkZXJzPWhvc3QmYWN0b3JfaWQ9MCZrZXlfaWQ9MCZyZXBvX2lkPTAifQ.RmgZvXzI53dKy0t8DLN5PTqQcDP93jKgw2Hg807Ici0)
![watch nvim-demo-1](demo.gif)


> [!IMPORTANT]
> `watch.nvim` requires Neovim 0.10+!
Expand Down Expand Up @@ -36,6 +39,7 @@ started Neovim.
- [x] Stop and start at will
- [x] Scrollable output
- [x] Pause watching when in the background
- [x] Option to open in a configurable split window

#### Planned:
- [ ] ANSI color support
Expand Down Expand Up @@ -65,10 +69,27 @@ local watch = require("watch")

watch.setup({
-------------------- Default configuration -----------------------------
refresh_rate = 500, -- The default refresh rate for a new watcher in
-- milliseconds. Defaults to `500`.
close_on_stop = false, -- Whether to automatically delete the buffer
-- when stopping a watcher. Defaults to `false`.
-- The default refresh rate for a new watcher in milliseconds. Defaults
-- to `500`.
refresh_rate = 500,
-- Whether to automatically delete the buffer when stopping a watcher.
-- Defaults to `false`.
close_on_stop = false,
-- Configuration for split window option
split = {
-- Whether to automatically delete the buffer when stopping a
-- watcher. Defaults to `false`.
enabled = false,
-- Where to place the split (above|below|right|left). Defaults to
-- `below`.
position = "below",
-- The size of the split in rows (or columns if position is right or
-- left). Defaults to `nil`.
size = nil,
-- Whether to focus on the newly created split watcher. Defaults to
-- `true`.
focus = true,
},
})
```

Expand Down
Binary file added demo.gif
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
28 changes: 23 additions & 5 deletions doc/watch.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

Author: Makaze <[email protected]>
License: GPLv3.0
Version: 0.1.0
Version: 0.2.0

================================================================================
INTRODUCTION *watch*
Expand Down Expand Up @@ -34,6 +34,7 @@ Features: ~
[x] Stop and start at will
[x] Scrollable output
[x] Pause watching when in the background
[x] Option to open in a configurable split window

Planned: ~
[ ] ANSI color support
Expand Down Expand Up @@ -77,10 +78,27 @@ the standard configuration. You can change those options by calling

watch.setup({
-------------------- Default configuration -----------------------------
refresh_rate = 500, -- The default refresh rate for a new watcher in
-- milliseconds. Defaults to `500`.
close_on_stop = false, -- Whether to automatically delete the buffer
-- when stopping a watcher. Defaults to `false`.
-- The default refresh rate for a new watcher in milliseconds. Defaults
-- to `500`.
refresh_rate = 500,
-- Whether to automatically delete the buffer when stopping a watcher.
-- Defaults to `false`.
close_on_stop = false,
-- Configuration for split window option
split = {
-- Whether to automatically delete the buffer when stopping a
-- watcher. Defaults to `false`.
enabled = false,
-- Where to place the split (above|below|right|left). Defaults to
-- `below`.
position = "below",
-- The size of the split in rows (or columns if position is right or
-- left). Defaults to `nil`.
size = nil,
-- Whether to focus on the newly created split watcher. Defaults to
-- `true`.
focus = true,
},
})
>
Expand Down
63 changes: 57 additions & 6 deletions lua/watch.lua
Original file line number Diff line number Diff line change
Expand Up @@ -48,30 +48,56 @@ end
--- Global list of watchers and associated data.
Watch.watchers = {}

--- @class watch.SplitConfig
---
--- @field enabled boolean Whether to open the watch in a new split. Defaults to `false`.
--- @field position '"above"'|'"below"'|'"right"'|'"left'" Where to place the split (above|below|right|left). Defaults to `below`.
--- @field size integer|nil The size of the split in rows (or columns if position is right or left). Defaults to `nil`.
--- @field focus boolean Whether to focus on the newly created split watcher. Defaults to `true`.
---
--- Configuration for watch.nvim.

--- @class watch.Config
---
--- @field refresh_rate integer The default refresh rate for a new watcher in milliseconds. Defaults to `500`.
--- @field close_on_stop boolean Whether to automatically delete the buffer when stopping a watcher. Defaults to `false`.
--- @field split watch.SplitConfig Configuration options for opening the watcher in a split.
---
--- Configuration for watch.nvim.

--- @type watch.Config
Watch.config = {
refresh_rate = 500,
close_on_stop = false,
split = {
enabled = false,
position = "below",
size = nil,
focus = true,
},
}

--- @class watch.SplitConfigOverride
---
--- @field enabled boolean Whether to open the watch in a new split. Defaults to `false`.
--- @field position? '"above"'|'"below"'|'"right"'|'"left'" Where to place the split (above|below|right|left). Defaults to `below`.
--- @field size? integer|nil The size of the split in rows (or columns if position is right or left). Defaults to `nil`.
--- @field focus? boolean Whether to focus on the newly created split watcher. Defaults to `true`.
---
--- Configuration for watch.nvim.

--- @class watch.ConfigOverride
---
--- @field refresh_rate integer? The default refresh rate for a new watcher in milliseconds. Defaults to `500`.
--- @field close_on_stop boolean? Whether to automatically delete the buffer when stopping a watcher. Defaults to `false`.
--- @field refresh_rate? integer The default refresh rate for a new watcher in milliseconds. Defaults to `500`.
--- @field close_on_stop? boolean Whether to automatically delete the buffer when stopping a watcher. Defaults to `false`.
--- @field split? watch.SplitConfigOverride Configuration options for opening the watcher in a split.
---
--- Configuration overrides for watch.nvim.

--- Changes configuration options. See `:help watch-config`.
--- You do not have to call this function unless you want to change anything!
---
--- @param opts watch.ConfigOverride?
--- @param opts? watch.ConfigOverride
Watch.setup = function(opts)
-- Do nothing if nothing given
if not opts or not next(opts) then
Expand Down Expand Up @@ -140,8 +166,8 @@ end
--- Starts continually reloading a buffer's contents with a shell command. If the command is aleady being watched, then opens that buffer in the current window.
---
--- @param command string Shell command.
--- @param refresh_rate integer? Time between reloads in milliseconds. Defaults to `watch.config.refresh_rate`.
--- @param bufnr integer? Buffer number to update. Defaults to a new buffer.
--- @param refresh_rate? integer Time between reloads in milliseconds. Defaults to `watch.config.refresh_rate`.
--- @param bufnr? integer Buffer number to update. Defaults to a new buffer.
Watch.start = function(command, refresh_rate, bufnr)
-- Check if command is nil
if not command or not string.len(command) then
Expand Down Expand Up @@ -177,6 +203,24 @@ Watch.start = function(command, refresh_rate, bufnr)
refresh_rate = Watch.config.refresh_rate
end

-- Create a split based on configurations
local split = Watch.config.split or {}
if split and split.enabled then
local position = split.position
local size = split.size or ""

if position == "above" then
A.nvim_command("split | wincmd k | resize " .. size)
elseif position == "right" then
A.nvim_command(size .. "vsplit")
elseif position == "left" then
A.nvim_command("vsplit | wincmd h | vertical resize " .. size)
else
-- Must be "below" by default
A.nvim_command(size .. "split")
end
end

-- Get existing bufnr if bufname already exists
bufnr = get_buf_by_name(command) or bufnr

Expand All @@ -190,6 +234,13 @@ Watch.start = function(command, refresh_rate, bufnr)
-- Always set as current buffer when starting
A.nvim_win_set_buf(0, bufnr)

-- Unfocus the window if set to false
if split and split.enabled then
if not split.focus then
A.nvim_command("wincmd p")
end
end

-- Set up a timer to run the function every refresh_rate
local timer = uv.new_timer()
timer:start(
Expand Down Expand Up @@ -222,7 +273,7 @@ end
---
--- `WARNING:` If `watch.config.close_on_stop` is set to `true`, then affected buffers will also be deleted.
---
--- @param event string|table? The command name to stop. If string, then uses the string. If table, then uses `event.file`.
--- @param event? string|table The command name to stop. If string, then uses the string. If table, then uses `event.file`.
Watch.stop = function(event)
-- Get the current buffer if it is a watcher
local bufname = nil
Expand Down

0 comments on commit e88b353

Please sign in to comment.