3rd / image.nvim

🖼️ Bringing images to Neovim.
MIT License
803 stars 35 forks source link

Telescope preview issue #183

Open miszo opened 1 week ago

miszo commented 1 week ago

I'm trying to use your plugin to render previews in telescope. I've created a bufferpreviewer_maker like this:

local previewers = require('telescope.previewers')
local image_api = require('image')

local M = {}
local is_image_preview = false
local supported_images = { 'png', 'jpg', 'jpeg', 'heic', 'avif', 'gif', 'webp' }
local image = nil
local last_file_path = ''

local get_extension = function(filepath)
  local split_path = vim.split(filepath:lower(), '.', { plain = true })
  return split_path[#split_path]
end

local is_supported_image = function(filepath)
  local extension = get_extension(filepath)
  return vim.tbl_contains(supported_images, extension)
end

local delete_image = function()
  if not image then
    return
  end
  image:clear()
  is_image_preview = false
end

local create_image = function(filepath, winid, bufnr)
  image = image_api.from_file(filepath, { window = winid, buffer = bufnr })
  if not image then
    return
  end
  image:render()

  is_image_preview = true
end

M.buffer_previewer_maker = function(filepath, bufnr, opts)
  -- NOTE: Clear image when preview other file
  if is_image_preview and last_file_path ~= filepath then
    delete_image()
  end

  last_file_path = filepath

  local extension = get_extension(filepath)
  if is_supported_image(extension) then
    create_image(filepath, opts.winid, bufnr)
  else
    previewers.buffer_previewer_maker(filepath, bufnr, opts)
  end
end

M.teardown = function()
  if is_image_preview then
    delete_image()
  end
end

return M

And I have the problem when I try to preview the image for the first time – it doesn't render, it renders on the second attempt.

1st preview attempt 2nd preview attempt

I think that the problem is in the create_image function.

local create_image = function(filepath, winid, bufnr)
  image = image_api.from_file(filepath, { window = winid, buffer = bufnr })
  if not image then
    return
  end
  image:render()

  is_image_preview = true
end

Any ideas how to resolve the issue?

My env:

Plugin setup:

  {
    'vhyrro/luarocks.nvim',
    priority = 1001, -- this plugin needs to run before anything else
    opts = {
      rocks = { 'magick' },
    },
  },
  {
    '3rd/image.nvim',
    dependencies = { 'luarocks.nvim' },
    config = function(_, opts)
      opts.integrations = opts.integrations or {}
      opts.integrations.markdown = opts.integrations.markdown or {}
      opts.integrations.markdown.only_render_image_at_cursor = true
      opts.hijack_file_patterns = opts.hijack_file_patterns or {}
      opts.hijack_file_patterns = { '*.png', '*.jpg', '*.jpeg', '*.gif', '*.webp', '*.avif', '*.heic' }
      opts.window_overlap_clear_enabled = true -- tried to remove or change it to false, the outcome was the same
      require('image').setup(opts)
    end,
  },
miszo commented 1 week ago

I've added the echo statement in the create_image function

local create_image = function(filepath, winid, bufnr)
  image = image_api.from_file(filepath, { window = winid, buffer = bufnr })
  if not image then
    return
  end
  image:render()

  vim.api.nvim_echo({
    { 'image.is_rendered: ' .. tostring(image.is_rendered), nil },
  }, false, {})

  is_image_preview = true
end

And on the first try it prints image.is_rendered: false

CleanShot 2024-06-22 at 21 00 33@2x

But on the second try it returns the image.is_rendered: true

CleanShot 2024-06-22 at 21 02 26@2x

miszo commented 1 week ago

I'm not sure whether it should be the actual solution, but I've wrapped it with the vim.defer_fn and it works every time 😅

local create_image = function(filepath, winid, bufnr)
  image = image_api.from_file(filepath, { window = winid, buffer = bufnr })
  if not image then
    return
  end
  vim.defer_fn(function()
    image:render()
  end, 0)

  is_image_preview = true
end
exosyphon commented 2 days ago

@miszo I'd love to play around with this telescope previewer. Do you have a repo to install this as a telescope extension?

miszo commented 2 days ago

@exosyphon, didn't go that deep to set up this as a telescope extension.

Here's the code for: