Migrate awesome to the new stuff.
[~madcoder/dotfiles.git] / config / awesome / rc.lua
1 -- awesome 3 configuration file
2
3 -- Include awesome library, with lots of useful function!
4 require("awful")
5 require("eminent")
6 require("wicked")
7 require("beautiful")
8
9 terminal = "x-terminal-emulator"
10 lock     = 'xscreensaver-command -lock'
11 beautiful.init(awful.util.getdir("config").."/theme")
12
13 -- {{{ Modkeys
14 modkey = "Mod4"
15 shift = "Shift"
16 alt = "Mod1"
17 control = "Control"
18
19 k_n  = {}
20 k_m  = {modkey}
21 k_ms = {modkey, shift}
22 k_ma = {modkey, alt}
23 k_mc = {modkey, control}
24 k_a  = {alt}
25 k_ac = {alt, control}
26 k_c  = {control}
27 k_cs = {control, shift}
28 k_s  = {shift}
29
30 -- }}}
31
32 -- {{{ Markup helper functions
33 -- Inline markup is a tad ugly, so use these functions
34 -- to dynamically create markup.
35 function fg(color, text)
36     return '<span color="'..color..'">'..text..'</span>'
37 end
38
39 function heading(text)
40     return fg(beautiful.fg_focus, text)
41 end
42
43 -- }}}
44 -- {{{ Functions
45 -- Toggle whether we're viewing a tag
46 function tag_toggleview(tag)
47     tag:view(not tag:isselected())
48 end
49
50 -- Get the screen number we're on
51 function getscreen()
52     local sel = client.focus
53     return (sel and sel.screen) or mouse.screen
54 end
55
56 -- Move current client to a specific screen
57 function client_movetoscreen(i)
58     client.focus.screen = i
59 end
60
61 -- }}}
62 -- {{{ Set tag names
63
64 for s = 1, screen.count() do
65     eminent.newtag(s, 5)
66     for i = 1, 10 do
67         eminent.tag.name(i, s, 'work-'..i)
68     end
69 end
70
71 -- }}}
72 -- {{{ Taglist
73
74 maintaglist = {}
75 maintaglist.buttons = awful.util.table.join(
76     awful.button(k_n, 1, awful.tag.viewonly),
77     awful.button(k_s, 1, awful.client.toggletag)
78 )
79
80 -- }}}
81 -- {{{ Widgets
82
83 -- {{{ Load Averages Widget
84
85 loadwidget = widget({
86     type = 'textbox',
87     name = 'gpuwidget',
88     align = 'right'
89 })
90
91 wicked.register(loadwidget, 'function', function (widget, args)
92     -- Use /proc/loadavg to get the average system load on 1, 5 and 15 minute intervals
93     local f = io.open('/proc/loadavg')
94     local n = f:read()
95     f:close()
96
97     -- Find the third space
98     local pos = n:find(' ', n:find(' ', n:find(' ')+1)+1)
99
100     return heading('Load')..': '..n:sub(1,pos-1)
101
102 end, 2)
103
104 -- }}}
105 -- {{{ CPU Usage Widget
106
107 cputextwidget = widget({
108     type = 'textbox',
109     name = 'cputextwidget',
110     align = 'right'
111 })
112
113 cputextwidget.text = heading('CPU')..': 00% '
114 wicked.register(cputextwidget, 'cpu', function (widget, args)
115     local r = tonumber(args[1])
116     local percent = args[1]..'%'
117     if r < 10 then
118         percent = '0'..percent
119     end
120     if r < 25 then
121         percent = fg('green', percent)
122     elseif r < 50 then
123         percent = fg('yellow', percent)
124     elseif r < 75 then
125         percent = fg('orange', percent)
126     else
127         percent = fg('red', percent)
128     end
129     return heading('CPU')..': '..percent..' '
130 end, 2)
131
132 -- }}}
133 -- {{{ CPU Graph Widget
134
135 cpugraphwidget = widget({
136     type = 'graph',
137     name = 'cpugraphwidget',
138     align = 'right'
139 })
140
141 cpugraphwidget.height = 0.85
142 cpugraphwidget.width = 45
143 cpugraphwidget.bg = '#333333'
144 cpugraphwidget.border_color = '#0a0a0a'
145 cpugraphwidget.grow = 'right'
146
147 cpugraphwidget:plot_properties_set('cpu', {
148     fg = '#AEC6D8',
149     fg_center = '#285577',
150     fg_end = '#285577',
151     vertical_gradient = false
152 })
153
154 wicked.register(cpugraphwidget, 'cpu', '$1', 2, 'cpu')
155
156 -- }}}
157 -- {{{ Memory Usage Widget
158
159 memtextwidget = widget({
160     type = 'textbox',
161     name = 'memtextwidget',
162     align = 'right'
163 })
164
165 memtextwidget.text = heading('MEM')..': '
166 wicked.register(memtextwidget, 'mem', function (widget, args)
167     -- Add extra preceding zeroes when needed
168     local r = tonumber(args[1])
169     local percent = args[1]..'%'
170     if r < 10 then
171         percent = '0'..percent
172     end
173     if r < 50 then
174         percent = fg('green', percent)
175     elseif r < 80 then
176         percent = fg('orange', percent)
177     else
178         percent = fg('red', percent)
179     end
180     return heading('MEM')..': '..percent..' '..args[2]..'M'
181 end, 2)
182
183 -- }}}
184 -- {{{ Battery widget
185 --[[
186 batterywidget = widget({
187     type = 'textbox',
188     name = 'batterywidget',
189     align = 'right'
190 })
191
192 function batterywidget_update()
193     local v = io.popen("powersave -b|sed -ne 's/.*Remaining percent: \\(.*\\)/\\1/p'"):read()
194     local r = tonumber(v)
195
196     percent = v
197     if r < 10 then
198         percent = fg('red', percent)
199     elseif r < 25 then
200         percent = fg('orange', percent)
201     else
202         percent = fg('green', percent)
203     end
204     batterywidget.text = heading('BAT')..': '..percent
205 end
206 batterywidget_update()
207 awful.hooks.timer.register(30, batterywidget_update)
208 --]]
209 -- }}}
210 -- {{{ spacers
211
212 rspacer = widget({ type = 'textbox', name = 'rspacer', align = 'right' })
213 rspacer.text = " │ "
214
215 -- }}}
216 -- {{{ Clock
217 clockwidget = widget({ type = "textbox", name = "clockwidget", align = "right" })
218 clock_update = function()
219     clockwidget.text = fg("#dddddd", os.date("%a %d %b - %H:%M"))
220 end
221 clock_update()
222 awful.hooks.timer.register(10, clock_update)
223
224 -- }}}
225
226 mymenubox = widget{ type = "textbox", name = "mytextbox", align = "left" }
227 -- mysystray = widget{ type = "systray", name = "mysystray", align = "right" }
228
229 -- {{{ Statusbar
230
231 mainstatusbar = {}
232
233 for s = 1, screen.count() do
234     mainstatusbar[s] = wibox{
235         position = "top",
236         height = 18,
237         name = "mainstatusbar" .. s,
238     }
239
240     mainstatusbar[s].widgets = {
241         awful.widget.taglist.new(s, awful.widget.taglist.label.noempty, maintaglist.buttons),
242         maintaglist,
243         mymenubox,
244
245         rspacer, loadwidget,
246         rspacer, cputextwidget, cpugraphwidget,
247         rspacer, memtextwidget,
248         rspacer, clockwidget,
249         s == 1 and rspacer or nil,
250         s == 1 and mysystray or nil,
251     }
252     mainstatusbar[s].screen = s
253 end
254
255 -- }}}
256 -- }}}
257
258 -- {{{ Keys
259 ---- {{{ Global keys
260
261 local hist = os.getenv("HOME") .. "/.cache/awesome/history"
262 globalkeys = awful.util.table.join(
263     -- Mod+{A/S}: Switch to prev/next tag
264     awful.key(k_m, "Left",  eminent.tag.prev),
265     awful.key(k_m, "Right", eminent.tag.next),
266
267     -- Mod+Shift+{A/S}: Move window to Prev/Next tag
268     awful.key(k_ms, "Left", function()
269         awful.client.movetotag(eminent.tag.getprev())
270         eminent.tag.prev()
271     end),
272     awful.key(k_ms, "Right", function()
273         awful.client.movetotag(eminent.tag.getnext())
274         eminent.tag.next()
275     end),
276
277     -- Mod+Shift_{E/D}: move window to next/prev screen
278     awful.key(k_mc, "Right", function()
279        local s = getscreen() + 1
280        while s > screen.count() do
281            s = s-screen.count()
282        end
283        client_movetoscreen(s)
284     end),
285     awful.key(k_mc, "Left", function()
286        local s = getscreen() - 1
287        while s < 1 do
288            s = s+screen.count()
289        end
290        client_movetoscreen(s)
291     end),
292
293
294     -- Focus Prev/Next window
295     awful.key(k_m, "j",
296         function ()
297             awful.client.focus.byidx(1)
298             if client.focus then client.focus:raise() end
299         end),
300     awful.key(k_m, "k",
301         function ()
302             awful.client.focus.byidx(-1)
303             if client.focus then client.focus:raise() end
304         end),
305
306     -- Swap window with the Prev/Next one
307     awful.key(k_ms, "j", function () awful.client.swap.byidx(1) end),
308     awful.key(k_ms, "k", function () awful.client.swap.byidx(-1) end),
309
310     -- Mod+{E/D}: Switch to next/previous screen
311     awful.key(k_m, "Tab",  function () awful.screen.focus(1) end),
312     awful.key(k_ms, "Tab", function () awful.screen.focus(-1) end),
313
314     -- Mod+Enter: Launch a new terminal
315     awful.key(k_m,  "e",      function() awful.util.spawn("firefox") end),
316     awful.key(k_m,  "Return", function() awful.util.spawn(terminal) end),
317     awful.key(k_ac, "r", awesome.restart),
318     awful.key(k_m, "F12", function() awful.util.spawn(lock) end),
319     awful.key({}, "#148", function() awful.util.spawn("kcalc") end),
320
321     -- Layout manipulation
322     awful.key(k_m,  "l", function () awful.tag.incmwfact(0.05) end),
323     awful.key(k_m,  "h", function () awful.tag.incmwfact(-0.05) end),
324     awful.key(k_ms, "h", function () awful.tag.incnmaster(1) end),
325     awful.key(k_ms, "l", function () awful.tag.incnmaster(-1) end),
326     awful.key(k_mc, "h", function () awful.tag.incncol(1) end),
327     awful.key(k_mc, "l", function () awful.tag.incncol(-1) end),
328
329     -- Menu
330     awful.key(k_m, "r",
331         function ()
332             awful.prompt.run({ prompt = "Run: " },
333                              mymenubox,
334                              awful.util.spawn,
335                              awful.completion.bash,
336                              awful.util.getdir("cache").."/commands")
337         end),
338     awful.key(k_m, "F4",
339         function ()
340             awful.prompt.run({ prompt = "Run Lua code: " },
341                              mymenubox,
342                              awful.util.eval,
343                              awful.prompt.bash,
344                              awful.util.getdir("cache").."/lua_commands")
345     end),
346
347     awful.key({}, "#192", function() eminent.tag.goto(1, nil, true) end),
348     awful.key({}, "#193", function() eminent.tag.goto(2, nil, true) end),
349     awful.key({}, "#194", function() eminent.tag.goto(3, nil, true) end),
350     awful.key({}, "#195", function() eminent.tag.goto(4, nil, true) end),
351     awful.key({}, "#196", function() eminent.tag.goto(5, nil, true) end)
352 )
353
354 -- Mod+#: Switch to tag
355 -- Mod+Shift+#: Toggle tag display
356 -- Mod+Control+#: Move client to tag
357 -- Mod+Alt+#: Toggle client on tag
358
359 for i = 1, 10 do
360     globalkeys = awful.util.table.join(
361         globalkeys,
362         awful.key(k_m, i % 10,
363             function()
364                 eminent.tag.goto(i, nil, true)
365             end),
366
367         awful.key(k_ms, i % 10,
368             function ()
369                 local t = eminent.tag.getn(i, nil, true)
370                 if t ~= nil then t.selected = not t.selected end
371             end),
372         awful.key(k_mc, i % 10,
373             function ()
374                 local t = eminent.tag.getn(i, nil, true)
375                 if t ~= nil then awful.client.movetotag(t) end
376             end)
377     )
378 end
379
380 ---- }}}
381 ---- {{{ Client hotkeys
382
383 clientkeys = awful.util.table.join(
384     awful.key(k_m, "i", function (c)
385         if mymenubox.text then
386             mymenubox.text = ""
387         else
388             mymenubox.text = "Class: " .. c.class .. " Instance: ".. c.instance
389         end
390     end),
391
392     -- Client manipulation
393     awful.key(k_m, "c", function (c) c:kill() end),
394     awful.key(k_m, "o", awful.client.floating.toggle),
395     awful.key(k_m, "t", awful.client.togglemarked),
396     awful.key(k_m, "F11", function (c) c.fullscreen = not c.fullscreen end)
397 )
398
399 ---- }}}
400
401 root.keys(globalkeys)
402 -- }}}
403 -- {{{ Hooks
404
405 awful.hooks.focus.register(function (c)
406     if not awful.client.ismarked(c) then
407         c.border_color = beautiful.border_focus
408     end
409 end)
410
411 awful.hooks.unfocus.register(function (c)
412     if not awful.client.ismarked(c) then
413         c.border_color = beautiful.border_normal
414     end
415 end)
416
417 awful.hooks.marked.register(function (c)
418     c.border_color = beautiful.border_marked
419 end)
420
421 awful.hooks.unmarked.register(function (c)
422     c.border_color = beautiful.border_focus
423 end)
424
425 -- Hook function to execute when the mouse enters a client.
426 awful.hooks.mouse_enter.register(function (c)
427     -- Sloppy focus
428     client.focus = c
429 end)
430
431 awful.hooks.manage.register(function (c, startup)
432     if not startup and awful.client.focus.filter(c) then
433         c.screen = mouse.screen
434     end
435
436     -- Add mouse bindings
437     c:buttons(awful.util.table.join(
438         awful.button({ }, 1, function (c) client.focus = c; c:raise() end),
439         awful.button(k_a, 1, awful.mouse.client.move),
440         awful.button(k_a, 3, awful.mouse.client.resize)
441     ))
442
443     -- Create border
444     c.border_width = beautiful.border_width
445     c.border_color = beautiful.border_normal
446
447     -- Make certain windows floating
448     local class = c.class:lower()
449     if class:find('pinentry')
450     or class:find('kcalc')
451     or class:find('gajim')
452     then
453         c.floating = true
454     end
455
456     -- Focus new clients
457     client.focus = c
458     c:keys(clientkeys)
459     c.size_hints_honor = false
460 end)
461
462 -- Hook function to execute when arranging the screen
463 -- (tag switch, new client, etc)
464 awful.hooks.arrange.register(function (screen)
465     local sel = client.focus
466
467     if not sel then
468         sel = awful.client.focus.history.get(screen, 0)
469         if not sel then return end
470         client.focus = sel
471     end
472
473     local o = mouse.object_under_pointer()
474     if not o or (type(o) == "client" and o ~= sel) then
475         local g = sel:geometry()
476
477         mouse.coords { x = g.x + 5, y = g.y + 5 }
478     end
479 end)
480
481 -- }}}
482
483 awful.util.spawn("xkbcomp -w 0 -R/usr/share/X11/xkb /home/madcoder/.Xkeyboard :0")