187 lines
6.1 KiB
Lua
187 lines
6.1 KiB
Lua
local awful = require("awful")
|
|
local wibox = require("wibox")
|
|
local gears = require("gears")
|
|
local beautiful = require("beautiful")
|
|
local menubar = require("menubar")
|
|
local naughty = require "naughty"
|
|
local cairo = require("lgi").cairo
|
|
local Rsvg = require("lgi").Rsvg
|
|
local longpress = require("awesome-longpress")
|
|
local launcherpopup = {
|
|
buttonsize = 128,
|
|
spacing = 5,
|
|
iconPath = gears.filesystem.get_configuration_dir() .. "/awesome-launcherpopup/",
|
|
updateOnSpawn = true,
|
|
font = "sans",
|
|
fontSize = 15,
|
|
applications = {},
|
|
allInstances = {}
|
|
}
|
|
|
|
function launcherpopup.update()
|
|
naughty.notify({text="started update"})
|
|
menubar.menu_gen.generate(function(rv)
|
|
launcherpopup.applications = rv
|
|
for k,v in pairs(launcherpopup.allInstances) do
|
|
if k and v then
|
|
w,e = pcall(v.populateMenu)
|
|
if not w then naughty.notify{text=e} end
|
|
end
|
|
end
|
|
end)
|
|
end
|
|
|
|
local function tryLoadIcon(icon)
|
|
local img = icon
|
|
if dentry.icon:match("%.([^%.]+)$") == "svg" then
|
|
naughty.notify{text="is svg"}
|
|
img = cairo.ImageSurface(cairo.Format.ARGB32,launcherpopup.buttonsize,launcherpopup.buttonsize)
|
|
local cr = cairo.Context(img)
|
|
Rsvg.Handle.new_from_file(dentry.icon):render_cairo(cr)
|
|
end
|
|
return img
|
|
end
|
|
|
|
local function getFont(scale)
|
|
return string.format("%s %d",launcherpopup.font,launcherpopup.fontSize * (scale or 1))
|
|
end
|
|
|
|
function launcherpopup.new(s)
|
|
local menuStart = 1
|
|
local launcherWidget = wibox.widget{
|
|
layout = wibox.layout.fixed.vertical,
|
|
spacing = launcherpopup.spacing
|
|
}
|
|
local launcher = awful.popup{
|
|
layout = wibox.layout.fixed.vertical,
|
|
widget = launcherWidget,
|
|
border_color = beautiful.border_focus,
|
|
border_width = 2,
|
|
ontop = true,
|
|
placement = awful.placement.centered,
|
|
visible = false,
|
|
screen = s,
|
|
}
|
|
local launcherButtons = wibox.widget{
|
|
layout = wibox.layout.grid.vertical,
|
|
spacing = launcherpopup.spacing
|
|
}
|
|
local launcherNav = wibox.widget{
|
|
layout = wibox.layout.ratio.horizontal,
|
|
forced_width = math.floor((s.geometry.width) / (launcherpopup.buttonsize + launcherpopup.spacing * 2)) * (launcherpopup.buttonsize + launcherpopup.spacing)
|
|
}
|
|
local launcherList = wibox.widget{
|
|
layout = wibox.layout.grid,
|
|
spacing = launcherpopup.spacing
|
|
}
|
|
launcherWidget:add(launcherList)
|
|
launcherWidget:add(launcherNav)
|
|
local launcherNextPage = wibox.widget{
|
|
widget = wibox.widget.imagebox,
|
|
image = launcherpopup.iconPath .. "/next.svg",
|
|
forced_width=launcherpopup.buttonsize * 0.75,
|
|
forced_height=launcherpopup.buttonsize * 0.75
|
|
}
|
|
local launcherPreviousPage = wibox.widget{
|
|
widget = wibox.widget.imagebox,
|
|
image = launcherpopup.iconPath .. "/previous.svg",
|
|
forced_width=launcherpopup.buttonsize * 0.75,
|
|
forced_height=launcherpopup.buttonsize * 0.75
|
|
}
|
|
launcherNav:add(
|
|
wibox.container.place(launcherPreviousPage,"left","top"),
|
|
wibox.container.place(launcherNextPage,"right","top"))
|
|
local function fillMenu()
|
|
launcherList:reset()
|
|
local maxRows = math.floor(s.geometry.height / (launcherpopup.buttonsize * 1.5 + launcherpopup.spacing * 2)) - 2
|
|
local maxColumns = math.floor((s.geometry.width) / (launcherpopup.buttonsize + launcherpopup.spacing * 2))
|
|
local maxEntries = maxRows * maxColumns
|
|
local x,y = 1,1
|
|
for y = 1, maxRows do
|
|
for x = 1, maxColumns do
|
|
local dentry = launcherpopup.applications[(menuStart - 1) + (y-1)*maxColumns + x]
|
|
if not dentry then dentry = {icon="",name=""} end
|
|
local mwidget = wibox.widget{
|
|
layout = wibox.layout.fixed.vertical
|
|
}
|
|
local mwicon = wibox.widget{
|
|
image = dentry.icon or launcherpopup.iconPath .. "/default.svg",
|
|
widget = wibox.widget.imagebox,
|
|
forced_width = launcherpopup.buttonsize,
|
|
forced_height = launcherpopup.buttonsize
|
|
}
|
|
mwidget:add(mwicon)
|
|
local mwtext = wibox.container.constraint(wibox.widget{
|
|
widget = wibox.widget.textbox,
|
|
valign = center,
|
|
align = center,
|
|
font = getFont(),
|
|
text = dentry.name
|
|
},"exact",launcherpopup.buttonsize,launcherpopup.buttonsize * 0.5)
|
|
mwidget:add(mwtext)
|
|
longpress.add(mwidget,function()
|
|
if dentry.cmdline then
|
|
awful.spawn(dentry.cmdline)
|
|
launcher:hide()
|
|
end
|
|
end)
|
|
launcherList:add_widget_at(wibox.container.constraint(mwidget,"max",launcherpopup.buttonsize,launcherpopup.buttonsize*1.5),y,x)
|
|
end
|
|
end
|
|
end
|
|
local function goToEntry(n)
|
|
local maxRows = math.floor(s.geometry.height / (launcherpopup.buttonsize * 1.5 + launcherpopup.spacing * 2)) - 2
|
|
local maxColumns = math.floor((s.geometry.width) / (launcherpopup.buttonsize + launcherpopup.spacing * 2))
|
|
local maxEntries = maxRows * maxColumns
|
|
menuStart = n
|
|
if menuStart < 1 then menuStart = (math.floor(#launcherpopup.applications / maxEntries) * maxEntries) + 1 end
|
|
if menuStart > #launcherpopup.applications then menuStart = 1 end
|
|
fillMenu()
|
|
end
|
|
longpress.add(launcherNextPage,function()
|
|
goToEntry(menuStart + ((math.floor(s.geometry.height / (launcherpopup.buttonsize * 1.5 + launcherpopup.spacing * 2)) - 2) * math.floor((s.geometry.width) / (launcherpopup.buttonsize + launcherpopup.spacing * 2))))
|
|
end,
|
|
function()
|
|
goToEntry(#launcherpopup.applications)
|
|
end)
|
|
longpress.add(launcherPreviousPage,function()
|
|
goToEntry(menuStart - ((math.floor(s.geometry.height / (launcherpopup.buttonsize * 1.5 + launcherpopup.spacing * 2)) - 2) * math.floor((s.geometry.width) / (launcherpopup.buttonsize + launcherpopup.spacing * 2))))
|
|
end,
|
|
function()
|
|
goToEntry(1)
|
|
end)
|
|
function launcher.populateMenu()
|
|
fillMenu()
|
|
end
|
|
function launcher.addButton(icon, fn)
|
|
local newButton = awful.widget.button{
|
|
image = launcherpopup.iconPath .. "/" .. icon
|
|
}
|
|
newButton:set_forced_width(launcherpopup.buttonsize)
|
|
newButton:set_forced_height(launcherpopup.buttonsize)
|
|
newButton:buttons(gears.table.join(
|
|
newButton:buttons(),
|
|
awful.button({}, 1, nil, function()
|
|
fn()
|
|
launcher:hide()
|
|
end)
|
|
))
|
|
launcherButtons:add(newButton)
|
|
end
|
|
|
|
function launcher.show(self)
|
|
self.visible = true
|
|
end
|
|
function launcher.hide(self)
|
|
self.visible = false
|
|
end
|
|
function launcher.toggle(self)
|
|
self.visible = not self.visible
|
|
end
|
|
launcherpopup.allInstances[#launcherpopup.allInstances+1] = launcher
|
|
launcherpopup.update()
|
|
return launcher
|
|
end
|
|
|
|
return launcherpopup
|