diff --git a/lib/naughty.lua.in b/lib/naughty.lua.in index 1b9afce3..5aa8fd84 100644 --- a/lib/naughty.lua.in +++ b/lib/naughty.lua.in @@ -16,6 +16,8 @@ local button = button local capi = { screen = screen } local bt = require("beautiful") local screen = screen +local awful = awful +local dbus = dbus --- Notification library module("naughty") @@ -62,6 +64,10 @@ config.icon_size = 16 config.border_width = 1 config.hover_timeout = nil +-- Counter for the notifications +-- Required for later access via DBUS +local counter = 1 + --- Index of notifications. See config table for valid 'position' values. -- Each element is a table consisting of: -- @field box Wibox object containing the popup @@ -149,6 +155,22 @@ function destroy(notification) end end +--- Get notification by ID +-- @param id ID of the notification +-- @return notification object if it was found, nil otherwise +local function getById(id) + -- iterate the notifications to get the notfications with the correct ID + for s = 1, screen.count() do + for p,pos in pairs(notifications[s]) do + for i,notification in pairs(notifications[s][p]) do + if notification.id == id then + return notification + end + end + end + end +end + --- Create notification. args is a dictionary of optional arguments. For more information and defaults see respective fields in config table. -- @param text Text of the notification -- @param timeout Time in seconds after which popup expires @@ -162,6 +184,7 @@ end -- @param ontop Target screen for the notification -- @param run Function to run on left click -- @param width The popup width +-- @param replaces_id Replace the notification with the given ID -- @usage naughty.notify({ title = 'Achtung!', text = 'You\'re idling', timeout = 0 }) -- @return The notification object function notify(args) @@ -181,6 +204,27 @@ function notify(args) local bg = args.bg or config.bg or beautiful.bg_normal or '#535d6c' local border_color = config.border_color or beautiful.bg_focus or '#535d6c' local notification = {} + + -- replace notification if needed + if args.replaces_id then + obj = getById(args.replaces_id) + if obj then + -- destroy this and ... + destroy(obj) + end + -- ... may use its ID + if args.replaces_id < counter then + notification.id = args.replaces_id + else + counter = counter + 1 + notification.id = counter + end + else + -- get a brand new ID + counter = counter + 1 + notification.id = counter + end + notification.position = args.position or config.position notification.idx = #notifications[screen][notification.position] + 1 @@ -252,4 +296,78 @@ function notify(args) -- return the notification return notification end + +-- DBUS/Notification support + +-- Notify +awful.hooks.dbus.register("org.freedesktop.Notifications", function (data, arg1, replaces_id, icon, title, text) +args = {} +if data.member == "Notify" then + if text ~= "" then + args.text = text + if title ~= "" then + args.title = title + end + else + if title ~= "" then + args.text = title + else + return nil + end + end + if icon ~= "" then + args.icon = icon + end + if replaces_id and replaces_id ~= "" and replaces_id ~= 0 then + args.replaces_id = replaces_id + end + local id = notify(args).id + return "i", id +elseif data.member == "CloseNotification" then + local obj = getById(arg1) + if obj then + destroy(obj) + end +elseif data.member == "GetServerInfo" or data.member == "GetServerInformation" then + -- name of notification app, name of project, version of notification app, project version + return "s", "naughty", "s", "awesome", "s", "1337", "s", "1337" +end +end) + +awful.hooks.dbus.register("org.freedesktop.DBus.Introspectable", +function (data, text) +if data.member == "Introspect" then + local xml = [=[ + + + + + + + + + + + + + + + + + + + + + + +]=] + return "s", xml +end +end) + +-- listen for dbus notification requests +dbus.request_name("org.freedesktop.Notifications") + -- vim: filetype=lua:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=80