dotfiles/.config/lite-xl/libraries/widget/itemslist.lua

161 lines
3.9 KiB
Lua

--
-- ItemsList Widget.
-- @copyright Jefferson Gonzalez
-- @license MIT
--
local style = require "core.style"
local Widget = require "libraries.widget"
local Button = require "libraries.widget.button"
local ListBox = require "libraries.widget.listbox"
local InputDialog = require "libraries.widget.inputdialog"
local MessageBox = require "libraries.widget.messagebox"
---@class widget.itemslist : widget
---@field list widget.listbox
---@field add widget.button
---@field remove widget.button
local ItemsList = Widget:extend()
---Constructor
---@param parent widget
function ItemsList:new(parent)
ItemsList.super.new(self, parent)
self.type_name = "widget.itemslist"
self.border.width = 0
self.dialog = false
self.list = ListBox(self)
local this = self
function self.list:on_mouse_pressed(button, x, y, clicks)
if not ListBox.on_mouse_pressed(self, button, x, y, clicks) then
return false
end
if clicks == 2 and not this.dialog then
this.dialog = true
local selected = this.list:get_selected()
local selvalue = this.list:get_row_text(selected)
---@type widget.inputdialog
local input = InputDialog("Edit Item", "Enter the new item value:", selvalue)
function input:on_save(value)
this:edit_item(selected, value)
end
function input:on_close()
InputDialog.on_close(self)
self:destroy()
this.dialog = false
end
input:show()
end
return true
end
self.add = Button(self, "Add")
self.add:set_icon("B")
function self.add:on_click()
if not this.dialog then
---@type widget.inputdialog
local input = InputDialog("Add Item", "Enter the new item:")
function input:on_save(value)
this:add_item(value)
end
function input:on_close()
InputDialog.on_close(self)
self:destroy()
this.dialog = false
end
input:show()
end
end
self.remove = Button(self, "Remove")
self.remove:set_icon("C")
function self.remove:on_click()
local selected = this.list:get_selected()
if selected then
this:remove_item(selected)
else
MessageBox.error("No item selected", "Please select an item to remove")
end
end
end
---Add a new item into the list.
---@param text widget.styledtext | string
---@param data any
function ItemsList:add_item(text, data)
if type(text) == "string" then
text = {text}
end
self.list:add_row(text, data)
self.list:set_visible_rows()
self:on_change()
end
---Edit an existing item on the list.
---@param idx integer
---@param text widget.styledtext | string
---@param data any
function ItemsList:edit_item(idx, text, data)
if type(text) == "string" then
text = {text}
end
self.list:set_row(idx, text)
if data then
self.list:set_row_data(idx, data)
end
self:on_change()
end
---Remove the given item from the list.
---@param idx integer
function ItemsList:remove_item(idx)
self.list:remove_row(idx)
self:on_change()
end
---Return the items from the list.
---@return table<integer, string>
function ItemsList:get_items()
local output = {}
local count = #self.list.rows
for i=1, count, 1 do
table.insert(output, self.list:get_row_text(i))
end
return output
end
function ItemsList:update()
if not ItemsList.super.update(self) then return false end
if self.size.x == 0 then
self.size.x = self.add:get_width()
+ (style.padding.x / 2) + self.remove:get_width() + (50 * SCALE)
self.size.y = self.add:get_height() + (style.padding.y * 2) + 100
end
self.list:set_position(0, 0)
self.list:set_size(
self.size.x,
self.size.y - self.add:get_height() - (style.padding.y * 2)
)
self.add:set_position(0, self.list:get_bottom() + style.padding.y)
self.remove:set_position(
self.add:get_right() + (style.padding.x / 2),
self.list:get_bottom() + style.padding.y
)
return true
end
return ItemsList