Compare commits

...

4 commits

Author SHA1 Message Date
3e58cde2fe refactor: move to uv
instead of poetry
2026-04-08 08:29:12 +02:00
ddfe1c6eb6 feat(box): color based on the hash of the app
Instead of based on the urgency.
2025-03-13 16:30:25 +01:00
7b80153d15 feat(MessageBox): use a hashed color for summaries 2025-02-19 10:39:36 +01:00
1d440ac7c8 feat(MessageBox): replace vertical layout with boxes
- fix: test and send use argparse.
2025-02-19 10:18:27 +01:00
3 changed files with 89 additions and 15 deletions

View file

@ -20,6 +20,8 @@ The CLI bard relies on your terminal using a font patched with the "Powerline"
characters. The recommended fonts are the ones from the characters. The recommended fonts are the ones from the
[Nerd font project](https://www.nerdfonts.com/). [Nerd font project](https://www.nerdfonts.com/).
You may also need to install the `libgirepository-2.0-dev` on your system.
Usage Usage
===== =====

View file

@ -1,15 +1,30 @@
[tool.poetry] [project]
name = "clibard" name = "clibard"
version = "0.1.0" version = "0.1.0"
description = "See all your notifications in the terminal" description = "See all your notifications in the terminal"
authors = ["nojhan <nojhan@nojhan.net>"] authors = [
{ name = "nojhan", email = "nojhan@nojhan.net" },
]
readme = "README.md" readme = "README.md"
[tool.poetry.dependencies] requires-python = ">3.11"
python = "^3.11" dependencies = [
faker = "^0.7.4" "faker>=0.7.4",
humanize = "^4.11" "humanize>=4.11",
rich = "^13.9" "rich>=13.9",
dbus-python = "^1.3" "dbus-python>=1.3",
PyGObject = "^3.50" # You may need to install the system package for libgirepository1.0-dev "PyGObject>=3.50", # You may need to install the system package for libgirepository-2.0-dev
]
[project.scripts]
clibard = "clibard.clibard:main"
[build-system]
requires = ["setuptools>=68", "wheel"]
build-backend = "setuptools.build_meta"
[tool.setuptools.packages.find]
where = ["src"]
include = ["clibard"]

View file

@ -3,9 +3,10 @@
import copy import copy
import signal import signal
import datetime import datetime
import humanize
import collections import collections
import humanize import rich
from rich.console import Console from rich.console import Console
import dbus import dbus
@ -149,6 +150,14 @@ class Message:
"body": 242, "body": 242,
} }
# 🚨🚩🚧🛎 🛈 🏲 🏴📌📳🗨 🗩 🗬 🗭 🗮 🗯 🧭⚠⚲✎ <20> ❓❔︖🯄
self.icons = {
"low": "🛈 ",
"normal": "🗨 ",
"critical": "🚨",
"unknown": "🯄 ",
}
self._style = {} self._style = {}
for k in self.color: for k in self.color:
self._style[k] = f"color({self.color[k]})" self._style[k] = f"color({self.color[k]})"
@ -200,6 +209,19 @@ class Message:
self.last_color = f"{self.style(key)}" self.last_color = f"{self.style(key)}"
def auto_fg(self, bg):
# Automated black or white foreground.
if Color.ansi_lightness(bg) >= 50:
return "black"
else:
return "white"
def hash_color(self, text, colors = None):
if not colors:
return hash(text) % 256
else:
return colors[hash(text) % len(colors)]
class MessageLine(Message): class MessageLine(Message):
def print_on(self, console = None, end = ""): def print_on(self, console = None, end = ""):
@ -235,6 +257,37 @@ class MessageParagraph(Message):
return len(hdate) + len(self.app) + len(self.summary) + len(self.body) + 6 return len(hdate) + len(self.app) + len(self.summary) + len(self.body) + 6
class MessageBox(Message):
def print_on(self, console = None, end = ""):
hdate = self.date.strftime("%Y-%m-%d %H:%M")
if console != None:
# summ_color = f"{self.auto_fg(FIXME)} on color({self.color[self.urgency]})"
body_color = f"color({self.color['summary_'+self.urgency]})"
bg = self.hash_color(self.summary)
sfg = f"{self.auto_fg(bg)} on color({bg})"
sfgi = f"color({bg})"
summ = f"─[{sfgi}][/][{sfg}]{self.summary}[/][{sfgi}][/]─"
title = f"{self.icons[self.urgency]} {summ} {self.app}"
# title = f"[{summ_color}]{self.summary}[/]─ {self.app}"
bs = self.hash_color(self.app)
box = rich.panel.Panel(
f"[{body_color}]{self.body}[/]",
title=title,
title_align="left",
# subtitle = self.icons[self.urgency],
# subtitle_align = "left",
border_style=f"color({bs})",
safe_box = False,
)
console.print(box)
return len(hdate) + len(self.app) + len(self.summary) + len(self.body) + 6
class Broker: class Broker:
def __init__(self, max_msg = 100, bounds = "", msg_cls = Message): def __init__(self, max_msg = 100, bounds = "", msg_cls = Message):
@ -361,7 +414,7 @@ def test_messages(nb = 7):
return notifs return notifs
if __name__ == "__main__": def main():
import sys import sys
import argparse import argparse
@ -382,8 +435,8 @@ if __name__ == "__main__":
if asked.layout[0] == "h": if asked.layout[0] == "h":
broker = HorizontalBroker(bounds = "><") broker = HorizontalBroker(bounds = "><")
elif asked.layout[0] == "v": elif asked.layout[0] == "v":
broker = VerticalBroker(bounds = "><") broker = VerticalBroker(bounds = "><", msg_cls=MessageBox)
notifs = test_messages(int(sys.argv[2])) notifs = test_messages(int(asked.test))
for notif in notifs: for notif in notifs:
broker.receive(None, notif) broker.receive(None, notif)
print("\n", end="") print("\n", end="")
@ -391,7 +444,7 @@ if __name__ == "__main__":
elif asked.send: elif asked.send:
import os import os
import time import time
notifs = test_messages(int(sys.argv[2])) notifs = test_messages(int(asked.send))
for notif in notifs: for notif in notifs:
m = Message(notif) m = Message(notif)
os.system(f"""notify-send "{m.summary}" "{m.body}" -u {m.urgency}""") os.system(f"""notify-send "{m.summary}" "{m.body}" -u {m.urgency}""")
@ -402,5 +455,9 @@ if __name__ == "__main__":
broker.run() broker.run()
elif asked.layout[0] == "v": elif asked.layout[0] == "v":
broker = VerticalBroker() broker = VerticalBroker(msg_cls=MessageBox)
broker.run() broker.run()
if __name__ == "__main__":
main()