7
|
1 |
require("naughty")
|
|
2 |
require("awful")
|
|
3 |
require("debug")
|
|
4 |
require("vicious")
|
|
5 |
require("wicked")
|
|
6 |
require("beautiful")
|
|
7 |
|
|
8 |
local ipairs = ipairs
|
|
9 |
local pairs = pairs
|
|
10 |
local naughty = naughty
|
|
11 |
local awful = awful
|
|
12 |
local debug = debug
|
|
13 |
local vicious = vicious
|
|
14 |
local wicked = wicked
|
|
15 |
local beautiful = beautiful
|
|
16 |
|
|
17 |
local capi = {
|
|
18 |
keygrabber = keygrabber,
|
|
19 |
client = client,
|
|
20 |
string = string,
|
|
21 |
widget = widget,
|
|
22 |
}
|
|
23 |
|
|
24 |
module("my")
|
|
25 |
|
|
26 |
local in_error = false
|
|
27 |
function notify_error(err)
|
|
28 |
-- Make sure we don't go into an endless error loop
|
|
29 |
if in_error then return end
|
|
30 |
in_error = true
|
|
31 |
|
|
32 |
naughty.notify({ preset = naughty.config.presets.critical,
|
|
33 |
title = "Oops, an error happened!",
|
|
34 |
text = err })
|
|
35 |
in_error = false
|
|
36 |
end
|
|
37 |
|
|
38 |
function mkspawn(p)
|
|
39 |
return function () awful.util.spawn(p) end
|
|
40 |
end
|
|
41 |
|
|
42 |
function setxkbmap(kb)
|
|
43 |
XKBDIR="$HOME/.xkb"
|
|
44 |
-- Strange bug on xkbcomp: pushing directly the output to the display
|
|
45 |
-- lead to an error; We need to convert it first to .xkb and then feed
|
|
46 |
-- xkbcomp again for setting the x display
|
|
47 |
p = 'setxkbmap "' .. kb .. " -print | xkbcomp -xkb -a -I" .. XKBDIR .. " - - | kxbcomp - $DISPLAY"
|
|
48 |
awful.util.spawn_with_shell(p)
|
|
49 |
end
|
|
50 |
|
|
51 |
function kill_all(rule)
|
|
52 |
for c in awful.client.iterate(rule) do
|
|
53 |
c:kill()
|
|
54 |
end
|
|
55 |
end
|
|
56 |
|
|
57 |
function quit()
|
|
58 |
kill_all(awful.rules.any)
|
|
59 |
awesome.quit()
|
|
60 |
end
|
|
61 |
|
|
62 |
function show_clients()
|
|
63 |
if instance then
|
|
64 |
instance:hide()
|
|
65 |
instance = nil
|
|
66 |
else
|
|
67 |
instance = awful.menu.clients({width=250})
|
|
68 |
end
|
|
69 |
end
|
|
70 |
|
|
71 |
local function widgets_cpu()
|
|
72 |
local w = awful.widget.graph()
|
|
73 |
-- Graph properties
|
|
74 |
w:set_width(30)
|
|
75 |
w:set_background_color("#729fcf")
|
|
76 |
w:set_gradient_colors({ "#729fcf", "LightBlue", "white" })
|
|
77 |
-- Register widget
|
|
78 |
vicious.register(w, vicious.widgets.cpu, "$1", 1)
|
|
79 |
return w
|
|
80 |
end
|
|
81 |
|
|
82 |
local function widgets_mdp()
|
|
83 |
-- Initialize widget
|
|
84 |
local w = capi.widget({ type = "textbox" })
|
|
85 |
-- Register widget
|
|
86 |
vicious.register(w, vicious.widgets.mpd,
|
|
87 |
function (widget, args)
|
|
88 |
if args["{state}"] == "Stop" then
|
|
89 |
return " - "
|
|
90 |
else
|
|
91 |
return args["{Artist}"]..' - '.. args["{Title}"]
|
|
92 |
end
|
|
93 |
end, 10)
|
|
94 |
return w
|
|
95 |
end
|
|
96 |
|
|
97 |
local function widgets_mem(monitor)
|
|
98 |
-- Initialize widget
|
|
99 |
local w = awful.widget.progressbar()
|
|
100 |
-- Progressbar properties
|
|
101 |
w:set_width(10)
|
|
102 |
w:set_vertical(true)
|
|
103 |
w:set_background_color("#729fcf")
|
|
104 |
w:set_gradient_colors({ "#729fcf", "LightBlue", "white" })
|
|
105 |
-- Register widget
|
|
106 |
vicious.register(w, vicious.widgets.mem, "$1", 5)
|
|
107 |
return w
|
|
108 |
end
|
|
109 |
|
|
110 |
local function widgets_net(device)
|
|
111 |
local w = capi.widget({ type = "textbox"})
|
|
112 |
-- w:set_vertical(true)
|
|
113 |
w.width = 150
|
|
114 |
w.align = 'center'
|
|
115 |
vicious.register(w, wicked.widgets.net,
|
|
116 |
'${' .. device .. ' up} / ${' .. device .. ' down}',
|
|
117 |
1)
|
|
118 |
return w
|
|
119 |
end
|
|
120 |
|
|
121 |
local function widgets_mode()
|
|
122 |
local w = capi.widget({ type = "textbox"})
|
|
123 |
widgets.mode_widget = w
|
|
124 |
return w
|
|
125 |
end
|
|
126 |
|
|
127 |
local function widgets_keyboard()
|
|
128 |
local w = capi.widget({ type = "textbox"})
|
|
129 |
widgets.keyboard_widget = w
|
|
130 |
return w
|
|
131 |
end
|
|
132 |
|
|
133 |
local function widgets_decorated(w, onclick)
|
|
134 |
local wg = w
|
|
135 |
if w.widget then
|
|
136 |
wg = w.widget
|
|
137 |
end
|
|
138 |
wg:buttons(awful.util.table.join(
|
|
139 |
awful.button({}, 1, onclick)))
|
|
140 |
return w
|
|
141 |
end
|
|
142 |
|
|
143 |
widgets = {
|
|
144 |
cpu = widgets_cpu,
|
|
145 |
mem = widgets_mem,
|
|
146 |
net = widgets_net,
|
|
147 |
mdp = widgets_mdp,
|
|
148 |
mode = widgets_mode,
|
|
149 |
keyboard = widgets_keyboard,
|
|
150 |
decorated = widgets_decorated,
|
|
151 |
}
|
|
152 |
|
|
153 |
function make_key(k, n, f)
|
|
154 |
return { key = k, name = n, func = f}
|
|
155 |
end
|
|
156 |
|
|
157 |
function show_kt(keytable, title)
|
|
158 |
-- todo: replace with a menu ?
|
|
159 |
text = ""
|
|
160 |
for _, k in ipairs(keytable) do
|
|
161 |
text = text .. "\'" .. k.key .. "\'\t" .. k.name .. "\n"
|
|
162 |
end
|
|
163 |
naughty.notify({text = text,
|
|
164 |
title = title,
|
|
165 |
position = "top_left",
|
|
166 |
})
|
|
167 |
end
|
|
168 |
|
|
169 |
local keynames = {
|
|
170 |
[" "] = "space",
|
|
171 |
["\t"] = "tab",
|
|
172 |
}
|
|
173 |
|
|
174 |
local function translate_key(mod, key)
|
|
175 |
local skey = ""
|
|
176 |
for m,v in pairs(mod) do
|
|
177 |
if v then
|
|
178 |
skey = skey .. v .. "+"
|
|
179 |
end
|
|
180 |
end
|
|
181 |
skey = skey .. (keynames[key] or key)
|
|
182 |
return skey
|
|
183 |
end
|
|
184 |
|
|
185 |
local function kt_handler(keytable, mod, key, event)
|
|
186 |
if event == "release" then
|
|
187 |
return true
|
|
188 |
end
|
|
189 |
local theme = beautiful.get()
|
|
190 |
widgets.mode_widget.bg = theme.bg_focus
|
|
191 |
if key == "Escape" then
|
|
192 |
return false
|
|
193 |
end
|
|
194 |
local skey = capi.string.lower(translate_key(mod, key))
|
|
195 |
if skey == "control+h" or skey == "shift+?" then
|
|
196 |
show_kt(keytable, "Current binding")
|
|
197 |
return true
|
|
198 |
end
|
|
199 |
for _,k in ipairs(keytable) do
|
|
200 |
if skey == capi.string.lower(k.key) then
|
|
201 |
return k.func(c)
|
|
202 |
end
|
|
203 |
end
|
|
204 |
-- notify_error("Nothing for " .. skey)
|
|
205 |
widgets.mode_widget.bg = theme.bg_urgent
|
|
206 |
return true
|
|
207 |
end
|
|
208 |
|
|
209 |
local function stop_kt()
|
|
210 |
capi.keygrabber.stop()
|
|
211 |
widgets.mode_widget.visible = false
|
|
212 |
end
|
|
213 |
|
|
214 |
function mkinteractive(f)
|
|
215 |
return function (c)
|
|
216 |
stop_kt()
|
|
217 |
return f(c)
|
|
218 |
end
|
|
219 |
end
|
|
220 |
|
|
221 |
|
|
222 |
-- local is_in_run_kt = false
|
|
223 |
function run_kt(c, keytable, title)
|
|
224 |
widgets.mode_widget.text = "Mode: " .. title
|
|
225 |
widgets.mode_widget.visible = true
|
|
226 |
widgets.mode_widget.bg = "LightBlue"
|
|
227 |
widgets.mode_widget:buttons(
|
|
228 |
awful.util.table.join(
|
|
229 |
awful.button({}, 1, function () show_kt(keytable, "Binding") end),
|
|
230 |
awful.button({}, 3, stop_kt)))
|
|
231 |
capi.keygrabber.run(function (mod, key, event)
|
|
232 |
if not kt_handler(keytable, mod, key, event) then
|
|
233 |
stop_kt()
|
|
234 |
return false
|
|
235 |
end
|
|
236 |
return true
|
|
237 |
end)
|
|
238 |
end
|
|
239 |
|
|
240 |
function make_kt(keytable, title)
|
|
241 |
return function (c)
|
|
242 |
-- if is_in_run_kt then
|
|
243 |
-- -- notify_error("Already in run_kt:\n" .. debug.traceback())
|
|
244 |
-- is_in_run_kt = false -- reset
|
|
245 |
-- return false
|
|
246 |
-- end
|
|
247 |
return run_kt(c, keytable, title)
|
|
248 |
end
|
|
249 |
end
|
|
250 |
|
|
251 |
function make_focus_bydirection(direction)
|
|
252 |
return function ()
|
|
253 |
awful.client.focus.bydirection(direction)
|
|
254 |
if capi.client.focus then capi.client.focus:raise() end
|
|
255 |
return true
|
|
256 |
end
|
|
257 |
end
|
|
258 |
|
|
259 |
function make_globalkeys(modifiers, keytable)
|
|
260 |
local t = {}
|
|
261 |
for _,k in ipairs(keytable) do
|
|
262 |
t = awful.util.table.join(t, awful.key(modifiers, k.key, k.func))
|
|
263 |
end
|
|
264 |
return t
|
|
265 |
end
|
|
266 |
|