#
# Neovim home-manager configuration (CoC).
#
# vim: et:ts=2:sw=2:
#
{ nil, ... }:
{
  home-manager.users.deprekated =
    { pkgs, ... }:
    {

      # CoC configuration for Neovim.
      programs.neovim = {

        extraPackages = with pkgs; [ clang-tools ];

        coc = {
          enable = true;

          pluginConfig = ''
            set completeopt=menu,menuone,preview,noselect,noinsert

            function! CheckBackspace() abort
              let l:col = col('.') - 1
              return !col || getline('.')[col - 1]  =~# '\s'
            endfunction

            " Accept the selected completion with <CR>.
            inoremap <expr> <CR> coc#pum#visible() ? coc#pum#confirm() : "\<CR>"

            " Select the next completion with <Tab>.
            inoremap <expr> <Tab> coc#pum#visible() ? coc#pum#next(1) : CheckBackspace() ? "\<Tab>" : coc#refresh()

            " Select the previous completion with <S-Tab>
            inoremap <expr><S-TAB> coc#pum#visible() ? coc#pum#prev(1) : "\<C-h>"
          '';

          settings = {

            suggest = {
              enablePreview = true;
              floatEnable = true;
              autoTrigger = "always";
              preferCompleteThanJumpPlaceholder = true;
              maxCompleteItemCount = 100;
              snippetsSupport = false;
              localityBonus = true;
              minTriggerInputLength = 3;
              acceptSuggestionOnCommitCharacter = true;
              noselect = true;
              removeDuplicateItems = true;
            };

            colors.filetypes = [
              "vim"
              "c"
              "cpp"
              "python"
              "rust"
            ];

            semanticTokens.filetypes = [
              "vim"
              "c"
              "cpp"
              "python"
              "rust"
            ];

            diagnostic = {
              diagnostic.checkCurrentLine = true;
              diagnostic.virtualText = true;
              diagnostic.virtualTextLevel = "error";
              diagnostic.separateRelatedInformationAsDiagnostics = true;
            };

            signature = {
              enable = true;
              target = "float";
            };

            hover.target = "float";
            codeLens.enable = false;

            coc = {
              preferences = {
                currentFunctionSymbolAutoUpdate = true;
                jumpCommand = "tabe";

                formatOnSaveFiletypes = [
                  "css"
                  "typescript"
                  "javascript"
                  "cpp"
                  "nix"
                  "rust"
                ];
              };
            };

            cpp = {
              referencesCodeLens.enable = false;
            };
            c = {
              referencesCodeLens.enable = false;
            };
            swift = {
              referencesCodeLens.enable = false;
            };

            vimlsp.trace.server = "messages";
            git.enableGlobalStatus = false;
            json.enable = true;
            json.trace.server = "messages";

            python = {
              linting = {
                enabled = true;
                pylintUseMinimalCheckers = true;
                pylintEnabled = true;
                pylintArgs = [
                  "--max-line-length"
                  "120"
                  "--max-args"
                  "8"
                  "--extension-pkg-whitelist=PySide2"
                  "--disable=C0326"
                  "--disable=no-else-return"
                ];
              };
              formatting.provider = "black";
            };

            pyright.trace.server = "messages";
            python.analysis.useLibraryCodeForTypes = true;

            rust-analyzer = {
              serverPath = "/run/current-system/sw/bin/rust-analyzer";
              lens.implementations = false;
              trace.server = "messages";
              updates.checkOnStartup = false;
            };

            suggest.completionItemKindLabels = {
              variable = "var";
              function = "fun";
              method = "meth";
              module = "mod";
              value = "val";
              default = "default";
              keyword = "key";
              class = "class";
              unit = "unit";
              field = "field";
              property = "prop";
              constant = "const";
              operator = "op";
              reference = "ref";
              typeParameter = "type param";
              text = "text";
              enum = "enum";
              file = "file";
              color = "color";
              event = "event";
              folder = "folder";
              struct = "struct";
              snippet = "snip";
              interface = "interface";
              enumMember = "enum member";
            };

            languageserver = {
              nix = {
                command = "${nil.nil}/bin/nil";
                filetypes = [ "nix" ];
                rootPatterns = [ "flake.nix" ];
                settings.nil.formatting.command = [ "${pkgs.nixfmt-rfc-style}/bin/nixfmt" ];
              };
            };

            diagnostic-languageserver = {
              enable = true;

              formatFiletypes = {
                "js" = "prettier";
                "c" = "clang-format";
                "cpp" = "clang-format";
                "nix" = "nixfmt";
              };

              formatters = {
                prettier = {
                  command = "prettier";
                  args = [
                    "--stdin"
                    "--stdin-filepath"
                    "%filepath"
                  ];
                  rootPatterns = [
                    ".prettierrc"
                    ".prettierrc.json"
                    ".prettierrc.toml"
                    ".prettierrc.json"
                    ".prettierrc.yml"
                    ".prettierrc.yaml"
                    ".prettierrc.json5"
                    ".prettierrc.js"
                    ".prettierrc.cjs"
                    "prettier.config.js"
                    "prettier.config.cjs"
                  ];
                };
                clang-format = {
                  command = "clang-format";
                  args = [ "%filepath" ];
                  rootPatterns = [ ".clang-format" ];
                };
                nixfmt.command = "${pkgs.nixfmt-rfc-style}/bin/nixfmt";
              };
            };

            explorer = {
              icon = {
                source = "vim-devicons";
                enableNerdfont = true;
              };
              width = 30;
            };
          };
        };
      };
    };
}
