Olá, pessoal!
Nesse tutorial vou mostrar uma solução que encontrei para criar um menu dinâmico infinito multinível.
Primeiramente vamos criar a classe Menu:
public class Menu {
private Long id;
private String nome; //Rótulo do menu.
private String navegacao; //Nome da navegação cadastrada no faces-config.xml
private Menu menuSuperior; //Elemento pai do menu caso haja.
private TipoMenu tipoMenu;
public Menu getMenuSuperior() {
return menuSuperior;
}
public TipoMenu getTipoMenu() {
if (tipoMenu == null){
tipoMenu = TipoMenu.ITEM;
}
return tipoMenu;
}
public String getNome() {
return nome;
}
public String getNavegacao() {
return navegacao;
}
public void setNome(String nome) {
this.nome = nome;
}
public void setNavegacao(String navegacao) {
this.navegacao = navegacao;
}
public void setMenuSuperior(Menu menuSuperior) {
this.menuSuperior = menuSuperior;
}
public void setTipoMenu(TipoMenu tipoMenu) {
this.tipoMenu = tipoMenu;
}
public Long getId() {
return id;
}
public void setId(Long id) {
this.id = id;
}
}
A classe TipoMenu é um enumerador:
public enum TipoMenu {
DROP_DOWN,
GROUP,
ITEM;
}
Realizando o controle:
public class MenuControle {
private HtmlToolBar htmlToolBar;
private int countId = 1;
@SuppressWarnings("unchecked")
public HtmlToolBar getHtmlToolBar(){
if (htmlToolBar == null){
try{
ArrayList<Menu> itens = (ArrayList<Menu>) getMenuDAO().listar(Menu.class); //UTILIZAR SEU MÉTODO DE LISTAGEM.
FacesContext context = FacesContext.getCurrentInstance();
htmlToolBar = (HtmlToolBar) context.getApplication().createComponent(HtmlToolBar.COMPONENT_TYPE);
htmlToolBar.setId("myToolBar" + countId++);
//BOTÃO SAIR
HtmlToolBarGroup htmlToolBarGroup = (HtmlToolBarGroup) context.getApplication().createComponent(HtmlToolBarGroup.COMPONENT_TYPE);
htmlToolBarGroup.setLocation("right");
htmlToolBarGroup.setId("myToolBarGroup" + countId++);
HtmlMenuItem menu = (HtmlMenuItem) context.getApplication().createComponent(HtmlMenuItem.COMPONENT_TYPE);
menu.setValue("Sair");
menu.setSubmitMode("ajax");
MethodExpression action = context.getApplication().getExpressionFactory().createMethodExpression(context.getELContext(), "#{menuControle.logout}", String.class, new Class[]{});
menu.setActionExpression(action);
htmlToolBarGroup.getChildren().add(menu);
htmlToolBar.getChildren().add(htmlToolBarGroup);
if (itens == null || itens.isEmpty()){
return htmlToolBar;
}
Map<Long, Map<Long, Menu>> menuTotal = new HashMap<Long, Map<Long, Menu>>();
for (Menu item : itens) {
Long idPai = item.getMenuSuperior() == null ? 0L : item.getMenuSuperior().getId();
if (!menuTotal.containsKey(idPai)){
menuTotal.put(idPai, new HashMap<Long, Menu>());
}
menuTotal.get(idPai).put(item.getId(), item);
}
montaMenu(context, htmlToolBar, menuTotal, 0L);
}catch (Exception e) {
e.printStackTrace();
}
}
return htmlToolBar;
}
public static void montaMenu(FacesContext context, UIComponent pai, Map<Long, Map<Long, Menu>> menuTotal, Long idPai){
Iterator<Long> it = menuTotal.get(idPai).keySet().iterator();
while (it.hasNext()) {
Long key = it.next();
Menu item = menuTotal.get(idPai).get(key);
UIComponent novoPai = null;
switch (item.getTipoMenu()) {
case DROP_DOWN:
HtmlDropDownMenu menuAdm = (HtmlDropDownMenu) context.getApplication().createComponent(HtmlDropDownMenu.COMPONENT_TYPE);
menuAdm.setValue(item.getNome());
pai.getChildren().add(menuAdm);
novoPai = menuAdm;
break;
case GROUP:
HtmlMenuGroup group = (HtmlMenuGroup) context.getApplication().createComponent(HtmlMenuGroup.COMPONENT_TYPE);
group.setValue(item.getNome());
pai.getChildren().add(group);
novoPai = group;
break;
case ITEM:
HtmlMenuItem menu = (HtmlMenuItem) context.getApplication().createComponent(HtmlMenuItem.COMPONENT_TYPE);
menu.setValue(item.getNome());
menu.setSubmitMode("ajax");
MethodExpression action = context.getApplication().getExpressionFactory().createMethodExpression(context.getELContext(), item.getNavegacao(), null, new Class<?>[0]);
menu.setActionExpression(action);
pai.getChildren().add(menu);
break;
}
if (menuTotal.containsKey(key)){
montaMenu(context, novoPai, menuTotal, key);
}
}
}
public String logout(){
//TODO SEU MÉTODO DE SAÍDA.
return "login";
}
public void setHtmlToolBar(HtmlToolBar htmlToolBar) {
this.htmlToolBar = htmlToolBar;
}
}
Agora basta inserir o menu no jsp:
<rich:toolBar binding="#{menuControle.htmlToolBar}"></rich:toolBar>
Não se esqueça de cadastrar a navegação no faces-config.xml.
Valew, galera!
Abraços!!!