One of the things I was missing in my favourite windowmanager awesome was a calendar widget. So I spent some minutes and coded it. Moving the mouse over the time widget will show a naughty popup with the current month, use your mouse buttons (and the shift key) to scroll trough the months. The only annoying thing was to figure out how to change the text of an existing notification: notification.box.widgets[2].text = "new test" is neither easy to figure out nor to use.

But here's the code for your rc.lua - in case you want to have a license for it - the code is published as public domain or under the ISC license, what ever you prefer.

Update: With thanks to a hint from madduck, the naughty popup is now aware of the screen your mouse is pointing to.

function displayMonth(month,year,weekStart)
    local t,wkSt=os.time{year=year, month=month+1, day=0},weekStart or 1
    local d=os.date("*t",t)
    local mthDays,stDay=d.day,(d.wday-d.day-wkSt+1)%7

    local lines = {}

    for x=0,6 do
        lines[x+1] = os.date("%a ",os.time{year=2006,month=1,day=x+wkSt})
    end
    lines[8] = "    "

    local writeLine = 1
    while writeLine < (stDay + 1) do
        lines[writeLine] = lines[writeLine] .. "   "
        writeLine = writeLine + 1
    end

    for x=1,mthDays do
        if writeLine == 8 then
            writeLine = 1
        end
        if writeLine == 1 or x == 1 then
            lines[8] = lines[8] .. os.date(" %V",os.time{year=year,month=month,day=x})
        end
        if (#(tostring(x)) == 1) then
            x = " " .. x
        end
        lines[writeLine] = lines[writeLine] .. " " .. x
        writeLine = writeLine + 1
    end
    local header = os.date("%B %Y\n",os.time{year=year,month=month,day=1})
    header = string.rep(" ", math.floor((#(lines[1]) - #header) / 2 )) .. header

    return header .. table.concat(lines, '\n')
end

local calendar = {}
function switchNaughtyMonth(switchMonths)
    if (#calendar < 3) then return end
    local swMonths = switchMonths or 1
    calendar[1] = calendar[1] + swMonths
    calendar[3].box.widgets[2].text = displayMonth(calendar[1], calendar[2], 2)
end

mytextbox.mouse_enter = function ()
    local month, year = os.date('%m'), os.date('%Y')
    calendar = { month, year, 
                naughty.notify({
                    text = displayMonth(month, year, 2),
                    timeout = 0, hover_timeout = 0.5,
                    width = 200, screen = mouse.screen
                })
               }
end 
mytextbox.mouse_leave = function () naughty.destroy(calendar[3]) end

mytextbox:buttons({
    button({ }, 1, function()
        switchNaughtyMonth(-1)
    end),
    button({ }, 3, function()
        switchNaughtyMonth(1)
    end),
    button({ }, 4, function()
        switchNaughtyMonth(-1)
    end),
    button({ }, 5, function()
        switchNaughtyMonth(1)
    end),
    button({ 'Shift' }, 1, function()
        switchNaughtyMonth(-12)
    end),
    button({ 'Shift' }, 3, function()
        switchNaughtyMonth(12)
    end),
    button({ 'Shift' }, 4, function()
        switchNaughtyMonth(-12)
    end),
    button({ 'Shift' }, 5, function()
        switchNaughtyMonth(12)
    end)
})
comment 1

Nice! Don't hesitate to share your work with the community by posting it on the awesome wiki. :)

Comment by dleone
comment 2
show screenshot plz )
Comment by Anonymous
Monospace
I had a problem with the formatting of the calendar (columns were of different width), solved it using monospace font.
Comment by rafal
week start day

My 2c: the week number should be calculated with %U when weekStart is 1 (Sunday) and with %V otherwise.

Thanks!

Comment by ZungBang
monospace text

If you don't use monospace fonts by default as I do, you could use the following line in naughty.notify():

text = string.format('<span font_desc="%s">%s</span>', "monospace", displayMonth(month, year, 2)),

Comment by Bernd Zeimetz
Error then delay

So, I'm having a slight but not serious, more annoying, problem trying to run this. At first the mytextbox time and date doesn't show up, it does eventually though. When I drop to tty1 to see whats wrong, I get this error:

luaA_dofunction:264: error running function: /home/rune/.config/awesome/rc.lua:478: attempt to index global 'mytextbox' (a nil value)

any clues or suggestions on what the problem might be. it looks like its leading me to the awful.hooks.mouse_enter.register hook/function, and its having problems figuring out mytextbox? It's very weird, and like I said, after a minute or two the textbox eventually shows up and functions correctly.

Comment by Nythain
comment 8

Nice work but shouldn`t it be

calendar2.addCalendarToWidget(mytextclock, "%s")

instead of

calendar2.addCalendarToWidget(datewidget, "%s")

Comment by VicRem