feat: args && class id

This commit is contained in:
Alexis 2018-12-18 17:30:54 +01:00
parent 66ad2864c2
commit b554094c7e
29 changed files with 1405 additions and 93 deletions

View File

@ -6,24 +6,24 @@
namespace waybar {
class ALabel : public IModule {
public:
ALabel(const Json::Value&, const std::string format, uint16_t interval = 0);
public:
ALabel(const Json::Value &, const std::string format, uint16_t interval = 0);
virtual ~ALabel() = default;
virtual auto update() -> void;
virtual std::string getIcon(uint16_t, const std::string& alt = "");
virtual operator Gtk::Widget&();
virtual std::string getIcon(uint16_t, const std::string &alt = "");
virtual operator Gtk::Widget &();
protected:
protected:
Gtk::EventBox event_box_;
Gtk::Label label_;
const Json::Value& config_;
const Json::Value &config_;
std::string format_;
std::mutex mutex_;
const std::chrono::seconds interval_;
private:
bool handleToggle(GdkEventButton* const& ev);
bool handleScroll(GdkEventScroll*);
private:
bool handleToggle(GdkEventButton *const &ev);
bool handleScroll(GdkEventScroll *);
bool alt = false;
const std::string default_format_;
};

View File

@ -15,7 +15,7 @@ class Client {
Client(int argc, char *argv[]);
int main(int argc, char *argv[]);
Glib::RefPtr<Gtk::Application> gtk_app;
Gtk::Main gtk_main;
std::string css_file;
std::string config_file;
Glib::RefPtr<Gdk::Display> gdk_display;
@ -27,8 +27,8 @@ class Client {
std::vector<std::unique_ptr<Bar>> bars;
private:
void setupConfigs(const std::string& config, const std::string& style);
void bindInterfaces();
auto setupCss();
const std::string getValidPath(std::vector<std::string> paths);
static void handleGlobal(void *data, struct wl_registry *registry,

View File

@ -23,7 +23,7 @@ namespace fs = std::filesystem;
class Battery : public ALabel {
public:
Battery(const Json::Value&);
Battery(const std::string&, const Json::Value&);
~Battery();
auto update() -> void;
private:

View File

@ -9,7 +9,7 @@ namespace waybar::modules {
class Clock : public ALabel {
public:
Clock(const Json::Value&);
Clock(const std::string&, const Json::Value&);
auto update() -> void;
private:
waybar::util::SleeperThread thread_;

View File

@ -13,7 +13,7 @@ namespace waybar::modules {
class Cpu : public ALabel {
public:
Cpu(const Json::Value&);
Cpu(const std::string&, const Json::Value&);
auto update() -> void;
private:
static inline const std::string data_dir_ = "/proc/stat";

View File

@ -11,7 +11,7 @@ namespace waybar::modules {
class Custom : public ALabel {
public:
Custom(const std::string, const Json::Value&);
Custom(const std::string&, const Json::Value&);
~Custom();
auto update() -> void;
private:

View File

@ -9,7 +9,7 @@ namespace waybar::modules {
class Memory : public ALabel {
public:
Memory(const Json::Value&);
Memory(const std::string&, const Json::Value&);
auto update() -> void;
private:
static inline const std::string data_dir_ = "/proc/meminfo";

View File

@ -15,7 +15,7 @@ namespace waybar::modules {
class Network : public ALabel {
public:
Network(const Json::Value&);
Network(const std::string&, const Json::Value&);
~Network();
auto update() -> void;
private:

View File

@ -10,7 +10,7 @@ namespace waybar::modules {
class Pulseaudio : public ALabel {
public:
Pulseaudio(const Json::Value&);
Pulseaudio(const std::string&, const Json::Value&);
~Pulseaudio();
auto update() -> void;
private:

View File

@ -12,7 +12,7 @@ namespace waybar::modules::SNI {
class Tray : public IModule {
public:
Tray(const Json::Value&);
Tray(const std::string&, const Json::Value&);
auto update() -> void;
operator Gtk::Widget &();
private:

View File

@ -12,7 +12,7 @@ namespace waybar::modules::sway {
class Mode : public ALabel {
public:
Mode(const waybar::Bar&, const Json::Value&);
Mode(const std::string&, const waybar::Bar&, const Json::Value&);
auto update() -> void;
private:
void worker();

View File

@ -13,7 +13,7 @@ namespace waybar::modules::sway {
class Window : public ALabel {
public:
Window(const waybar::Bar&, const Json::Value&);
Window(const std::string&, const waybar::Bar&, const Json::Value&);
auto update() -> void;
private:
void worker();

View File

@ -12,7 +12,7 @@ namespace waybar::modules::sway {
class Workspaces : public IModule {
public:
Workspaces(const waybar::Bar&, const Json::Value&);
Workspaces(const std::string&, const waybar::Bar&, const Json::Value&);
auto update() -> void;
operator Gtk::Widget &();
private:

View File

@ -63,14 +63,14 @@ struct SleeperThread {
{
do_run_ = false;
condvar_.notify_all();
if (thread_.joinable()) {
thread_.detach();
}
}
~SleeperThread()
{
stop();
if (thread_.joinable()) {
thread_.detach();
}
}
private:

1264
include/util/clara.hpp Normal file

File diff suppressed because it is too large Load Diff

View File

@ -9,7 +9,7 @@ project(
],
)
cpp_args = []
cpp_args = ['-DVERSION="@0@"'.format(meson.project_version())]
cpp_link_args = []
if false # libc++

View File

@ -1,8 +1,9 @@
#include "client.hpp"
#include "util/clara.hpp"
#include <iostream>
waybar::Client::Client(int argc, char* argv[])
: gtk_app(Gtk::Application::create(argc, argv, "fr.arouillard.waybar")),
: gtk_main(argc, argv),
gdk_display(Gdk::Display::get_default())
{
if (!gdk_display) {
@ -12,25 +13,6 @@ waybar::Client::Client(int argc, char* argv[])
throw std::runtime_error("Bar need to run under Wayland");
}
wl_display = gdk_wayland_display_get_wl_display(gdk_display->gobj());
config_file = getValidPath({
"$XDG_CONFIG_HOME/waybar/config",
"$HOME/.config/waybar/config",
"$HOME/waybar/config",
"/etc/xdg/waybar/config",
"./resources/config",
});
css_file = getValidPath({
"$XDG_CONFIG_HOME/waybar/style.css",
"$HOME/.config/waybar/style.css",
"$HOME/waybar/style.css",
"/etc/xdg/waybar/style.css",
"./resources/style.css",
});
if (css_file.empty() || config_file.empty()) {
throw std::runtime_error("Missing required resources files");
}
std::cout << "Resources files: " + config_file + ", " + css_file << std::endl;
}
const std::string waybar::Client::getValidPath(std::vector<std::string> paths)
@ -88,6 +70,28 @@ void waybar::Client::handleGlobalRemove(void* data,
}
}
void waybar::Client::setupConfigs(const std::string& config, const std::string& style)
{
config_file = config.empty() ? getValidPath({
"$XDG_CONFIG_HOME/waybar/config",
"$HOME/.config/waybar/config",
"$HOME/waybar/config",
"/etc/xdg/waybar/config",
"./resources/config",
}) : config;
css_file = style.empty() ? getValidPath({
"$XDG_CONFIG_HOME/waybar/style.css",
"$HOME/.config/waybar/style.css",
"$HOME/waybar/style.css",
"/etc/xdg/waybar/style.css",
"./resources/style.css",
}) : style;
if (css_file.empty() || config_file.empty()) {
throw std::runtime_error("Missing required resources files");
}
std::cout << "Resources files: " + config_file + ", " + css_file << std::endl;
}
void waybar::Client::bindInterfaces()
{
registry = wl_display_get_registry(wl_display);
@ -103,11 +107,32 @@ void waybar::Client::bindInterfaces()
wl_display_roundtrip(wl_display);
}
int waybar::Client::main(int /*argc*/, char* /*argv*/[])
int waybar::Client::main(int argc, char* argv[])
{
bool show_help = false;
bool show_version = false;
std::string config;
std::string style;
auto cli = clara::detail::Help(show_help)
| clara::detail::Opt(show_version)["-v"]["--version"]("Show version")
| clara::detail::Opt(config, "config")["-c"]["--config"]("Config path")
| clara::detail::Opt(style, "style")["-s"]["--style"]("Style path");
auto res = cli.parse(clara::detail::Args(argc, argv));
if (!res) {
std::cerr << "Error in command line: " << res.errorMessage() << std::endl;
return 1;
}
if (show_help) {
std::cout << cli << std::endl;
return 0;
}
if (show_version) {
std::cout << "Waybar v" << VERSION << std::endl;
return 0;
}
setupConfigs(config, style);
bindInterfaces();
gtk_app->hold();
gtk_app->run();
gtk_main.run();
bars.clear();
zxdg_output_manager_v1_destroy(xdg_output_manager);
zwlr_layer_shell_v1_destroy(layer_shell);

View File

@ -7,43 +7,45 @@ waybar::Factory::Factory(const Bar& bar, const Json::Value& config)
waybar::IModule* waybar::Factory::makeModule(const std::string &name) const
{
try {
auto ref = name.substr(0, name.find("#"));
auto hash_pos = name.find("#");
auto ref = name.substr(0, hash_pos);
auto id = hash_pos != std::string::npos ? name.substr(hash_pos + 1) : "";
if (ref == "battery") {
return new waybar::modules::Battery(config_[name]);
return new waybar::modules::Battery(id, config_[name]);
}
#ifdef HAVE_SWAY
if (ref == "sway/mode") {
return new waybar::modules::sway::Mode(bar_, config_[name]);
return new waybar::modules::sway::Mode(id, bar_, config_[name]);
}
if (ref == "sway/workspaces") {
return new waybar::modules::sway::Workspaces(bar_, config_[name]);
return new waybar::modules::sway::Workspaces(id, bar_, config_[name]);
}
if (ref == "sway/window") {
return new waybar::modules::sway::Window(bar_, config_[name]);
return new waybar::modules::sway::Window(id, bar_, config_[name]);
}
#endif
if (ref == "memory") {
return new waybar::modules::Memory(config_[name]);
return new waybar::modules::Memory(id, config_[name]);
}
if (ref == "cpu") {
return new waybar::modules::Cpu(config_[name]);
return new waybar::modules::Cpu(id, config_[name]);
}
if (ref == "clock") {
return new waybar::modules::Clock(config_[name]);
return new waybar::modules::Clock(id, config_[name]);
}
#ifdef HAVE_DBUSMENU
if (ref == "tray") {
return new waybar::modules::SNI::Tray(config_[name]);
return new waybar::modules::SNI::Tray(id, config_[name]);
}
#endif
#ifdef HAVE_LIBNL
if (ref == "network") {
return new waybar::modules::Network(config_[name]);
return new waybar::modules::Network(id, config_[name]);
}
#endif
#ifdef HAVE_LIBPULSE
if (ref == "pulseaudio") {
return new waybar::modules::Pulseaudio(config_[name]);
return new waybar::modules::Pulseaudio(id, config_[name]);
}
#endif
if (ref.compare(0, 7, "custom/") == 0 && ref.size() > 7) {

View File

@ -1,8 +1,12 @@
#include "modules/battery.hpp"
waybar::modules::Battery::Battery(const Json::Value& config)
waybar::modules::Battery::Battery(const std::string& id, const Json::Value& config)
: ALabel(config, "{capacity}%", 60)
{
label_.set_name("battery");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
try {
if (config_["bat"].isString()) {
auto dir = data_dir_ / config_["bat"].asString();
@ -131,10 +135,8 @@ auto waybar::modules::Battery::update() -> void
}
if (format.empty()) {
event_box_.hide();
label_.set_name("");
} else {
event_box_.show();
label_.set_name("battery");
label_.set_markup(fmt::format(format, fmt::arg("capacity", capacity),
fmt::arg("icon", getIcon(capacity))));
}

View File

@ -1,9 +1,12 @@
#include "modules/clock.hpp"
waybar::modules::Clock::Clock(const Json::Value& config)
waybar::modules::Clock::Clock(const std::string& id, const Json::Value& config)
: ALabel(config, "{:%H:%M}", 60)
{
label_.set_name("clock");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
thread_ = [this] {
auto now = waybar::chrono::clock::now();
dp.emit();

View File

@ -1,9 +1,12 @@
#include "modules/cpu.hpp"
waybar::modules::Cpu::Cpu(const Json::Value& config)
waybar::modules::Cpu::Cpu(const std::string& id, const Json::Value& config)
: ALabel(config, "{usage}%", 10)
{
label_.set_name("cpu");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
thread_ = [this] {
dp.emit();
thread_.sleep_for(interval_);

View File

@ -1,18 +1,18 @@
#include "modules/custom.hpp"
waybar::modules::Custom::Custom(const std::string name,
waybar::modules::Custom::Custom(const std::string& name,
const Json::Value& config)
: ALabel(config, "{}"), name_(name), fp_(nullptr)
{
label_.set_name("custom-" + name_);
if (config_["exec"].isString()) {
if (interval_.count() > 0) {
delayWorker();
} else {
continuousWorker();
}
} else {
update();
}
dp.emit();
}
waybar::modules::Custom::~Custom()
@ -31,8 +31,7 @@ void waybar::modules::Custom::delayWorker()
auto res = waybar::util::command::exec(config_["exec-if"].asString());
if (res.exit_code != 0) {
can_update = false;
label_.hide();
label_.set_name("");
event_box_.hide();
}
}
if (can_update) {
@ -80,11 +79,8 @@ auto waybar::modules::Custom::update() -> void
{
// Hide label if output is empty
if (config_["exec"].isString() && (output_.out.empty() || output_.exit_code != 0)) {
label_.hide();
label_.set_name("");
event_box_.hide();
} else {
label_.set_name("custom-" + name_);
if (config_["return-type"].asString() == "json") {
parseOutputJson();
} else {
@ -109,7 +105,7 @@ auto waybar::modules::Custom::update() -> void
prevclass_ = "";
}
label_.show();
event_box_.show();
}
}

View File

@ -1,8 +1,12 @@
#include "modules/memory.hpp"
waybar::modules::Memory::Memory(const Json::Value& config)
waybar::modules::Memory::Memory(const std::string& id, const Json::Value& config)
: ALabel(config, "{}%", 30)
{
label_.set_name("memory");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
thread_ = [this] {
dp.emit();
thread_.sleep_for(interval_);
@ -17,11 +21,9 @@ auto waybar::modules::Memory::update() -> void
label_.set_markup(fmt::format(format_, used_ram_percentage));
auto used_ram_gigabytes = (memtotal_ - memfree_) / std::pow(1024, 2);
label_.set_tooltip_text(fmt::format("{:.{}f}Gb used", used_ram_gigabytes, 1));
label_.set_name("memory");
label_.show();
event_box_.show();
} else {
label_.set_name("");
label_.hide();
event_box_.hide();
}
}

View File

@ -1,9 +1,13 @@
#include "modules/network.hpp"
waybar::modules::Network::Network(const Json::Value& config)
waybar::modules::Network::Network(const std::string& id, const Json::Value& config)
: ALabel(config, "{ifname}", 60), family_(AF_INET),
cidr_(-1), signal_strength_dbm_(0), signal_strength_(0)
{
label_.set_name("network");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
sock_fd_ = socket(AF_NETLINK, SOCK_RAW, NETLINK_ROUTE);
if (sock_fd_ < 0) {
throw std::runtime_error("Can't open network socket");
@ -29,10 +33,9 @@ waybar::modules::Network::Network(const Json::Value& config)
}
}
initNL80211();
label_.set_name("network");
// Trigger first values
getInfo();
update();
dp.emit();
worker();
}

View File

@ -1,6 +1,6 @@
#include "modules/pulseaudio.hpp"
waybar::modules::Pulseaudio::Pulseaudio(const Json::Value &config)
waybar::modules::Pulseaudio::Pulseaudio(const std::string& id, const Json::Value &config)
: ALabel(config, "{volume}%"),
mainloop_(nullptr),
mainloop_api_(nullptr),
@ -10,6 +10,9 @@ waybar::modules::Pulseaudio::Pulseaudio(const Json::Value &config)
muted_(false),
scrolling_(false) {
label_.set_name("pulseaudio");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
mainloop_ = pa_threaded_mainloop_new();
if (mainloop_ == nullptr) {
throw std::runtime_error("pa_mainloop_new() failed.");

View File

@ -2,7 +2,7 @@
#include <iostream>
waybar::modules::SNI::Tray::Tray(const Json::Value &config)
waybar::modules::SNI::Tray::Tray(const std::string& id, const Json::Value &config)
: config_(config), watcher_(), host_(nb_hosts_, config,
std::bind(&Tray::onAdd, this, std::placeholders::_1),
std::bind(&Tray::onRemove, this, std::placeholders::_1))

View File

@ -1,12 +1,17 @@
#include "modules/sway/mode.hpp"
waybar::modules::sway::Mode::Mode(const Bar& bar, const Json::Value& config)
waybar::modules::sway::Mode::Mode(const std::string& id, const Bar& bar, const Json::Value& config)
: ALabel(config, "{}"), bar_(bar)
{
label_.set_name("mode");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
ipc_.connect();
ipc_.subscribe("[ \"mode\" ]");
// Launch worker
worker();
dp.emit();
}
void waybar::modules::sway::Mode::worker()
@ -32,12 +37,10 @@ void waybar::modules::sway::Mode::worker()
auto waybar::modules::sway::Mode::update() -> void
{
if (mode_.empty()) {
label_.set_name("");
label_.hide();
event_box_.hide();
} else {
label_.set_name("mode");
label_.set_markup(fmt::format(format_, mode_));
label_.set_tooltip_text(mode_);
label_.show();
event_box_.show();
}
}

View File

@ -1,9 +1,12 @@
#include "modules/sway/window.hpp"
waybar::modules::sway::Window::Window(const Bar &bar, const Json::Value& config)
waybar::modules::sway::Window::Window(const std::string& id, const Bar &bar, const Json::Value& config)
: ALabel(config, "{}"), bar_(bar), windowId_(-1)
{
label_.set_name("window");
if (!id.empty()) {
label_.get_style_context()->add_class(id);
}
if (label_.get_max_width_chars() == -1) {
label_.set_hexpand(true);
label_.set_ellipsize(Pango::EllipsizeMode::ELLIPSIZE_END);

View File

@ -1,10 +1,13 @@
#include "modules/sway/workspaces.hpp"
waybar::modules::sway::Workspaces::Workspaces(const Bar& bar,
waybar::modules::sway::Workspaces::Workspaces(const std::string& id, const Bar& bar,
const Json::Value& config)
: bar_(bar), config_(config), scrolling_(false)
{
box_.set_name("workspaces");
if (!id.empty()) {
box_.get_style_context()->add_class(id);
}
ipc_.connect();
ipc_.subscribe("[ \"workspace\" ]");
// Launch worker