diff --git a/README.md b/README.md
index ce25000..229b8ac 100644
--- a/README.md
+++ b/README.md
@@ -11,6 +11,14 @@ simply install and go.
[parinfer-rust]: https://github.com/eraserhd/parinfer-rust
[parinfer-lua]: https://github.com/oakmac/parinfer-lua
+## Requirements
+
+Neovim 0.7 or later.
+
+[Version 1.2.0][v1.2.0] works for older versions of Neovim.
+
+[v1.2.0]: https://github.com/gpanders/nvim-parinfer/releases/tag/v1.2.0
+
## Configuration
nvim-parinfer uses sane defaults that should "just work". You can see the
diff --git a/autoload/parinfer.vim b/autoload/parinfer.vim
deleted file mode 100644
index 18567a4..0000000
--- a/autoload/parinfer.vim
+++ /dev/null
@@ -1,71 +0,0 @@
-" Copyright (C) 2021 Gregory Anders
-"
-" SPDX-License-Identifier: GPL-3.0-or-later
-"
-" This program is free software: you can redistribute it and/or modify
-" it under the terms of the GNU General Public License as published by
-" the Free Software Foundation, either version 3 of the License, or
-" (at your option) any later version.
-"
-" This program is distributed in the hope that it will be useful,
-" but WITHOUT ANY WARRANTY; without even the implied warranty of
-" MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-" GNU General Public License for more details.
-"
-" You should have received a copy of the GNU General Public License
-" along with this program. If not, see .
-
-function! parinfer#log(...) abort
- if a:0 > 0
- let g:parinfer_logfile = a:1
- echomsg 'Parinfer is now logging to '.a:1
- else
- unlet! g:parinfer_logfile
- echomsg 'Parinfer is no longer logging'
- endif
-endfunction
-
-function! parinfer#enable(bang, enable) abort
- if a:bang
- let g:parinfer_enabled = a:enable
- echomsg 'Parinfer ' .. (a:enable ? 'enabled' : 'disabled') .. ' globally'
- else
- let b:parinfer_enabled = a:enable
- echomsg 'Parinfer ' .. (a:enable ? 'enabled' : 'disabled') .. ' in the current buffer'
- endif
-endfunction
-
-function! parinfer#toggle(bang) abort
- if a:bang
- call parinfer#enable(1, !g:parinfer_enabled)
- else
- call parinfer#enable(0, !b:parinfer_enabled)
- endif
-endfunction
-
-function! parinfer#init() abort
- if &previewwindow || &buftype ==# 'prompt'
- return
- endif
-
- command! -buffer ParinferStats lua parinfer.stats()
-
- lua parinfer.enter_buffer()
-
- augroup parinfer
- autocmd! TextChanged,TextChangedI,TextChangedP call v:lua.parinfer.text_changed(+expand(""))
- autocmd! CursorMoved,CursorMovedI call v:lua.parinfer.cursor_moved(+expand(""))
- augroup END
-
- if !get(b:, 'parinfer_no_maps', get(g:, 'parinfer_no_maps', 0))
- if mapcheck('', 'i') ==# ''
- imap (parinfer-tab)
- endif
-
- if mapcheck('', 'i') ==# ''
- imap (parinfer-backtab)
- endif
- endif
-endfunction
-
-lua require('parinfer.setup')
diff --git a/fnl/parinfer/setup.fnl b/fnl/parinfer/setup.fnl
index c530a82..55263b7 100644
--- a/fnl/parinfer/setup.fnl
+++ b/fnl/parinfer/setup.fnl
@@ -244,8 +244,8 @@
n
(/ min 1000000) (/ max 1000000) (/ avg 1000000) (/ std 1000000))))))
-(global parinfer {:enter_buffer enter-buffer
- :cursor_moved cursor-moved
- :text_changed text-changed
- : stats
- : tab})
+{:enter_buffer enter-buffer
+ :cursor_moved cursor-moved
+ :text_changed text-changed
+ : stats
+ : tab}
diff --git a/lua/parinfer/setup.lua b/lua/parinfer/setup.lua
index e41239e..eeda259 100644
--- a/lua/parinfer/setup.lua
+++ b/lua/parinfer/setup.lua
@@ -342,5 +342,4 @@ local function stats()
return nil
end
end
-parinfer = {enter_buffer = enter_buffer, cursor_moved = cursor_moved, text_changed = text_changed, stats = stats, tab = tab}
-return nil
+return {enter_buffer = enter_buffer, cursor_moved = cursor_moved, text_changed = text_changed, stats = stats, tab = tab}
diff --git a/plugin/parinfer.lua b/plugin/parinfer.lua
new file mode 100644
index 0000000..ba37508
--- /dev/null
+++ b/plugin/parinfer.lua
@@ -0,0 +1,158 @@
+if vim.g.loaded_parinfer then
+ return
+end
+vim.g.loaded_parinfer = true
+
+local defaults = {
+ mode = "smart",
+ enabled = true,
+ force_balance = false,
+ comment_chars = {";"},
+ filetypes = {
+ "clojure",
+ "scheme",
+ "lisp",
+ "racket",
+ "hy",
+ "fennel",
+ "janet",
+ "carp",
+ "wast",
+ "yuck",
+ },
+}
+
+for k, v in pairs(defaults) do
+ if not vim.g["parinfer_" .. k] then
+ vim.g["parinfer_" .. k] = v
+ end
+end
+
+local function set_enabled(bang, enable)
+ if bang then
+ vim.g.parinfer_enabled = enable
+ vim.api.nvim_echo(
+ {{string.format("Parinfer %s globally", enable and "enabled" or "disabled")}},
+ false,
+ {}
+ )
+ else
+ vim.b.parinfer_enabled = enable
+ vim.api.nvim_echo(
+ {{string.format("Parinfer %s in the current buffer", enable and "enabled" or "disabled")}},
+ false,
+ {}
+ )
+ end
+end
+
+vim.api.nvim_create_user_command("ParinferOn", function(args)
+ set_enabled(args.bang, true)
+end, { bang = true, desc = "Enable parinfer" })
+
+vim.api.nvim_create_user_command("ParinferOff", function(args)
+ set_enabled(args.bang, false)
+end, { bang = true, desc = "Disable parinfer" })
+
+vim.api.nvim_create_user_command("ParinferToggle", function(args)
+ if args.bang then
+ set_enabled(true, not vim.g.parinfer_enabled)
+ else
+ set_enabled(false, not vim.b.parinfer_enabled)
+ end
+end, { bang = true, desc = "Toggle parinfer" })
+
+vim.api.nvim_create_user_command("ParinferLog", function(args)
+ local logfile = args.args
+ if logfile then
+ vim.g.parinfer_logfile = logfile
+ vim.api.nvim_echo(
+ {{string.format("Logging parinfer output to %s", logfile)}},
+ false,
+ {}
+ )
+ else
+ vim.g.parinfer_logfile = nil
+ vim.api.nvim_echo(
+ {{"Disabled parinfer logging"}},
+ false,
+ {}
+ )
+ end
+end, { nargs = "?", desc = "Log parinfer output to a file" })
+
+vim.api.nvim_set_keymap("i", "(parinfer-tab)", "", {
+ noremap = true,
+ callback = function()
+ return require("parinfer.setup").tab(true)
+ end,
+ desc = "Move forward to the next tab stop",
+})
+
+vim.api.nvim_set_keymap("i", "(parinfer-backtab)", "", {
+ noremap = true,
+ callback = function()
+ return require("parinfer.setup").tab(false)
+ end,
+ desc = "Move backward to the previous tab stop",
+})
+
+vim.api.nvim_create_augroup("parinfer", {clear = true})
+vim.api.nvim_create_autocmd("FileType", {
+ group = "parinfer",
+ pattern = "janet",
+ callback = function(args)
+ vim.b[args.buf].parinfer_comment_chars = {"#"}
+ end,
+})
+vim.api.nvim_create_autocmd("FileType", {
+ group = "parinfer",
+ pattern = "*",
+ callback = function(args)
+ if vim.o.previewwindow or vim.bo[args.buf].buftype == "prompt" then
+ return
+ end
+
+ local ft = vim.bo[args.buf].filetype
+ local found = false
+ for _, v in ipairs(vim.g.parinfer_filetypes) do
+ if v == ft then
+ found = true
+ break
+ end
+ end
+
+ if not found then
+ return
+ end
+
+ local parinfer = require("parinfer.setup")
+
+ parinfer.enter_buffer()
+
+ vim.api.nvim_buf_create_user_command(args.buf, "ParinferStats", parinfer.stats, {
+ desc = "Display parinfer runtime statistics",
+ })
+
+ vim.api.nvim_create_autocmd({"TextChanged", "TextChangedI", "TextChangedP"}, {
+ buffer = args.buf,
+ callback = function(a) parinfer.text_changed(a.buf) end,
+ })
+
+ vim.api.nvim_create_autocmd({"CursorMoved", "CursorMovedI"}, {
+ buffer = args.buf,
+ callback = function(a) parinfer.cursor_moved(a.buf) end,
+ })
+
+ if vim.F.if_nil(vim.b.parinfer_no_maps, vim.g.parinfer_no_maps) ~= true then
+ if vim.fn.mapcheck("", "i") == "" then
+ vim.api.nvim_buf_set_keymap(args.buf, "i", "", "(parinfer-tab)", {})
+ end
+
+ if vim.fn.mapcheck("", "i") == "" then
+ vim.api.nvim_buf_set_keymap(args.buf, "i", "", "(parinfer-backtab)", {})
+ end
+ end
+
+ end,
+})
diff --git a/plugin/parinfer.vim b/plugin/parinfer.vim
deleted file mode 100644
index c1fabcc..0000000
--- a/plugin/parinfer.vim
+++ /dev/null
@@ -1,55 +0,0 @@
-" Copyright (C) 2021 Gregory Anders
-"
-" SPDX-License-Identifier: GPL-3.0-or-later
-"
-" This program is free software: you can redistribute it and/or modify
-" it under the terms of the GNU General Public License as published by
-" the Free Software Foundation, either version 3 of the License, or
-" (at your option) any later version.
-"
-" This program is distributed in the hope that it will be useful,
-" but WITHOUT ANY WARRANTY; without even the implied warranty of
-" MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-" GNU General Public License for more details.
-"
-" You should have received a copy of the GNU General Public License
-" along with this program. If not, see .
-
-if exists('g:loaded_parinfer') || !has('nvim')
- finish
-endif
-let g:loaded_parinfer = v:true
-
-if !exists('g:parinfer_mode')
- let g:parinfer_mode = 'smart'
-endif
-
-if !exists('g:parinfer_enabled')
- let g:parinfer_enabled = v:true
-endif
-
-if !exists('g:parinfer_force_balance')
- let g:parinfer_force_balance = v:false
-endif
-
-if !exists('g:parinfer_comment_chars')
- let g:parinfer_comment_chars = [';']
-endif
-
-if !exists('g:parinfer_filetypes')
- let g:parinfer_filetypes = ['clojure', 'scheme', 'lisp', 'racket', 'hy', 'fennel', 'janet', 'carp', 'wast', 'yuck']
-endif
-
-command! -bang ParinferOn call parinfer#enable(0, 1)
-command! -bang ParinferOff call parinfer#enable(0, 0)
-command! -bang ParinferToggle call parinfer#toggle(0)
-command! -nargs=? ParinferLog call parinfer#log()
-
-augroup parinfer
- autocmd!
- autocmd FileType janet let b:parinfer_comment_chars = ['#']
- autocmd FileType * if index(g:parinfer_filetypes, &filetype) != -1 | call parinfer#init() | endif
-augroup END
-
-inoremap (parinfer-tab) lua parinfer.tab(true)
-inoremap (parinfer-backtab) lua parinfer.tab(false)