package org.activityinfo.ui.client.page.common.nav; /* * #%L * ActivityInfo Server * %% * Copyright (C) 2009 - 2013 UNICEF * %% * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as * published by the Free Software Foundation, either version 3 of the * License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public * License along with this program. If not, see * <http://www.gnu.org/licenses/gpl-3.0.html>. * #L% */ import com.extjs.gxt.ui.client.Style.Scroll; import com.extjs.gxt.ui.client.event.*; import com.extjs.gxt.ui.client.widget.ContentPanel; import com.extjs.gxt.ui.client.widget.layout.FitLayout; import com.extjs.gxt.ui.client.widget.treepanel.TreePanel; import com.google.inject.Inject; import org.activityinfo.ui.client.AppEvents; import org.activityinfo.ui.client.EventBus; import org.activityinfo.ui.client.page.NavigationEvent; import org.activityinfo.ui.client.page.NavigationHandler; import org.activityinfo.ui.client.page.PageState; /** * UI component that provides a heirarchial list of navigation links. * <p/> * To use, you must implement * {@link org.activityinfo.ui.client.page.common.nav.Navigator}, which provides the * data for {@link com.extjs.gxt.ui.client.widget.treepanel.TreePanel} */ public class NavigationPanel extends ContentPanel { private final EventBus eventBus; private TreePanel<Link> tree; private Listener<NavigationEvent> navListener; private Listener<BaseEvent> changeListener; @Inject public NavigationPanel(final EventBus eventBus, final Navigator navigator) { this.eventBus = eventBus; this.setHeadingText(navigator.getHeading()); this.setScrollMode(Scroll.NONE); this.setLayout(new FitLayout()); tree = new LinkTreePanel(navigator, navigator.getStateId()); tree.addListener(Events.OnClick, new Listener<TreePanelEvent<Link>>() { @Override public void handleEvent(TreePanelEvent<Link> tpe) { if (tpe.getItem().getPageState() != null) { eventBus.fireEvent(new NavigationEvent(NavigationHandler.NAVIGATION_REQUESTED, tpe.getItem().getPageState())); } } }); navListener = new Listener<NavigationEvent>() { @Override public void handleEvent(NavigationEvent be) { onNavigated(be.getPlace()); } }; eventBus.addListener(NavigationHandler.NAVIGATION_AGREED, navListener); changeListener = new Listener<BaseEvent>() { @Override public void handleEvent(BaseEvent be) { tree.getStore().getLoader().load(); } }; eventBus.addListener(AppEvents.SCHEMA_CHANGED, changeListener); this.add(tree); } public void shutdown() { eventBus.removeListener(NavigationHandler.NAVIGATION_AGREED, navListener); eventBus.removeListener(AppEvents.SCHEMA_CHANGED, changeListener); } private void onNavigated(PageState place) { for (Link link : tree.getStore().getAllItems()) { if (link.getPageState() != null && link.getPageState().equals(place)) { showLink(link); } } } private void showLink(final Link link) { if (tree.isRendered()) { doExpandParents(link); } else { tree.addListener(Events.Render, new Listener<ComponentEvent>() { @Override public void handleEvent(ComponentEvent be) { doExpandParents(link); tree.removeListener(Events.Render, this); } }); } } private void doExpandParents(Link link) { Link parent = tree.getStore().getParent(link); tree.getSelectionModel().select(link, false); while (parent != null) { tree.setExpanded(parent, true); parent = tree.getStore().getParent(parent); } } }