diff --git a/bumblebee/modules/.battery.py.un~ b/bumblebee/modules/.battery.py.un~ new file mode 100644 index 0000000..8ab0992 Binary files /dev/null and b/bumblebee/modules/.battery.py.un~ differ diff --git a/bumblebee/modules/.traffic.py.un~ b/bumblebee/modules/.traffic.py.un~ new file mode 100644 index 0000000..48d390d Binary files /dev/null and b/bumblebee/modules/.traffic.py.un~ differ diff --git a/bumblebee/modules/battery.py b/bumblebee/modules/battery.py index f5e565e..61741ed 100644 --- a/bumblebee/modules/battery.py +++ b/bumblebee/modules/battery.py @@ -58,9 +58,9 @@ class Module(bumblebee.engine.Module): if estimate == power.common.TIME_REMAINING_UNLIMITED: return None if estimate == power.common.TIME_REMAINING_UNKNOWN: - return "n/a" + return "" except Exception: - return "n/a" + return "" return bumblebee.util.durationfmt(estimate*60, shorten=True, suffix=True) # estimate is in minutes def capacity(self, widget): diff --git a/bumblebee/modules/battery.py~ b/bumblebee/modules/battery.py~ new file mode 100644 index 0000000..f5e565e --- /dev/null +++ b/bumblebee/modules/battery.py~ @@ -0,0 +1,120 @@ +# pylint: disable=C0111,R0903 + +"""Displays battery status, remaining percentage and charging information. + +Parameters: + * battery.device : Comma-separated list of battery devices to read information from (defaults to auto for auto-detection) + * battery.warning : Warning threshold in % of remaining charge (defaults to 20) + * battery.critical : Critical threshold in % of remaining charge (defaults to 10) + * battery.showdevice : If set to "true", add the device name to the widget (defaults to False) +""" + +import os +import glob + +import bumblebee.input +import bumblebee.output +import bumblebee.engine +import bumblebee.util + +try: + import power +except ImportError: + pass + +class Module(bumblebee.engine.Module): + def __init__(self, engine, config): + widgets = [] + super(Module, self).__init__(engine, config, widgets) + self._batteries = self.parameter("device", "auto").split(",") + if self._batteries[0] == "auto": + self._batteries = glob.glob("/sys/class/power_supply/BAT*") + else: + self._batteries = [ "/sys/class/power_supply/{}".format(b) for b in self._batteries ] + if len(self._batteries) == 0: + self._batteries = [ "/sys/class/power_supply/BAT0" ] + self.update(widgets) + engine.input.register_callback(self, button=bumblebee.input.LEFT_MOUSE, + cmd="gnome-power-statistics") + + def update(self, widgets): + new_widgets = [] + for path in self._batteries: + widget = self.widget(path) + if not widget: + widget = bumblebee.output.Widget(full_text=self.capacity, name=path) + new_widgets.append(widget) + self.capacity(widget) + while len(widgets) > 0: del widgets[0] + for widget in new_widgets: + widgets.append(widget) + self._widgets = widgets + + def remaining(self): + estimate = 0.0 + try: + estimate = power.PowerManagement().get_time_remaining_estimate() + # do not show remaining if on AC + if estimate == power.common.TIME_REMAINING_UNLIMITED: + return None + if estimate == power.common.TIME_REMAINING_UNKNOWN: + return "n/a" + except Exception: + return "n/a" + return bumblebee.util.durationfmt(estimate*60, shorten=True, suffix=True) # estimate is in minutes + + def capacity(self, widget): + widget.set("capacity", -1) + widget.set("ac", False) + if not os.path.exists(widget.name): + widget.set("capacity", 100) + widget.set("ac", True) + return "ac" + capacity = 100 + try: + with open("{}/capacity".format(widget.name)) as f: + capacity = int(f.read()) + except IOError: + return "n/a" + capacity = capacity if capacity < 100 else 100 + widget.set("capacity", capacity) + if bumblebee.util.asbool(self.parameter("showdevice", False)): + widget.set("theme.minwidth", "100% ({})".format(os.path.basename(widget.name))) + return "{}% ({})".format(capacity, os.path.basename(widget.name)) + widget.set("theme.minwidth", "100%") + + remaining = None + if bumblebee.util.asbool(self.parameter("showremaining", True)): + remaining = self.remaining() + + return "{}%{}".format(capacity, "" if not remaining else " ({})".format(remaining)) + + def state(self, widget): + state = [] + capacity = widget.get("capacity") + + if capacity < 0: + return ["critical", "unknown"] + + if capacity < int(self.parameter("critical", 10)): + state.append("critical") + elif capacity < int(self.parameter("warning", 20)): + state.append("warning") + + if widget.get("ac"): + state.append("AC") + else: + charge = "" + with open("{}/status".format(widget.name)) as f: + charge = f.read().strip() + if charge == "Discharging": + state.append("discharging-{}".format(min([10, 25, 50, 80, 100] , key=lambda i:abs(i-capacity)))) + else: + if capacity > 95: + state.append("charged") + else: + state.append("charging") + + return state + +# vim: tabstop=8 expandtab shiftwidth=4 softtabstop=4 diff --git a/bumblebee/modules/traffic.py b/bumblebee/modules/traffic.py index ee21794..500eaa5 100644 --- a/bumblebee/modules/traffic.py +++ b/bumblebee/modules/traffic.py @@ -23,6 +23,7 @@ class Module(bumblebee.engine.Module): self._exclude = tuple(filter(len, self.parameter("exclude", "lo,virbr,docker,vboxnet,veth").split(","))) self._status = "" + self._showname = self.parameter("showname", "True") self._prev = {} self._states = {} self._states["include"] = [] @@ -86,11 +87,12 @@ class Module(bumblebee.engine.Module): name = "traffic-{}".format(interface) - self.create_widget(widgets, name, interface) + if self._showname != "False": + self.create_widget(widgets, name, interface) for direction in ["rx", "tx"]: name = "traffic.{}-{}".format(direction, interface) - widget = self.create_widget(widgets, name, attributes={"theme.minwidth": "1000.00MB"}) + widget = self.create_widget(widgets, name, attributes={"theme.minwidth": "100.00MB"}) prev = self._prev.get(name, 0) speed = bumblebee.util.bytefmt(int(data[direction]) - int(prev)) widget.full_text(speed) diff --git a/bumblebee/modules/traffic.py~ b/bumblebee/modules/traffic.py~ new file mode 100644 index 0000000..5dbad89 --- /dev/null +++ b/bumblebee/modules/traffic.py~ @@ -0,0 +1,100 @@ +# pylint: disable=C0111,R0903 + +"""Displays network IO for interfaces. + +Parameters: + * traffic.exclude: Comma-separated list of interface prefixes to exclude (defaults to "lo,virbr,docker,vboxnet,veth") + * traffic.states: Comma-separated list of states to show (prefix with "^" to invert - i.e. ^down -> show all devices that are not in state down) +""" + +import re +import psutil +import netifaces + +import bumblebee.util +import bumblebee.input +import bumblebee.output +import bumblebee.engine + +class Module(bumblebee.engine.Module): + def __init__(self, engine, config): + widgets = [] + super(Module, self).__init__(engine, config, widgets) + self._exclude = tuple(filter(len, self.parameter("exclude", "lo,virbr,docker,vboxnet,veth").split(","))) + self._status = "" + + self._showname = self.parameter("showname", "True") + self._prev = {} + self._states = {} + self._states["include"] = [] + self._states["exclude"] = [] + for state in tuple(filter(len, self.parameter("states", "").split(","))): + if state[0] == "^": + self._states["exclude"].append(state[1:]) + else: + self._states["include"].append(state) + self._update_widgets(widgets) + + def state(self, widget): + if "traffic.rx" in widget.name: + return "rx" + if "traffic.tx" in widget.name: + return "tx" + return self._status + + def update(self, widgets): + self._update_widgets(widgets) + + def create_widget(self, widgets, name, txt=None, attributes={}): + widget = bumblebee.output.Widget(name=name) + widget.full_text(txt) + widgets.append(widget) + + for key in attributes: + widget.set(key, attributes[key]) + + return widget + + def get_addresses(self, intf): + retval = [] + try: + for ip in netifaces.ifaddresses(intf).get(netifaces.AF_INET, []): + if ip.get("addr", "") != "": + retval.append(ip.get("addr")) + except Exception: + return [] + return retval + + def _update_widgets(self, widgets): + interfaces = [ i for i in netifaces.interfaces() if not i.startswith(self._exclude) ] + + del widgets[:] + + counters = psutil.net_io_counters(pernic=True) + for interface in interfaces: + if not interface: interface = "lo" + state = "down" + if len(self.get_addresses(interface)) > 0: + state = "up" + + if len(self._states["exclude"]) > 0 and state in self._states["exclude"]: continue + if len(self._states["include"]) > 0 and state not in self._states["include"]: continue + + data = { + "rx": counters[interface].bytes_recv, + "tx": counters[interface].bytes_sent, + } + + name = "traffic-{}".format(interface) + + #self.create_widget(widgets, name, interface) + + for direction in ["rx", "tx"]: + name = "traffic.{}-{}".format(direction, interface) + widget = self.create_widget(widgets, name, attributes={"theme.minwidth": "100.00MB"}) + prev = self._prev.get(name, 0) + speed = bumblebee.util.bytefmt(int(data[direction]) - int(prev)) + widget.full_text(speed) + self._prev[name] = data[direction] + +# vim: tabstop=8 expandtab shiftwidth=4 softtabstop=4 diff --git a/themes/.gruvbox-powerline-edit.json.un~ b/themes/.gruvbox-powerline-edit.json.un~ new file mode 100644 index 0000000..57a2bd4 Binary files /dev/null and b/themes/.gruvbox-powerline-edit.json.un~ differ diff --git a/themes/.powerline-edit.json.un~ b/themes/.powerline-edit.json.un~ new file mode 100644 index 0000000..754aa73 Binary files /dev/null and b/themes/.powerline-edit.json.un~ differ diff --git a/themes/gruvbox-powerline-edit.json b/themes/gruvbox-powerline-edit.json new file mode 100644 index 0000000..c943358 --- /dev/null +++ b/themes/gruvbox-powerline-edit.json @@ -0,0 +1,51 @@ +{ + "icons": [ "paxy97", "awesome-fonts" ], + "defaults": { + "warning": { + "fg": "#1d2021", + "bg": "#d79921e6" + }, + "critical": { + "fg": "#fbf1c7", + "bg": "#cc241de6" + }, + "default-separators": false, + "separator-block-width": 0 + }, + "cycle": [ + { + "fg": "#ebdbb2", + "bg": "#171a1ce6" + }, + { + "fg": "#fbf1c7", + "bg": "#282828e6" + } + ], + "dnf": { + "good": { + "fg": "#002b36", + "bg": "#859900e6" + } + }, + "battery": { + "charged": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + }, + "AC": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + } + }, + "cmus": { + "fg": "#fbf1c7", + "bg": "#080808e6" + }, + "bluetooth": { + "ON": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + } + } +} diff --git a/themes/gruvbox-powerline-edit.json~ b/themes/gruvbox-powerline-edit.json~ new file mode 100644 index 0000000..587ff84 --- /dev/null +++ b/themes/gruvbox-powerline-edit.json~ @@ -0,0 +1,51 @@ +{ + "icons": [ "paxy97", "awesome-fonts" ], + "defaults": { + "warning": { + "fg": "#1d2021", + "bg": "#d79921e6" + }, + "critical": { + "fg": "#fbf1c7", + "bg": "#cc241de6" + }, + "default-separators": false, + "separator-block-width": 0 + }, + "cycle": [ + { + "fg": "#ebdbb2", + "bg": "#171a1ce6" + }, + { + "fg": "#fbf1c7", + "bg": "#282828e6" + } + ], + "dnf": { + "good": { + "fg": "#002b36", + "bg": "#859900e6" + } + }, + "battery": { + "charged": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + }, + "AC": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + } + }, + "cmus": { + "fg": "#fbf1c7", + "bg": "#484848e6" + }, + "bluetooth": { + "ON": { + "fg": "#1d2021", + "bg": "#b8bb26e6" + } + } +} diff --git a/themes/powerline-edit.json b/themes/powerline-edit.json new file mode 100644 index 0000000..1828ebd --- /dev/null +++ b/themes/powerline-edit.json @@ -0,0 +1,48 @@ +{ + "icons": [ "awesome-fonts" ], + "defaults": { + "separator-block-width": 0, + "critical": { + "fg": "#ffffff", + "bg": "#ff0000" + }, + "warning": { + "fg": "#d75f00", + "bg": "#ffd700" + }, + "default_separators": false + }, + "cycle": [ + { + "fg": "#ffd700", + "bg": "#d75f00" + }, + { + "fg": "#ffffff", + "bg": "#0000f066" + } + ], + "dnf": { + "good": { + "fg": "#494949", + "bg": "#41db00" + } + }, + "battery": { + "charged": { + "fg": "#494949", + "bg": "#41db00" + }, + "AC": { + "fg": "#494949", + "bg": "#41db00" + }, + "charging": { + + "fg": "#494949", + "bg": "#41db00" + + } + + } +} diff --git a/themes/powerline-edit.json~ b/themes/powerline-edit.json~ new file mode 100644 index 0000000..df043c4 --- /dev/null +++ b/themes/powerline-edit.json~ @@ -0,0 +1,48 @@ +{ + "icons": [ "awesome-fonts" ], + "defaults": { + "separator-block-width": 0, + "critical": { + "fg": "#ffffff", + "bg": "#ff0000" + }, + "warning": { + "fg": "#d75f00", + "bg": "#ffd700" + }, + "default_separators": false + }, + "cycle": [ + { + "fg": "#ffd700", + "bg": "#d75f00" + }, + { + "fg": "#ffffff", + "bg": "#0000f0" + } + ], + "dnf": { + "good": { + "fg": "#494949", + "bg": "#41db00" + } + }, + "battery": { + "charged": { + "fg": "#494949", + "bg": "#41db00" + }, + "AC": { + "fg": "#494949", + "bg": "#41db00" + }, + "charging": { + + "fg": "#494949", + "bg": "#41db00" + + } + + } +}