HakonHarnes / img-clip.nvim

Effortlessly embed images into any markup language, like LaTeX, Markdown or Typst
MIT License
443 stars 7 forks source link

feat: flexible config structure #30

Closed HakonHarnes closed 7 months ago

HakonHarnes commented 7 months ago

Related issue

Closes #25.

Summary of changes

The configuration now complies with the following structure:

opts = {
  default = {
    -- default opts...
  },

  filetypes = {
    markdown = {
      -- markdown specific opts...
    },
  },

  dirs = {
    ["/path/to/project-a"] = {
      -- project a specific opts...

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    },
    ["/path/to/project-b"] = {
      -- project b specific opts...

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    },
  },

  files = {
    ["readme.md"] = {
      -- any readme.md file specific opts...

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    },

    ["/path/to/project-b/notes.md"] = {
      -- just this note.md file specific opts...

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    },
  },

  custom = {
    {
      trigger = function()
        return ... -- return true/false to enable these settings 
      end,

      -- opts here... 

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    }, 
    { -- another custom config
      trigger = function()
        return ... -- return true/false to enable these settings 
      end,

      -- opts here... 

      filetypes = {
        markdown = {
          -- markdown specific opts...
        },
      },
    }
  }
},

Documentation

Options can be overridden for specific files, directories or based on custom conditions. This means that you can have different options for different projects, or even different files within the same project.

For files and directories, you can specify settings that apply to only a specific file or directory using its absolute path (e.g. /home/user/project/README.md). You can also specify a general file or directory name (e.g. README.md) which will apply the settings to any README.md file. For custom options, you can specify a trigger function that returns a boolean value that is used to enable it.

The plugin evaluates the options in the following order:

  1. Custom options
  2. File-specific options
  3. Directory-specific options
  4. File type-specific options
  5. Default options

Example configuration:

-- file-specific opts
files = {
  ["/path/to/specific/file.md"] = {
    template = "Custom template for this file",
  },
  ["README.md"] = {
    template = "Custom template for README.md files",
  },
},

-- directory-specific opts
dirs = {
  ["/path/to/project"] = {
    template = "Project-specific template",
  },
},

-- custom opts
custom = {
  {
    trigger = function() -- returns true to activate
      return vim.fn.strftime("%A") == "Monday"
    end,
    template = "Template for Mondays only",
  },
}

The options can be nested arbitrarily deep:

dirs = {
  ["/home/user/markdown"] = {
    template = "template for this project",

    filetypes = { -- filetypes opt nested inside dirs
      markdown = {
        template = "markdown template"
      }
    },

    files = { -- files opt nested inside dirs
      ["readme.md"] = {
        dir_path = "images"
      },
    },
  },
}
lervag commented 7 months ago

I've tested on a file specific config now, and this works very well for me. Thanks!

I've not tested the other things, but I'll pin myself to the branch and will let you know if I notice any issues!

zachary-foster commented 7 months ago

This is working pretty good! I tested out the dirs and files settings, but I dont think I know neovim/lua well enough to test the custom settings well. Here are a few issues I found:

dirs and files do not allow for symlinks

It seems that the dirs configuration section does not follow symlinks. For example, with the setup below:

redacted@pop-os:~/blog$ realpath .
/media/redacted/external_primary/files/projects/personal/blog
redacted@pop-os:~/blog$ pwd
/home/redacted/blog

Both files and ~/blog are symlinks. This works as expected:

dirs = {
  ["/media/redacted/external_primary/files/projects/personal/blog"] = ...

But this does not

dirs = {
  ["/home/redacted/blog"] = ...

Settings for file names in files overwrite settings for specific file paths

It seems that having the more specific path to a single file should overwrite the more general file name. For example:

    files = {
      ["readme.md"] = {
        file_name = "general-%H-%M-%S",
        },
      },

      ["/media/redacted/external_primary/files/temp/readme.md"] = {
          file_name = "specific-%H-%M-%S",
        },
      },
    },

results in the "/media/redacted/external_primary/files/temp/readme.md" setting being ignored. I would suggest either always making specific file paths take precedence over file names, or make the order the settings are written in the config file to decide the precedence.

HakonHarnes commented 7 months ago

I've made some comments to your docs, I hope you don't mind.

A developer voluntarily proof-reading my documentation? I absolutely don't mind!

Your comments should be addressed in the latest commits.

HakonHarnes commented 7 months ago

dirs and files do not allow for symlinks

Should be fixed in https://github.com/HakonHarnes/img-clip.nvim/pull/30/commits/658f098279930de5f3e9e5642da92e69074fb741

Settings for file names in files overwrite settings for specific file paths

Should be fixed in https://github.com/HakonHarnes/img-clip.nvim/pull/30/commits/98591d99253927a7acb841d69085e41f7ca8dafb. It will use the longest directory/file path that matches the currently opened file/directory So, more specific/longer file paths have precedence over general/shorter paths.

zachary-foster commented 7 months ago

I tried out the new version a bit more and I confirmed that the symlink issue is fixed. Thanks!

I noticed that the ~ representing the home directory is not being recognized. For example ~/project does not work but /home/user/project does.

HakonHarnes commented 7 months ago

I noticed that the ~ representing the home directory is not being recognized.

Should be fixed in https://github.com/HakonHarnes/img-clip.nvim/pull/30/commits/f48fdd44d53d89a05eea13c2bfb1bb28e3989538

lervag commented 7 months ago

Glad to see this merged. Nice work! Thanks!

HakonHarnes commented 7 months ago

Glad to see this merged. Nice work! Thanks!

Thanks for the feature request and your thoughts on how it should be implemented! I really think it's a big quality-of-life improvement for end-users :) Also thank you @zachary-foster for the extensive testing subsequent bug reports!

lervag commented 7 months ago

Glad to help! ;)