irongit

A Neovim plugin enabling you to solve LeetCode problems.

feat: support for rendering images with `image.nvim`

kawreauthored
parent cb10052commit cd90b3e0ddd20552db01fb2af4439517381c2a38Browse files

5 files changed, +70 -11

+2-1.neoconf.json
@@ -7,7 +7,8 @@
77 "telescope.nvim",
88 "plenary.nvim",
99 "nui.nvim",
10- "nvim-web-devicons"
10+ "nvim-web-devicons",
11+ "image.nvim"
1112 ]
1213 }
1314 }
+15-0README.md
@@ -130,6 +130,9 @@ To see full configuration types see [template.lua](./lua/leetcode/config/templat
130130 ---@type fun(question: { lang: string })[]
131131 LeetQuestionNew = {},
132132 },
133+
134+ ---@type boolean
135+ image_support = false, -- setting this to `true` will disable question description wrap
133136 }
134137 ```
135138
@@ -199,6 +202,15 @@ hooks = {
199202 },
200203 ```
201204
205+### image support
206+
207+Whether to render question description images using [image.nvim]
208+
209+```lua
210+---@type boolean
211+image_support = false, -- setting this to `true` will disable question description wrap
212+```
213+
202214 ## 📋 Commands
203215
204216 ### `Leet` opens menu dashboard
@@ -274,10 +286,12 @@ local leet_arg = "leetcode.nvim"
274286
275287 return {
276288 "kawre/leetcode.nvim",
289+ ...
277290 lazy = leet_arg ~= vim.fn.argv()[1],
278291 opts = {
279292 arg = leet_arg,
280293 },
294+ ...
281295 }
282296 ```
283297
@@ -295,6 +309,7 @@ return {
295309
296310 - [alpha-nvim](https://github.com/goolord/alpha-nvim)
297311
312+[image.nvim]: https://github.com/3rd/image.nvim
298313 [lazy.nvim]: https://github.com/folke/lazy.nvim
299314 [leetcode]: https://leetcode.com
300315 [leetcode.nvim]: https://github.com/kawre/leetcode.nvim
+3-0lua/leetcode/config/template.lua
@@ -93,6 +93,9 @@ local M = {
9393 ---@type fun(question: { lang: string })[]
9494 LeetQuestionNew = {},
9595 },
96+
97+ ---@type boolean
98+ image_support = false, -- setting this to `true` will disable question description wrap
9699 }
97100
98101 return M
+9-0lua/leetcode/parser/html.lua
@@ -165,6 +165,15 @@ function Html:handle_link(text, tag_data)
165165 if attr.name == "src" then return attr end
166166 end, tag_data.attrs)[1] or {}
167167 link = src.value or ""
168+
169+ -- local bufnr = vim.api.nvim_get_current_buf()
170+ -- local image = image_api.from_url(link, {
171+ -- -- buffer = bufnr,
172+ -- -- with_virtual_padding = true,
173+ -- }, function(image)
174+ -- --
175+ -- image:render()
176+ -- end)
168177 end
169178
170179 local line = NuiLine()
+41-10lua/leetcode/ui/description.lua
@@ -1,4 +1,9 @@
11 local config = require("leetcode.config")
2+local log = require("leetcode.logger")
3+
4+local img_ok, image_api = pcall(require, "image")
5+local img_sup = img_ok and config.user.image_support
6+
27 local parser = require("leetcode.parser")
38
49 local Layout = require("leetcode-ui.layout")
@@ -15,6 +20,7 @@ local Split = require("nui.split")
1520 ---@field title any
1621 ---@field layout lc-ui.Layout
1722 ---@field visible boolean
23+---@field images table<string, Image>
1824 local description = {}
1925 description.__index = description
2026
@@ -45,7 +51,7 @@ function description:mount()
4551 })
4652 utils.set_win_opts(self.split.winid, {
4753 winhighlight = "Normal:NormalFloat,FloatBorder:FloatBorder",
48- wrap = true,
54+ wrap = not img_sup,
4955 colorcolumn = "",
5056 foldlevel = 999,
5157 foldcolumn = "1",
@@ -57,6 +63,9 @@ function description:mount()
5763 spell = false,
5864 signcolumn = "no",
5965 })
66+ if not img_ok and config.user.image_support then
67+ log.error("image.nvim not found but `image_support` is enabled")
68+ end
6069
6170 self:draw()
6271 self:autocmds()
@@ -74,16 +83,37 @@ function description:toggle()
7483 end
7584
7685 function description:draw()
77- -- local c = vim.api.nvim_win_get_cursor(self.split.winid)
7886 self.layout:draw(self.split)
79- -- vim.api.nvim_win_set_cursor(self.split.winid, c)
87+ self:draw_imgs()
8088 end
8189
82--- function description:redraw()
83--- local c = vim.api.nvim_win_get_cursor(self.split.winid)
84--- self.layout:draw()
85--- vim.api.nvim_win_set_cursor(self.split.winid, c)
86--- end
90+function description:draw_imgs()
91+ if not img_sup then return end
92+
93+ local lines = vim.api.nvim_buf_get_lines(self.split.bufnr, 1, -1, false)
94+ for i, line in ipairs(lines) do
95+ for link in line:gmatch("->%((http[s]?://%S+)%)") do
96+ local img = self.images[link]
97+
98+ if not img then
99+ self.images[link] = {}
100+
101+ image_api.from_url(link, {
102+ buffer = self.split.bufnr,
103+ window = self.split.winid,
104+ with_virtual_padding = true,
105+ }, function(image)
106+ if not image then return end
107+
108+ self.images[link] = image
109+ image:render({ y = i + 1 })
110+ end)
111+ elseif not vim.tbl_isempty(img) then
112+ img:clear(true)
113+ end
114+ end
115+ end
116+end
87117
88118 ---@private
89119 function description:populate()
@@ -147,14 +177,15 @@ function description:init(parent)
147177 focusable = true,
148178 })
149179
150- local obj = setmetatable({
180+ self = setmetatable({
151181 split = split,
152182 parent = parent,
153183 layout = {},
154184 visible = false,
185+ images = {},
155186 }, self)
156187
157- return obj:mount()
188+ return self:mount()
158189 end
159190
160191 return description