bar hide/show commands
This commit is contained in:
parent
1175bbbc23
commit
57063cb17f
2 changed files with 61 additions and 32 deletions
|
@ -1,5 +1,5 @@
|
||||||
project('somebar', ['c', 'cpp'],
|
project('somebar', ['c', 'cpp'],
|
||||||
default_options: ['cpp_std=c++17'])
|
default_options: ['cpp_std=c++17', 'cpp_args=-Wno-parentheses'])
|
||||||
|
|
||||||
wayland_dep = dependency('wayland-client')
|
wayland_dep = dependency('wayland-client')
|
||||||
wayland_cursor_dep = dependency('wayland-cursor')
|
wayland_cursor_dep = dependency('wayland-cursor')
|
||||||
|
|
91
src/main.cpp
91
src/main.cpp
|
@ -31,6 +31,8 @@ struct Monitor {
|
||||||
wl_unique_ptr<wl_output> wlOutput;
|
wl_unique_ptr<wl_output> wlOutput;
|
||||||
wl_unique_ptr<znet_tapesoftware_dwl_wm_monitor_v1> dwlMonitor;
|
wl_unique_ptr<znet_tapesoftware_dwl_wm_monitor_v1> dwlMonitor;
|
||||||
std::optional<Bar> bar;
|
std::optional<Bar> bar;
|
||||||
|
bool desiredVisibility {true};
|
||||||
|
bool hasData;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct SeatPointer {
|
struct SeatPointer {
|
||||||
|
@ -45,13 +47,14 @@ struct Seat {
|
||||||
std::optional<SeatPointer> pointer;
|
std::optional<SeatPointer> pointer;
|
||||||
};
|
};
|
||||||
|
|
||||||
static void waylandFlush();
|
static void updatemon(Monitor &mon);
|
||||||
static void requireGlobal(const void *p, const char *name);
|
|
||||||
static void setupStatusFifo();
|
static void setupStatusFifo();
|
||||||
static void onStatus();
|
static void onStatus();
|
||||||
|
static void cleanup();
|
||||||
|
static void requireGlobal(const void *p, const char *name);
|
||||||
|
static void waylandFlush();
|
||||||
[[noreturn]] static void diesys(const char *why);
|
[[noreturn]] static void diesys(const char *why);
|
||||||
[[noreturn]] static void die(const char *why);
|
[[noreturn]] static void die(const char *why);
|
||||||
static void cleanup();
|
|
||||||
|
|
||||||
wl_display *display;
|
wl_display *display;
|
||||||
wl_compositor *compositor;
|
wl_compositor *compositor;
|
||||||
|
@ -67,6 +70,7 @@ static wl_cursor_image *cursorImage;
|
||||||
static bool ready;
|
static bool ready;
|
||||||
static std::list<Monitor> monitors;
|
static std::list<Monitor> monitors;
|
||||||
static std::list<Seat> seats;
|
static std::list<Seat> seats;
|
||||||
|
static Monitor *selmon;
|
||||||
static std::string lastStatus;
|
static std::string lastStatus;
|
||||||
static std::string statusFifoName;
|
static std::string statusFifoName;
|
||||||
static int epoll {-1};
|
static int epoll {-1};
|
||||||
|
@ -75,10 +79,6 @@ static int statusFifoFd {-1};
|
||||||
static int statusFifoWriter {-1};
|
static int statusFifoWriter {-1};
|
||||||
static bool quitting {false};
|
static bool quitting {false};
|
||||||
|
|
||||||
// Intentionally not inside Monitor, so we can preemptively manage the
|
|
||||||
// visibility of bars on future outputs.
|
|
||||||
static std::unordered_map<std::string, bool> barVisibility;
|
|
||||||
|
|
||||||
void view(Monitor &m, const Arg &arg)
|
void view(Monitor &m, const Arg &arg)
|
||||||
{
|
{
|
||||||
znet_tapesoftware_dwl_wm_monitor_v1_set_tags(m.dwlMonitor.get(), arg.ui, 1);
|
znet_tapesoftware_dwl_wm_monitor_v1_set_tags(m.dwlMonitor.get(), arg.ui, 1);
|
||||||
|
@ -212,6 +212,11 @@ static const struct znet_tapesoftware_dwl_wm_v1_listener dwlWmListener = {
|
||||||
static const struct znet_tapesoftware_dwl_wm_monitor_v1_listener dwlWmMonitorListener {
|
static const struct znet_tapesoftware_dwl_wm_monitor_v1_listener dwlWmMonitorListener {
|
||||||
.selected = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*, uint32_t selected) {
|
.selected = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*, uint32_t selected) {
|
||||||
auto mon = static_cast<Monitor*>(mv);
|
auto mon = static_cast<Monitor*>(mv);
|
||||||
|
if (selected) {
|
||||||
|
selmon = mon;
|
||||||
|
} else if (selmon == mon) {
|
||||||
|
selmon = nullptr;
|
||||||
|
}
|
||||||
mon->bar->setSelected(selected);
|
mon->bar->setSelected(selected);
|
||||||
},
|
},
|
||||||
.tag = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*, uint32_t tag, uint32_t state, uint32_t numClients, int32_t focusedClient) {
|
.tag = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*, uint32_t tag, uint32_t state, uint32_t numClients, int32_t focusedClient) {
|
||||||
|
@ -228,11 +233,8 @@ static const struct znet_tapesoftware_dwl_wm_monitor_v1_listener dwlWmMonitorLis
|
||||||
},
|
},
|
||||||
.frame = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*) {
|
.frame = [](void *mv, znet_tapesoftware_dwl_wm_monitor_v1*) {
|
||||||
auto mon = static_cast<Monitor*>(mv);
|
auto mon = static_cast<Monitor*>(mv);
|
||||||
if (mon->bar->visible()) {
|
mon->hasData = true;
|
||||||
mon->bar->invalidate();
|
updatemon(*mon);
|
||||||
} else {
|
|
||||||
mon->bar->show(mon->wlOutput.get());
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -240,9 +242,23 @@ static void setupMonitor(Monitor &monitor) {
|
||||||
monitor.dwlMonitor.reset(znet_tapesoftware_dwl_wm_v1_get_monitor(dwlWm, monitor.wlOutput.get()));
|
monitor.dwlMonitor.reset(znet_tapesoftware_dwl_wm_v1_get_monitor(dwlWm, monitor.wlOutput.get()));
|
||||||
monitor.bar.emplace(&monitor);
|
monitor.bar.emplace(&monitor);
|
||||||
monitor.bar->setStatus(lastStatus);
|
monitor.bar->setStatus(lastStatus);
|
||||||
znet_tapesoftware_dwl_wm_monitor_v1_add_listener(monitor.dwlMonitor.get(), &dwlWmMonitorListener, &monitor);
|
|
||||||
auto xdgOutput = zxdg_output_manager_v1_get_xdg_output(xdgOutputManager, monitor.wlOutput.get());
|
auto xdgOutput = zxdg_output_manager_v1_get_xdg_output(xdgOutputManager, monitor.wlOutput.get());
|
||||||
zxdg_output_v1_add_listener(xdgOutput, &xdgOutputListener, &monitor);
|
zxdg_output_v1_add_listener(xdgOutput, &xdgOutputListener, &monitor);
|
||||||
|
znet_tapesoftware_dwl_wm_monitor_v1_add_listener(monitor.dwlMonitor.get(), &dwlWmMonitorListener, &monitor);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void updatemon(Monitor &mon)
|
||||||
|
{
|
||||||
|
if (!mon.hasData) return;
|
||||||
|
if (mon.desiredVisibility) {
|
||||||
|
if (mon.bar->visible()) {
|
||||||
|
mon.bar->invalidate();
|
||||||
|
} else {
|
||||||
|
mon.bar->show(mon.wlOutput.get());
|
||||||
|
}
|
||||||
|
} else if (mon.bar->visible()) {
|
||||||
|
mon.bar->hide();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// called after we have received the initial batch of globals
|
// called after we have received the initial batch of globals
|
||||||
|
@ -305,13 +321,27 @@ static void updateVisibility(const std::string &name, T updater)
|
||||||
{
|
{
|
||||||
auto isCurrent = name == argCurrent;
|
auto isCurrent = name == argCurrent;
|
||||||
auto isAll = name == argAll;
|
auto isAll = name == argAll;
|
||||||
|
for (auto& mon : monitors) {
|
||||||
|
if (isAll ||
|
||||||
|
isCurrent && &mon == selmon ||
|
||||||
|
mon.xdgName == name) {
|
||||||
|
auto newVisibility = updater(mon.desiredVisibility);
|
||||||
|
if (newVisibility != mon.desiredVisibility) {
|
||||||
|
mon.desiredVisibility = newVisibility;
|
||||||
|
updatemon(mon);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void onStatus()
|
static void onStatus()
|
||||||
{
|
{
|
||||||
|
// this doesn't handle cases where there's multiple or partial lines in the buffer
|
||||||
char buffer[512];
|
char buffer[512];
|
||||||
auto n = read(statusFifoFd, buffer, sizeof(buffer));
|
auto n = read(statusFifoFd, buffer, sizeof(buffer));
|
||||||
auto str = std::string {buffer, (unsigned long) n};
|
auto str = std::string {buffer, (unsigned long) n};
|
||||||
|
auto trailer = str.rfind('\n');
|
||||||
|
if (trailer != std::string::npos) str.erase(trailer);
|
||||||
if (str.rfind(prefixStatus, 0) == 0) {
|
if (str.rfind(prefixStatus, 0) == 0) {
|
||||||
lastStatus = str.substr(prefixStatus.size());
|
lastStatus = str.substr(prefixStatus.size());
|
||||||
for (auto &monitor : monitors) {
|
for (auto &monitor : monitors) {
|
||||||
|
@ -454,24 +484,14 @@ int main(int argc, char **argv)
|
||||||
cleanup();
|
cleanup();
|
||||||
}
|
}
|
||||||
|
|
||||||
void die(const char *why) {
|
void requireGlobal(const void *p, const char *name)
|
||||||
fprintf(stderr, "%s\n", why);
|
{
|
||||||
|
if (p) return;
|
||||||
|
fprintf(stderr, "Wayland compositor does not export required global %s, aborting.\n", name);
|
||||||
cleanup();
|
cleanup();
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
void diesys(const char *why) {
|
|
||||||
perror(why);
|
|
||||||
cleanup();
|
|
||||||
exit(1);
|
|
||||||
}
|
|
||||||
|
|
||||||
void cleanup() {
|
|
||||||
if (!statusFifoName.empty()) {
|
|
||||||
unlink(statusFifoName.c_str());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void waylandFlush()
|
void waylandFlush()
|
||||||
{
|
{
|
||||||
wl_display_dispatch_pending(display);
|
wl_display_dispatch_pending(display);
|
||||||
|
@ -485,10 +505,19 @@ void waylandFlush()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static void requireGlobal(const void *p, const char *name)
|
void die(const char *why) {
|
||||||
{
|
|
||||||
if (p) return;
|
|
||||||
fprintf(stderr, "Wayland compositor does not export required global %s, aborting.\n", name);
|
|
||||||
cleanup();
|
cleanup();
|
||||||
exit(1);
|
exit(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void diesys(const char *why) {
|
||||||
|
perror(why);
|
||||||
|
cleanup();
|
||||||
|
exit(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
void cleanup() {
|
||||||
|
if (!statusFifoName.empty()) {
|
||||||
|
unlink(statusFifoName.c_str());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
Loading…
Reference in a new issue