feat(ipc): New message type "action:"
Adds a new message type, prefixed "action:" that will perform the same task as mouse actions. This could be used to control menu modules: echo action:menu-open-1 > /tmp/lemonbuddy_mqueue.<pid> echo action:menu-close > /tmp/lemonbuddy_mqueue.<pid> Ref #84
This commit is contained in:
parent
0a1e9c86c4
commit
2fd88c4f60
@ -42,6 +42,7 @@ class controller {
|
||||
|
||||
void bootstrap_modules();
|
||||
|
||||
void on_ipc_action(const ipc_action& message);
|
||||
void on_mouse_event(string input);
|
||||
void on_unrecognized_action(string input);
|
||||
void on_update();
|
||||
|
@ -16,6 +16,10 @@ struct ipc_hook {
|
||||
static constexpr auto prefix{"hook:"};
|
||||
string payload;
|
||||
};
|
||||
struct ipc_action {
|
||||
static constexpr auto prefix{"action:"};
|
||||
string payload;
|
||||
};
|
||||
|
||||
/**
|
||||
* Component used for inter-process communication.
|
||||
@ -31,18 +35,21 @@ class ipc {
|
||||
|
||||
void attach_callback(callback<const ipc_command&>&& cb);
|
||||
void attach_callback(callback<const ipc_hook&>&& cb);
|
||||
void attach_callback(callback<const ipc_action&>&& cb);
|
||||
void receive_messages();
|
||||
|
||||
protected:
|
||||
void parse(const string& payload) const;
|
||||
void delegate(const ipc_command& msg) const;
|
||||
void delegate(const ipc_hook& msg) const;
|
||||
void delegate(const ipc_action& msg) const;
|
||||
|
||||
private:
|
||||
const logger& m_log;
|
||||
|
||||
vector<callback<const ipc_command&>> m_command_callbacks;
|
||||
vector<callback<const ipc_hook&>> m_hook_callbacks;
|
||||
vector<callback<const ipc_action&>> m_action_callbacks;
|
||||
|
||||
stateflag m_running{false};
|
||||
|
||||
|
@ -107,8 +107,9 @@ void controller::bootstrap(bool writeback, bool dump_wmname) {
|
||||
if (m_conf.get<bool>(m_conf.bar_section(), "enable-ipc", false)) {
|
||||
m_log.trace("controller: Create IPC handler");
|
||||
m_ipc = configure_ipc().create<decltype(m_ipc)>();
|
||||
m_ipc->attach_callback(bind(&controller::on_ipc_action, this, placeholders::_1));
|
||||
} else {
|
||||
m_log.warn("Inter-process communication support disabled");
|
||||
m_log.info("Inter-process messaging disabled");
|
||||
}
|
||||
|
||||
// Listen for events on the root window to be able to
|
||||
@ -389,7 +390,7 @@ void controller::bootstrap_modules() {
|
||||
module.reset(new menu_module(bar, m_log, m_conf, module_name));
|
||||
else if (type == "custom/ipc") {
|
||||
if (!m_ipc)
|
||||
throw application_error("Inter-process communication support needs to be enabled");
|
||||
throw application_error("Inter-process messaging needs to be enabled");
|
||||
module.reset(new ipc_module(bar, m_log, m_conf, module_name));
|
||||
m_ipc->attach_callback(
|
||||
bind(&ipc_module::on_message, dynamic_cast<ipc_module*>(module.get()), placeholders::_1));
|
||||
@ -416,6 +417,24 @@ void controller::bootstrap_modules() {
|
||||
throw application_error("No modules created");
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback for received ipc actions
|
||||
*/
|
||||
void controller::on_ipc_action(const ipc_action& message) {
|
||||
string action = message.payload.substr(strlen(ipc_action::prefix));
|
||||
|
||||
if (action.empty()) {
|
||||
m_log.err("Cannot enqueue empty IPC action");
|
||||
return;
|
||||
}
|
||||
|
||||
eventloop::entry_t evt{static_cast<int>(event_type::INPUT)};
|
||||
snprintf(evt.data, sizeof(evt.data), "%s", action.c_str());
|
||||
|
||||
m_log.info("Enqueuing IPC action: %s", action);
|
||||
m_eventloop->enqueue(evt);
|
||||
}
|
||||
|
||||
/**
|
||||
* Callback for clicked bar actions
|
||||
*/
|
||||
|
@ -41,6 +41,13 @@ void ipc::attach_callback(callback<const ipc_hook&>&& cb) {
|
||||
m_hook_callbacks.emplace_back(cb);
|
||||
}
|
||||
|
||||
/**
|
||||
* Register listener callback for ipc_action messages
|
||||
*/
|
||||
void ipc::attach_callback(callback<const ipc_action&>&& cb) {
|
||||
m_action_callbacks.emplace_back(cb);
|
||||
}
|
||||
|
||||
/**
|
||||
* Start listening for event messages
|
||||
*/
|
||||
@ -71,6 +78,8 @@ void ipc::parse(const string& payload) const {
|
||||
delegate(ipc_command{payload});
|
||||
} else if (payload.find(ipc_hook::prefix) == 0) {
|
||||
delegate(ipc_hook{payload});
|
||||
} else if (payload.find(ipc_action::prefix) == 0) {
|
||||
delegate(ipc_action{payload});
|
||||
} else {
|
||||
m_log.warn("Received unknown ipc message: (payload=%s)", payload);
|
||||
}
|
||||
@ -96,4 +105,14 @@ void ipc::delegate(const ipc_hook& message) const {
|
||||
m_log.warn("Unhandled message (payload=%s)", message.payload);
|
||||
}
|
||||
|
||||
/**
|
||||
* Send ipc message to attached listeners
|
||||
*/
|
||||
void ipc::delegate(const ipc_action& message) const {
|
||||
if (!m_action_callbacks.empty())
|
||||
for (auto&& callback : m_action_callbacks) callback(message);
|
||||
else
|
||||
m_log.warn("Unhandled message (payload=%s)", message.payload);
|
||||
}
|
||||
|
||||
LEMONBUDDY_NS_END
|
||||
|
Loading…
Reference in New Issue
Block a user