+class MenuItem(object):
+ type = None
+
+ def __init__(self, menu=None):
+ self.menu = menu
+
+ def is_active(self):
+ return False
+
+
+class MenuDivider(MenuItem):
+ type = "divider"
+
+
+class MenuHeader(MenuItem):
+ type = "header"
+
+ def __init__(self, title, menu=None):
+ MenuItem.__init__(self, menu=menu)
+
+ self.title = title
+
+
+class MenuLink(MenuItem):
+ type = "link"
+
+ def __init__(self, title, handler=None, url=None, menu=None):
+ MenuItem.__init__(self, menu=menu)
+
+ self.title = title
+ self.handler = handler
+
+ self.url = url or handler.url
+
+ def is_active(self):
+ if not self.handler:
+ return False
+
+ return isinstance(self.menu.handler, self.handler)
+
+
+class MenuMixin(object):
+ type = "menu"
+
+ @property
+ def items(self):
+ if not hasattr(self, "_items"):
+ self._items = []
+
+ return self._items
+
+ def __iter__(self):
+ """
+ Iterator over all item in this menu
+ """
+ return iter(self.items)
+
+ def add_divider(self, *args, **kwargs):
+ """
+ Adds a divider to the menu
+ """
+ divider = MenuDivider(*args, **kwargs)
+ self.items.append(divider)
+
+ return divider
+
+ def add_handler(self, handler, title=None, **kwargs):
+ """
+ Automatically adds a handler to the menu
+ """
+ title = title or self.locale.translate(handler.title)
+
+ return self.add_link(title=title, handler=handler,
+ url=handler.url, **kwargs)
+
+ def add_header(self, *args, **kwargs):
+ """
+ Adds a headline in the menu
+ """
+ header = MenuHeader(*args, **kwargs)
+ self.items.append(header)
+
+ return header
+
+ def add_link(self, *args, **kwargs):
+ """
+ Adds a link to the menu
+ """
+ link = MenuLink(*args, menu=self, **kwargs)
+ self.items.append(link)
+
+ return link
+
+ def add_submenu(self, *args, **kwargs):
+ """
+ Adds a submenu to the menu
+ """
+ kwargs.update({
+ "menu" : self,
+ })
+
+ submenu = SubMenu(*args, **kwargs)
+ self.items.append(submenu)
+
+ return submenu
+
+
+class Menu(MenuMixin):
+ """
+ The main menu object that creates a little menu on the side
+ """
+ def __init__(self, handler, title=None):
+ self.handler = handler
+ self.title = title
+
+ @property
+ def locale(self):
+ """
+ Shortcut to access the user's locale
+ """
+ return self.handler.locale
+
+
+
+class SubMenu(MenuItem, MenuMixin):
+ """
+ A sub menu in the side menu
+ """
+
+ type = "menu"
+
+ def __init__(self, title, menu=None):
+ self.title = title
+ self.menu = menu
+
+ @property
+ def locale(self):
+ """
+ Shortcut to access the user's locale
+ """
+ return self.menu.locale
+
+