LunarVimのすゝめ

## はじめに
### LunarVimって何？
Neovim向けのIDEレイヤです。
非常に高速で拡張性に優れていて、`Treesitter`や`NativeLSP`に標準対応しています。
また、**既存のNeovim設定と併用することができます**。（←ここ重要）


* github
https://github.com/LunarVim/LunarVim

* docs
https://www.lunarvim.org

* 作者さんのDiscordサーバー
https://discord.gg/Xb9B4Ny

 ![](https://github.com/LunarVim/LunarVim/raw/rolling/utils/media/demo1.png)
 ![](https://github.com/LunarVim/LunarVim/raw/rolling/utils/media/demo2.png)
 ![](https://github.com/LunarVim/LunarVim/raw/rolling/utils/media/demo3.png)

## インストール

注意：　**v0.5以降のNeovimが必要です。**

### packer.nvim

luaで書かれたNeovim向けのプラグイン管理プラグインです。
コレがないとLunarVimのインストール中にエラーがでます。

```sh
git clone --depth 1 https://github.com/wbthomason/packer.nvim\
 ~/.local/share/nvim/site/pack/packer/start/packer.nvim
 ```

### Nerd Fonts
[ここ](https://www.nerdfonts.com/)からダウンロードできます。
諸々のアイコンを表示するために必要です。
詳しい使い方は[gg](https://www.google.com/)ってください。

### LunarVim

LunarVimは現在開発段階です。
StableでもRollingでもバグはあるので、修正が早いRollingをおすすめします。
また、上で述べたように既存のnvim設定とは衝突しないため、`~/.config/nvim/`等はそのままで問題ありません。

* Rolling

```sh
LV_BRANCH=rolling bash <(curl -s https://raw.githubusercontent.com/lunarvim/lunarvim/rolling/utils/installer/install.sh)
```

* Stable

```sh
bash <(curl -s https://raw.githubusercontent.com/lunarvim/lunarvim/master/utils/installer/install.sh)
```

途中でNode.js, Python, Rustの依存関係をインストールするか尋ねられます。
それぞれTreesitterやpynvim、ripgrep等を使う際に必要になりますので、基本的にはすべて`yes`を選択してください。
インストールが正常に終了したら、LunarVimが使えるようになっているはずです。
コマンドラインにて、`lvim` で LunarVim、 `nvim` で既存のNeovimが起動することを確認してください。

```sh
lvim        #LunarVimを起動
nvim        #Neovimを既存の設定で起動
```
もし`lvim`を実行しても冒頭のようなメニュー画面が表示されず、初期状態のNeovimが起動するようでしたら、その状態で

```vim
:PackerInstall
```
を実行し、パッケージのインストールが終了したらlvimを再起動してください。

## 実際に使ってみる
### とりあえず
設定ファイルを開いてみましょう。
メニュー画面の下の方にある`Configuration`にカーソルを持っていき、Enterで選択します。
すると`~/.config/lvim/config.lua`が開き、その際に自動でLuaのLSPがインストールされます。
実際にLSPが動いていることを確かめてみましょう。
試しに`""`の片方を削除してみると...

![01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1428783/7d988f71-e126-8495-99b3-e535c6cc86e8.png)

ちゃんとエラーメッセージが表示されます。

![02.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/1428783/52dffa4b-b793-d0e1-02d4-c2b9a90c4c6e.png)

補完も効きます。

各言語のTreesitterは

```vim
:TSInstall <TAB>
```

LSPは

```
:LspInstall <TAB>
```
でインストールできます。
`Treesitter`の対応言語は[こちら](https://github.com/nvim-treesitter/nvim-treesitter#supported-languages)、
`NativeLSP`の対応言語は[こちら](https://github.com/williamboman/nvim-lsp-installer#available-lsps)を参照してください。

言語の名前とLSPの名前が異る場合がありますので注意してください。
例えば、RubyのLSPが`solargraph`だったり、scalaが`metals`だったりします。
そこらへんは対応言語と一緒に確認してください。

### 設定ファイルをいじってみる
基本的には普通のNeovim設定をLuaで書くときと同じです。
`:w`すると自動で`:so %`されます。
また、lvimは独自の関数を提供しています。
例えばプラグインをインストールする際に、

```lua
lvim.plugins = {
    {"folke/tokyonight.nvim"},
    {
      "folke/trouble.nvim",
      cmd = "TroubleToggle",
    },
}
```

のような書き方ができます。
この記事では詳細な設定には踏み入りませんので、適宜[公式ドキュメント](https://www.lunarvim.org/configuration/01-settings.html)等を参考にしてください。

### 各言語向けの設定例
#### C/C++
* Treesitter

```vim
:TSInstall c
:TSInstall cpp
```

* LSP

```vim
:LspInstall clangd
```

* フォーマッタ

`clangd`はデフォルトで`clang_format`を提供していますが、他にも`uncrustify`等を使うこともできます。

```lua
local formatters = require "lvim.lsp.null-ls.formatters"
formatters.setup { { exe = "uncrustify", args = {} } }
```
その際、フォーマッタは自前でインストールする必要があります。

* LSPカスタマイズ例

```lua
local clangd_flags = {
  "--all-scopes-completion",
  "--suggest-missing-includes",
  "--background-index",
  "--pch-storage=disk",
  "--cross-file-rename",
  "--log=info",
  "--completion-style=detailed",
  "--enable-config", -- clangd 11+ supports reading from .clangd configuration file
  "--clang-tidy",
  -- "--clang-tidy-checks=-*,llvm-*,clang-analyzer-*,modernize-*,-modernize-use-trailing-return-type",
  -- "--fallback-style=Google",
  -- "--header-insertion=never",
  -- "--query-driver=<list-of-white-listed-complers>"
}
local clangd_bin = "clangd"

local custom_on_attach = function(client, bufnr)
  require("lvim.lsp").common_on_attach(client, bufnr)
  local opts = { noremap = true, silent = true }
  vim.api.nvim_buf_set_keymap(bufnr, "n", "<leader>lh", "<Cmd>ClangdSwitchSourceHeader<CR>", opts)
end

local opts = {
  cmd = { clangd_bin, unpack(clangd_flags) },
  on_attach = custom_on_attach,
}

require("lvim.lsp.manager").setup("clangd", opts)
```

* デバッガ

```vim
:DIInstall ccppr_vsc
```

`pretty-printing`を有効にするには、以下のように設定します。

```lua:~/.config/lvim/ftplugin/cpp.lua
local dap_install = require "dap-install"
dap_install.config("ccppr_vsc", {
  adapters = {
    type = "executable",
  },
  configurations = {
    {
      type = "cpptools",
      request = "launch",
      name = "Launch with pretty-print",
      program = function()
        return vim.fn.input('Path to exe: ', vim.fn.getcwd() .. '/', 'file')
      end,
      cwd = "${workspaceFolder}",
      stopOnEntry = true,
      setupCommands = {
        {
          description = "Enable pretty-printing",
          text = "-enable-pretty-printing",
        }
      }
    },
  }
})
```

#### Python
* Treesitter

```vim
:TSInstall python
```

* サポートされているLSP、フォーマッタ、リンタ

```lua
python = { "jedi_language_server", "pylsp", "pyright" }
python = { "autopep8", "black", "isort", "reorder-python-imports", "yapf" }
python = { "flake8", "pylint" }
```

* LSP設定

```vim
:NlspConfig pyright
```

* デバッガ

```vim
:DIInstall python
```

```lua:~/.config/lvim/ftplugin/python.lua
local dap_install = require "dap-install"
dap_install.config("python", {})
```

#### Rust
* Treesitter

```vim
:TSInstall rust
```

* サポートされているLSP、フォーマッタ

```lua
rust = { "rust_analyzer" }
rust = { "rustfmt" }
```

* LSP設定

```vim
:NlspConfig rust_analyzer
```

* デバッガ

```
:DIInstall codelldb
```

```lua:~/.config/lvim/ftplugin/rust.lua
local dap_install = require "dap-install"
dap_install.config("codelldb", {})
```

* 必要に応じて

```lua
lvim.lsp.override = { "rust" }
lvim.plugins = {
  {
    "simrat39/rust-tools.nvim",
    config = function()
      require("rust-tools").setup({
        tools = {
          autoSetHints = true,
          hover_with_actions = true,
          runnables = {
            use_telescope = true,
          },
        },
        server = {
          cmd = { vim.fn.stdpath "data" .. "/lsp_servers/rust/rust-analyzer" },
          on_attach = require("lvim.lsp").common_on_attach,
          on_init = require("lvim.lsp").common_on_init,
        },
        })
    end,
    ft = { "rust", "rs" },
  },
}
```

#### Go
* Treesitter

```vim
:TSInstall go
```

* サポートされているLSP、フォーマッタ

```lua
go = { "gopls" }
go = { "gofmt", "gofumpt", "goimports", "golines" }
```

* LSP設定

```vim
:NlspConfig gopls
```

* デバッガ

```vim
:DIInstall go_delve
```

```lua:~/.config/lvim/ftplugin/go.lua
local dap_install = require "dap-install"
dap_install.config("go_delve", {})
```

#### その他
細かい設定は[こちら](https://www.lunarvim.org/languages/#at-a-glance)を参照してください。

## 補足
### アップデート
内部からコマンドでアップデートすることができます。

```vim
:LvimUpdate
```

### アンインストール
スクリプトで自動でやってくれます。
**LunarVim関連は設定ファイルを含めてすべて消えます**のでご注意ください。

```sh
bash ~/.local/share/lunarvim/lvim/utils/installer/uninstall.sh
```

## あとがき
ここまで読んでいただきありがとうございます。
現状LunarVimに関する日本語で書かれた情報が殆どなかったため、拙い文章ではありますがこのような記事を書かせていただきました。
もし需要があれば、より詳しい設定方法等を説明した続編も書こうと考えております。
興味がある方はぜひコメントをお寄せください。