Jibo Dynamic Menu System
This module provides a dynamic menu system that automatically scans the Skills directory for menuEntry.json files and adds them to Jibo's menu screen.
How It Works
When Jibo boots up, the main-menu-patch.js module:
- Patches
jibo.loader.load()to intercept menu loading - Scans the
/opt/jibo/Jibo/Skillsdirectory for folders containingmenuEntry.json - Injects the found skills/submenus into the main menu
- Patches the main-menu skill's
redirectToSkillto handle custom skill launches
Quick Start
Adding a Simple Skill Button to the Menu (you really should follow PROVIDERS.md at this point)
- Create a folder in the
Skillsdirectory (e.g.,MySkill/) - Add a
menuEntry.jsonfile inside:
{
"type": "skill",
"title": "My Skill",
"icon": "resources/icons/settings.png",
"color": "blue",
"skillId": "MySkill",
"description": "Short description of my skill",
"order": 50
}
- Your skill will automatically appear in Jibo's main menu!
Note: For the button to actually launch a skill, that skill must be a proper Jibo skill package registered in @be/be/package.json. If the skill isn't found, Jibo will show a fallback message.
Creating a Submenu (Category/Folder)
- Create a folder in the
Skillsdirectory (e.g.,Games/) - Add a
menuEntry.jsonmarking it as a submenu:
{
"type": "submenu",
"title": "Games",
"submenuTitle": "Choose a Game",
"icon": "resources/icons/fun-stuff.png",
"color": "purple",
"description": "Fun games to play with Jibo",
"order": 10
}
- Inside that folder, create subfolders for each skill, each with their own
menuEntry.json - A button will appear in the main menu that opens a submenu with those skills!
Directory Structure Example (OLD)
/opt/jibo/Jibo/Skills/
├── @be/ # Core brain (ignored by scanner)
├── MySimpleSkill/
│ └── menuEntry.json # type: "skill" - appears as button in main menu
├── MyGames/
│ ├── menuEntry.json # type: "submenu" - opens submenu when pressed
│ ├── GameOne/
│ │ └── menuEntry.json # type: "skill" - appears in MyGames submenu
│ └── GameTwo/
│ └── menuEntry.json # type: "skill" - appears in MyGames submenu
menuEntry.json Schema
| Field | Type | Required | Description |
|---|---|---|---|
type |
"skill" | "submenu" |
Yes | "skill" for buttons, "submenu" for folders |
title |
string | Yes | Button label shown on Jibo's screen |
icon |
string | Yes | Icon path (see Icon Paths below) |
color |
string | No | Button color theme (see below). Default: "default" |
skillId |
string | Yes (for skills) | The skill ID to launch |
submenuTitle |
string | No | Title shown when submenu is opened |
description |
string | No | Tooltip/accessibility text |
order |
number | No | Sort order (lower = first). Default: 100 |
hidden |
boolean | No | Set to true to hide from menu |
Available Colors
default- Standard grayblue- Blue themegreen- Green themered- Red themepurple- Purple themeorange- Orange themeteal- Teal/cyan themepink- Pink themeyellow- Yellow themecyan- Cyan theme
Icon Paths
Icons are resolved relative to the @be/main-menu package. Available built-in icons:
| Icon Path | Description |
|---|---|
resources/icons/settings.png |
Settings gear |
resources/icons/fun-stuff.png |
Star/fun icon (good for submenus) |
resources/icons/clock.png |
Clock |
resources/icons/heart.png |
Heart |
resources/icons/surprise.png |
Gift/surprise |
resources/icons/dance.png |
Dancing figure |
resources/icons/joke.png |
Comedy mask |
resources/icons/tips.png |
Lightbulb |
resources/icons/gallery.png |
Photo gallery |
resources/icons/radio.png |
Music notes |
resources/icons/create.png |
Camera |
resources/icons/photobooth.png |
Photo booth |
resources/icons/exercise.png |
Exercise/yoga |
resources/icons/weather.png |
Weather cloud |
resources/icons/calendar.png |
Calendar |
resources/icons/circuit-saver.png |
Circuit saver |
resources/icons/dice.png |
Dice |
resources/icons/coin.png |
Coin |
resources/icons/emoji.png |
Emoji face |
resources/icons/word-of-the-day.png |
Word icon |
resources/icons/news.png |
News icon |
resources/icons/twerk.png |
Twerk icon |
resources/icons/scanner.png |
Scanner icon |
Example: Complete Skill Setup
Simple Skill (testSkillA/menuEntry.json)
{
"type": "skill",
"title": "Test Skill A",
"icon": "resources/icons/settings.png",
"color": "blue",
"skillId": "testSkillA",
"description": "A test skill",
"order": 10
}
Submenu (TestSubMenuA/menuEntry.json)
{
"type": "submenu",
"title": "Test Submenu",
"submenuTitle": "Test Skills",
"icon": "resources/icons/fun-stuff.png",
"color": "purple",
"description": "A submenu with test skills",
"order": 20
}
Skill inside Submenu (TestSubMenuA/testSkillB/menuEntry.json)
{
"type": "skill",
"title": "Test Skill B",
"icon": "resources/icons/surprise.png",
"color": "green",
"skillId": "testSkillB",
"description": "A skill inside a submenu",
"order": 1
}
Technical Details
How the Patch Works
- postinit.js calls
mainMenuPatch.applyPatch(be)andmainMenuPatch.patchLoader(jibo) - When the main-menu skill tries to load
main-menu-verbal.json, the patch intercepts it - The patch scans the Skills directory for
menuEntry.jsonfiles - It converts them to the proper button format and injects them into the menu config
- When a dynamic skill button is pressed, the patched
redirectToSkillhandles the launch - For submenus, a new menu view is displayed with the submenu's children
Files
main-menu-patch.js- Core patch that hooks into the systemskills-scanner.js- Alternative scanning implementation (not currently used)menu-manager.js- Alternative menu display implementation (not currently used)
Debugging
Check the browser console for log messages starting with main-menu-patch:. These show:
- When the patch is initialized
- When menu loads are intercepted
- How many dynamic skills are injected
- When skills/submenus are selected
Limitations
- Nested submenus (submenus within submenus) are not supported
- Custom skills must be registered in
@be/be/package.jsonto actually launch - Icon files must exist in the
@be/main-menu/resources/icons/directory
Troubleshooting
Skill button not appearing in menu?
- Check that
menuEntry.jsonexists and is valid JSON - Verify
hiddenis not set totrue - Make sure
typeis set to"skill"or"submenu" - Check the browser console for
main-menu-patch:log messages
Submenu appears empty?
- Make sure child skill folders have
menuEntry.jsonfiles - Verify child skills have
type: "skill"(nested submenus not supported) - Check that child folders are direct children of the submenu folder
Skill button doesn't launch anything?
- The skill needs to be a proper Jibo skill package
- The skill must be registered in
@be/be/package.jsonunderjibo.skills - If unregistered, Jibo will show a fallback message
Icon not loading?
- Verify the icon path is correct (e.g.,
resources/icons/settings.png) - Only built-in icons from
@be/main-menu/resources/icons/are supported - Check the list of available icons above