Easy menu building for SwiftBar (... and xbar)
Project description
swiftbarmenu
✨ Easy menu building for SwiftBar (... and xbar).
Transform this...
from swiftbarmenu import Menu
m = Menu('My menu')
m.add_item('Item 1')
item2 = m.add_item('Item 2', sep=True, checked=True)
item2.add_item('Subitem 1')
item2.add_item('Subitem 2')
m.add_link('Item 3', 'https://example.com', color='yellow')
m.add_item(':thermometer: Item 4', color='orange', sfcolor='black', sfsize=20)
m.dump()
Into this...
Installation
pip install swiftbarmenu
Check out uv!
Usage
Check out the features through basic examples below.
Basic menu
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_item('Item 1')
Item 1
>>> m.add_item('Item 2')
Item 2
>>> m.dump()
My menu
---
Item 1
Item 2
Added items are instances of MenuItem:
>>> from swiftbarmenu import MenuItem
>>> m = Menu('My menu')
>>> item = m.add_item('Item 1')
>>> isinstance(item, MenuItem)
True
>>> item.text
'Item 1'
Multiple header
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_header('Header 2')
Header 2
>>> m.add_header('Header 3')
Header 3
>>> m.dump()
My menu
Header 2
Header 3
---
Add parameters
You can add multiple parameters:
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> item = m.add_item('Item 1', color='orange', size=18, checked=True)
>>> item
Item 1|color=orange size=18 checked=True
>>> m.dump()
My menu
---
Item 1|color=orange size=18 checked=True
>>> item.text
'Item 1'
>>> item.params
{'color': 'orange', 'size': 18, 'checked': True}
>>>
Add links
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_link('GitHub', 'https://github.com')
GitHub|href=https://github.com
>>> m.dump()
My menu
---
GitHub|href=https://github.com
It's actually a shortcut for:
>>> m.add_item('GitHub', href='https://github.com')
GitHub|href=https://github.com
Nested items
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> item1 = m.add_item('Item 1')
>>> item1.add_item('Item 1.1')
Item 1.1
>>> item1.add_item('Item 1.2')
Item 1.2
>>> item1.add_item('Item 1.3')
Item 1.3
>>> m.dump()
My menu
---
Item 1
-- Item 1.1
-- Item 1.2
-- Item 1.3
Swift icons
You can add SF Symbols using :symbol:
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_item('Sunny! :sun.max:')
Sunny! :sun.max:
>>> m.add_item('Cloudy! :cloud.rain:', sfcolor='blue')
Cloudy! :cloud.rain:|sfcolor=blue
>>> m.dump()
My menu
---
Sunny! :sun.max:
Cloudy! :cloud.rain:|sfcolor=blue
The parameter sfcolor only colorizes sf symbols.
Search sf symbols here.
Add separators
A separator is a thin long line on the menu:
>>> from swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_item('Item 1')
Item 1
>>> m.add_item('Item 2', sep=True)
Item 2
>>> m.add_item('Item 3')
Item 3
>>> m.dump()
My menu
---
Item 1
---
Item 2
Item 3
You can explicitly add a separator using:
>>> m.add_sep()
---
Access header and body
Within the menu, you can access the header and the body:
>>> from src.swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_header('Header 2')
Header 2
>>> m.add_header('Header 3')
Header 3
>>> m.add_item('Item 1')
Item 1
>>> m.add_item('Item 2')
Item 2
>>> m.header
[My menu, Header 2, Header 3]
>>> m.body
[Item 1, Item 2]
You can also access items inside header and body:
>>> from swiftbarmenu import MenuItem
>>> m.header[0]
My menu
>>> isinstance(m.header[0], MenuItem)
True
>>> m.body[1]
Item 2
>>> isinstance(m.body[1], MenuItem)
True
Even with nested items:
>>> from src.swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> item1 = m.add_item('Item 1')
>>> item1.add_item('Item 1.1')
Item 1.1
>>> item1.add_item('Item 1.2')
Item 1.2
>>> item1.add_item('Item 1.3')
Item 1.3
>>> item1[2]
Item 1.3
Clear items
You can clear whole menu:
>>> from src.swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> m.add_header('Header 2')
Header 2
>>> m.add_header('Header 3')
Header 3
>>> m.add_item('Item 1')
Item 1
>>> m.add_item('Item 2')
Item 2
>>> m
My menu
Header 2
Header 3
---
Item 1
Item 2
>>> m.clear()
>>> m
>>> m.header
[]
>>> m.body
[]
You can also clear nested items for a certain item:
>>> from src.swiftbarmenu import Menu
>>> m = Menu('My menu')
>>> item1 = m.add_item('Item 1')
>>> item1.add_item('Item 1.1')
Item 1.1
>>> item1.add_item('Item 1.2')
Item 1.2
>>> item1.add_item('Item 1.3')
Item 1.3
>>> m
My menu
---
Item 1
-- Item 1.1
-- Item 1.2
-- Item 1.3
>>> item1.clear()
>>> m
My menu
---
Item 1
Changelog
Releases use Semantic Versioning (<major>.<minor>.<patch>).
0.1.1
Released 2025-02-27
- Fixes menus with no header.
0.1.0
Released 2025-02-26
- First release.
Project details
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters