http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/config/ServiceDescriptionConfigUIFactory.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/config/ServiceDescriptionConfigUIFactory.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/config/ServiceDescriptionConfigUIFactory.java deleted file mode 100644 index 8746b54..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/config/ServiceDescriptionConfigUIFactory.java +++ /dev/null @@ -1,57 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.config; - -import javax.swing.JPanel; - -import uk.org.taverna.configuration.Configurable; -import uk.org.taverna.configuration.ConfigurationUIFactory; - -import net.sf.taverna.t2.servicedescriptions.ServiceDescriptionRegistry; -import net.sf.taverna.t2.servicedescriptions.ServiceDescriptionsConfiguration; - -public class ServiceDescriptionConfigUIFactory implements ConfigurationUIFactory { - private ServiceDescriptionsConfiguration serviceDescriptionsConfiguration; - private ServiceDescriptionRegistry serviceDescriptionRegistry; - - @Override - public boolean canHandle(String uuid) { - return uuid.equals(serviceDescriptionsConfiguration.getUUID()); - } - - @Override - public Configurable getConfigurable() { - return serviceDescriptionsConfiguration; - } - - @Override - public JPanel getConfigurationPanel() { - return new ServiceDescriptionConfigPanel(serviceDescriptionsConfiguration, serviceDescriptionRegistry); - } - - public void setServiceDescriptionRegistry(ServiceDescriptionRegistry serviceDescriptionRegistry) { - this.serviceDescriptionRegistry = serviceDescriptionRegistry; - } - - public void setServiceDescriptionsConfiguration(ServiceDescriptionsConfiguration serviceDescriptionsConfiguration) { - this.serviceDescriptionsConfiguration = serviceDescriptionsConfiguration; - } -}
http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/menu/AddServiceProviderMenu.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/menu/AddServiceProviderMenu.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/menu/AddServiceProviderMenu.java deleted file mode 100644 index f975778..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/menu/AddServiceProviderMenu.java +++ /dev/null @@ -1,113 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.menu; - -import java.awt.Component; -import java.awt.event.ActionEvent; -import java.util.ArrayList; -import java.util.Collections; -import java.util.Comparator; -import java.util.List; - -import javax.swing.AbstractAction; -import javax.swing.JButton; -import javax.swing.JPopupMenu; - -import net.sf.taverna.t2.servicedescriptions.ConfigurableServiceProvider; -import net.sf.taverna.t2.servicedescriptions.ServiceDescription; -import net.sf.taverna.t2.servicedescriptions.ServiceDescriptionProvider; -import net.sf.taverna.t2.servicedescriptions.ServiceDescriptionRegistry; -import net.sf.taverna.t2.workbench.ui.servicepanel.ServicePanel; -import net.sf.taverna.t2.workbench.ui.servicepanel.actions.AddServiceProviderAction; - -/** - * A menu that provides a set up menu actions for adding new service providers - * to the Service Panel. - * <p> - * The Actions are discovered from the {@link ServiceDescriptionProvider}s found - * through the SPI. - * - * @author Stuart Owen - * @author Stian Soiland-Reyes - * @author Alan R Williams - * - * @see ServiceDescription - * @see ServicePanel - * @see ServiceDescriptionRegistry#addServiceDescriptionProvider(ServiceDescriptionProvider) - */ -@SuppressWarnings("serial") -public class AddServiceProviderMenu extends JButton { - public static class ServiceProviderComparator implements - Comparator<ServiceDescriptionProvider> { - @Override - public int compare(ServiceDescriptionProvider o1, - ServiceDescriptionProvider o2) { - return o1.getName().toLowerCase().compareTo( - o2.getName().toLowerCase()); - } - } - - private final static String ADD_SERVICE_PROVIDER_MENU_NAME = "Import new services"; - - private final ServiceDescriptionRegistry serviceDescriptionRegistry; - - public AddServiceProviderMenu(ServiceDescriptionRegistry serviceDescriptionRegistry) { - super(); - this.serviceDescriptionRegistry = serviceDescriptionRegistry; - - final Component c = createCustomComponent(); - setAction(new AbstractAction(ADD_SERVICE_PROVIDER_MENU_NAME) { - @Override - public void actionPerformed(ActionEvent e) { - ((JPopupMenu) c).show(AddServiceProviderMenu.this, 0, - AddServiceProviderMenu.this.getHeight()); - } - }); - } - - private Component createCustomComponent() { - JPopupMenu addServiceMenu = new JPopupMenu( - ADD_SERVICE_PROVIDER_MENU_NAME); - addServiceMenu.setToolTipText("Add a new service provider"); - boolean isEmpty = true; - List<ConfigurableServiceProvider> providers = new ArrayList<>( - serviceDescriptionRegistry.getUnconfiguredServiceProviders()); - Collections.sort(providers, new ServiceProviderComparator()); - for (ConfigurableServiceProvider provider : providers) { - /* - * Skip BioCatalogue's ConfigurableServiceProviderS as they should - * not be used to add servcie directlry but rather though the - * Service Catalogue perspective - */ - if (provider.getId().toLowerCase().contains("servicecatalogue")) - continue; - - AddServiceProviderAction addAction = new AddServiceProviderAction( - provider, this); - addAction.setServiceDescriptionRegistry(serviceDescriptionRegistry); - addServiceMenu.add(addAction); - isEmpty = false; - } - if (isEmpty) - addServiceMenu.setEnabled(false); - return addServiceMenu; - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/Filter.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/Filter.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/Filter.java deleted file mode 100644 index e67e8f5..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/Filter.java +++ /dev/null @@ -1,33 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import javax.swing.tree.DefaultMutableTreeNode; - -public interface Filter { - boolean pass(DefaultMutableTreeNode node); - - String filterRepresentation(String original); - - void setSuperseded(boolean superseded); - - boolean isSuperseded(); -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeCellRenderer.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeCellRenderer.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeCellRenderer.java deleted file mode 100644 index 21f43c5..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeCellRenderer.java +++ /dev/null @@ -1,59 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import static net.sf.taverna.t2.workbench.icons.WorkbenchIcons.folderClosedIcon; -import static net.sf.taverna.t2.workbench.icons.WorkbenchIcons.folderOpenIcon; - -import java.awt.Component; - -import javax.swing.JTree; -import javax.swing.tree.DefaultTreeCellRenderer; - -@SuppressWarnings("serial") -public class FilterTreeCellRenderer extends DefaultTreeCellRenderer { - private Filter filter = null; - - @Override - public Component getTreeCellRendererComponent(JTree tree, Object value, - boolean sel, boolean expanded, boolean leaf, int row, - boolean hasFocus) { - - super.getTreeCellRendererComponent(tree, value, sel, expanded, leaf, - row, hasFocus); - Filter filter = getFilter(); - if (filter != null) - setText(filter.filterRepresentation(getText())); - if (expanded) - setIcon(folderOpenIcon); - else - setIcon(folderClosedIcon); - return this; - } - - public Filter getFilter() { - return filter; - } - - public void setFilter(Filter currentFilter) { - this.filter = currentFilter; - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeModel.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeModel.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeModel.java deleted file mode 100644 index 191ed66..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeModel.java +++ /dev/null @@ -1,92 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import java.util.ArrayList; -import java.util.List; - -import javax.swing.tree.DefaultTreeModel; -import javax.swing.tree.TreePath; - -import org.apache.log4j.Logger; - -public final class FilterTreeModel extends DefaultTreeModel { - private static final long serialVersionUID = -8931308369832839862L; - private static final Logger logger = Logger - .getLogger(FilterTreeModel.class); - - Filter currentFilter; - - public FilterTreeModel(FilterTreeNode node) { - this(node, null); - } - - public FilterTreeModel(FilterTreeNode node, Filter filter) { - super(node); - currentFilter = filter; - node.setFilter(filter); - } - - public void setFilter(Filter filter) { - if (root != null) { - currentFilter = filter; - ((FilterTreeNode) root).setFilter(filter); - Object[] path = { root }; - fireTreeStructureChanged(this, path, null, null); - } - } - - @Override - public int getChildCount(Object parent) { - if (parent instanceof FilterTreeNode) - return (((FilterTreeNode) parent).getChildCount()); - return 0; - } - - @Override - public Object getChild(Object parent, int index) { - if (parent instanceof FilterTreeNode) - return (((FilterTreeNode) parent).getChildAt(index)); - return null; - } - - /** - * @return the currentFilter - */ - public Filter getCurrentFilter() { - return currentFilter; - } - - public TreePath getTreePathForObjectPath(List<Object> path) { - List<FilterTreeNode> resultList = new ArrayList<>(); - FilterTreeNode current = (FilterTreeNode) root; - resultList.add(current); - for (int i = 1; (i < path.size()) && (current != null); i++) { - logger.debug("Looking in " + current.getUserObject() + " for " + path.get(i)); - current = current.getChildForObject(path.get(i)); - if (current != null) - resultList.add(current); - } - if (current != null) - return new TreePath(resultList.toArray()); - return null; - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeNode.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeNode.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeNode.java deleted file mode 100644 index 83fd439..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeNode.java +++ /dev/null @@ -1,142 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import java.util.ArrayList; -import java.util.HashSet; -import java.util.List; -import java.util.Set; - -import javax.swing.tree.DefaultMutableTreeNode; - -import org.apache.log4j.Logger; - -public class FilterTreeNode extends DefaultMutableTreeNode { - private static final long serialVersionUID = 1933553584349932151L; - @SuppressWarnings("unused") - private static Logger logger = Logger.getLogger(FilterTreeNode.class); - - private Filter filter; - private boolean passed = true; - private List<FilterTreeNode> filteredChildren = new ArrayList<>(); - - public FilterTreeNode(Object userObject) { - super(userObject); - userObject.toString(); - } - - public Filter getFilter() { - return filter; - } - - public void setFilter(Filter filter) { - if ((filter == null) || !filter.isSuperseded()) { - this.filter = filter; - passed = false; - filteredChildren.clear(); - if (filter == null) { - passed = true; - passFilterDown(null); - } else if (filter.pass(this)) { - passed = true; - passFilterDown(null); - } else { - passFilterDown(filter); - passed = filteredChildren.size() != 0; - } - } - } - - private void passFilterDown(Filter filter) { - int realChildCount = super.getChildCount(); - for (int i = 0; i < realChildCount; i++) { - FilterTreeNode realChild = (FilterTreeNode) super.getChildAt(i); - realChild.setFilter(filter); - if (realChild.isPassed()) - filteredChildren.add(realChild); - } - } - - public void add(FilterTreeNode node) { - super.add(node); - node.setFilter(filter); - // TODO work up - if (node.isPassed()) - filteredChildren.add(node); - } - - @Override - public void remove(int childIndex) { - if (filter != null) - // as child indexes might be inconsistent.. - throw new IllegalStateException("Can't remove while the filter is active"); - super.remove(childIndex); - } - - @Override - public int getChildCount() { - if (filter == null) - return super.getChildCount(); - return filteredChildren.size(); - } - - @Override - public FilterTreeNode getChildAt(int index) { - if (filter == null) - return (FilterTreeNode) super.getChildAt(index); - return filteredChildren.get(index); - } - - public boolean isPassed() { - return passed; - } - - public Set<FilterTreeNode> getLeaves() { - Set<FilterTreeNode> result = new HashSet<>(); - if (super.getChildCount() == 0) { - result.add(this); - return result; - } - - for (int i = 0; i < super.getChildCount(); i++) { - FilterTreeNode child = (FilterTreeNode) super.getChildAt(i); - result.addAll(child.getLeaves()); - } - return result; - } - - public FilterTreeNode getChildForObject(Object userObject) { - FilterTreeNode result = null; - for (int i=0; (i < super.getChildCount()) && (result == null); i++) { - FilterTreeNode child = (FilterTreeNode) super.getChildAt(i); - Object nodeObject = child.getUserObject(); -// logger.info("nodeObject is a " + nodeObject.getClass() + " - " + -// "userObject is a " + userObject.getClass()); - if (nodeObject.toString().equals(userObject.toString())) { - result = child; -// logger.info(nodeObject + " is equal to " + userObject); -// } else { -// logger.info(nodeObject + " is not equal to " + userObject); - } - } - return result; - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeSelectionModel.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeSelectionModel.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeSelectionModel.java deleted file mode 100644 index a5adfe9..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/FilterTreeSelectionModel.java +++ /dev/null @@ -1,46 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import javax.swing.tree.DefaultTreeSelectionModel; -import javax.swing.tree.TreePath; -import javax.swing.tree.TreeSelectionModel; - -public class FilterTreeSelectionModel extends DefaultTreeSelectionModel{ - private static final long serialVersionUID = 3127644524735089630L; - - public FilterTreeSelectionModel(){ - super(); - setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION); - } - - @Override - public void setSelectionPath(TreePath path) { - /* - * Nothing happens here - only calls to mySetSelectionPath() will have - * the effect of a node being selected. - */ - } - - public void mySetSelectionPath(TreePath path) { - super.setSelectionPath(path); - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/MyFilter.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/MyFilter.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/MyFilter.java deleted file mode 100644 index 8baa0eb..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/MyFilter.java +++ /dev/null @@ -1,89 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import javax.swing.tree.DefaultMutableTreeNode; - -public class MyFilter implements Filter { - private static final String HTML_MATCH_END = "</font><font color=\"black\">"; - private static final String HTML_MATCH_START = "</font><font color=\"red\">"; - private static final String HTML_POSTFIX = "</font></html>"; - private static final String HTML_PREFIX = "<html><font color=\"black\">"; - - private String filterString; - private boolean superseded; - private String filterLowerCase; - - public MyFilter(String filterString) { - this.filterString = filterString; - this.filterLowerCase = filterString.toLowerCase(); - this.superseded = false; - } - - private boolean basicFilter(DefaultMutableTreeNode node) { - if (filterString.isEmpty()) - return true; - return node.getUserObject().toString().toLowerCase() - .contains(filterLowerCase); - } - - @Override - public boolean pass(DefaultMutableTreeNode node) { - return basicFilter(node); - } - - @Override - public String filterRepresentation(String original) { - StringBuilder sb = new StringBuilder(HTML_PREFIX); - int from = 0; - String originalLowerCase = original.toLowerCase(); - int index = originalLowerCase.indexOf(filterLowerCase, from); - while (index > -1) { - sb.append(original.substring(from, index)); - sb.append(HTML_MATCH_START); - sb.append(original.substring(index, - index + filterLowerCase.length())); - sb.append(HTML_MATCH_END); - from = index + filterLowerCase.length(); - index = originalLowerCase.indexOf(filterLowerCase, from); - } - if (from < original.length()) - sb.append(original.substring(from, original.length())); - return sb.append(HTML_POSTFIX).toString(); - } - - /** - * @return the superseded - */ - @Override - public boolean isSuperseded() { - return superseded; - } - - /** - * @param superseded - * the superseded to set - */ - @Override - public void setSuperseded(boolean superseded) { - this.superseded = superseded; - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/TreePanel.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/TreePanel.java b/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/TreePanel.java deleted file mode 100644 index 46eca53..0000000 --- a/taverna-activity-palette-ui/src/main/java/net/sf/taverna/t2/workbench/ui/servicepanel/tree/TreePanel.java +++ /dev/null @@ -1,371 +0,0 @@ -/******************************************************************************* - * Copyright (C) 2007-2009 The University of Manchester - * - * Modifications to the initial code base are copyright of their - * respective authors, or their employers as appropriate. - * - * This program is free software; you can redistribute it and/or - * modify it under the terms of the GNU Lesser General Public License - * as published by the Free Software Foundation; either version 2.1 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 - * Lesser General Public License for more details. - * - * You should have received a copy of the GNU Lesser General Public - * License along with this program; if not, write to the Free Software - * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 - ******************************************************************************/ -package net.sf.taverna.t2.workbench.ui.servicepanel.tree; - -import static java.awt.BorderLayout.CENTER; -import static java.awt.BorderLayout.NORTH; -import static java.awt.BorderLayout.WEST; -import static java.awt.Color.GRAY; -import static java.awt.GridBagConstraints.HORIZONTAL; -import static java.awt.GridBagConstraints.NONE; -import static javax.swing.SwingUtilities.invokeLater; -import static net.sf.taverna.t2.lang.ui.EdgeLineBorder.TOP; - -import java.awt.BorderLayout; -import java.awt.Component; -import java.awt.GridBagConstraints; -import java.awt.GridBagLayout; -import java.awt.event.ActionEvent; -import java.awt.event.ActionListener; -import java.awt.event.KeyAdapter; -import java.awt.event.KeyEvent; -import java.lang.reflect.InvocationTargetException; -import java.util.ArrayList; -import java.util.Enumeration; -import java.util.HashSet; -import java.util.List; -import java.util.Set; -import java.util.Timer; -import java.util.TimerTask; - -import javax.swing.JButton; -import javax.swing.JLabel; -import javax.swing.JPanel; -import javax.swing.JScrollPane; -import javax.swing.JTextField; -import javax.swing.JTree; -import javax.swing.border.CompoundBorder; -import javax.swing.border.EmptyBorder; -import javax.swing.event.TreeExpansionEvent; -import javax.swing.event.TreeExpansionListener; -import javax.swing.tree.TreeCellRenderer; -import javax.swing.tree.TreePath; - -import net.sf.taverna.t2.lang.ui.EdgeLineBorder; - -import org.apache.log4j.Logger; - -@SuppressWarnings("serial") -public abstract class TreePanel extends JPanel { - private static int MAX_EXPANSION = 100; - private static final int SEARCH_WIDTH = 15; - private static Logger logger = Logger.getLogger(TreePanel.class); - - protected Set<List<Object>> expandedPaths = new HashSet<>(); - protected FilterTreeModel filterTreeModel; - protected JTextField searchField = new JTextField(SEARCH_WIDTH); - protected JTree tree = new JTree(); - protected JScrollPane treeScrollPane; - - private String availableObjectsString = ""; - private String matchingObjectsString = ""; - private String noMatchingObjectsString = ""; - - private TreeExpandCollapseListener treeExpandListener = new TreeExpandCollapseListener(); - private Object filterLock = new Object(); - - public TreePanel(FilterTreeModel treeModel) { - filterTreeModel = treeModel; - } - - public void expandTreePaths() throws InterruptedException, - InvocationTargetException { -// Filter appliedFilter = filterTreeModel.getCurrentFilter(); -// if (appliedFilter == null) { - for (int i = 0; (i < tree.getRowCount()) && (i < MAX_EXPANSION); i++) - tree.expandRow(i); -// } else { -// boolean rowsFinished = false; -// for (int i = 0; (!appliedFilter.isSuperseded()) && (!rowsFinished) -// && (i < MAX_EXPANSION); i++) { -// TreePath tp = tree.getPathForRow(i); -// if (tp == null) { -// rowsFinished = true; -// } else { -// if (!appliedFilter.pass((DefaultMutableTreeNode) tp -// .getLastPathComponent())) { -// tree.expandRow(i); -// } -// } -// } -// } - } - - public void expandAll(FilterTreeNode node, boolean expand) { - @SuppressWarnings("unused") - FilterTreeNode root = (FilterTreeNode) tree.getModel().getRoot(); - - // Traverse tree from root - expandAll(new TreePath(node.getPath()), expand); - } - - @SuppressWarnings("rawtypes") - private void expandAll(TreePath parent, boolean expand) { - // Traverse children - FilterTreeNode node = (FilterTreeNode) parent.getLastPathComponent(); - if (node.getChildCount() >= 0) - for (Enumeration e=node.children(); e.hasMoreElements(); ) { - FilterTreeNode n = (FilterTreeNode) e.nextElement(); - TreePath path = parent.pathByAddingChild(n); - expandAll(path, expand); - } - - // Expansion or collapse must be done bottom-up - if (expand) - tree.expandPath(parent); - else - tree.collapsePath(parent); - } - - protected void initialize() { - setLayout(new BorderLayout()); - treeScrollPane = new JScrollPane(tree); - tree.setModel(filterTreeModel); - tree.addTreeExpansionListener(treeExpandListener); - tree.setCellRenderer(createCellRenderer()); - tree.setSelectionModel(new FilterTreeSelectionModel()); - - JPanel topPanel = new JPanel(); - topPanel.setBorder(new CompoundBorder(new EdgeLineBorder(TOP, GRAY), new EmptyBorder(10, 5, 0, 5))); - topPanel.setLayout(new GridBagLayout()); - GridBagConstraints c = new GridBagConstraints(); - - JLabel filterLabel = new JLabel("Filter: "); - c.fill = NONE; - c.gridx = 0; - c.gridy = 0; - c.weightx = 0.0; - c.anchor = GridBagConstraints.LINE_START; - topPanel.add(filterLabel, c); - - c.fill = HORIZONTAL; - c.gridx = 1; - c.gridy = 0; - c.weightx = 1.0; - topPanel.add(searchField, c); - - - c.fill = NONE; - c.gridx = 2; - c.gridy = 0; - c.weightx = 0.0; - final JButton clearButton = new JButton("Clear"); - clearButton.addActionListener(new ActionListener() { - @Override - public void actionPerformed(ActionEvent e) { - searchField.setText(""); - invokeLater(new RunFilter()); - clearButton.getParent().requestFocusInWindow();// so that the button does not stay focused after it is clicked on and did its action - } - }); - topPanel.add(clearButton, c); - - c.gridx = 3; - c.weightx = 0.2; - topPanel.add(new JPanel(), c); - - JPanel topExtraPanel = new JPanel(new BorderLayout()); - - topExtraPanel.add(topPanel, NORTH); - - Component extraComponent = createExtraComponent(); - if (extraComponent != null) { - JPanel extraPanel = new JPanel(); - extraPanel.setLayout(new BorderLayout()); - extraPanel.add(extraComponent, WEST); - topExtraPanel.add(extraPanel, CENTER); - } - - add(topExtraPanel, NORTH); - add(treeScrollPane, CENTER); - - searchField.addKeyListener(new SearchFieldKeyAdapter()); - } - - protected Component createExtraComponent() { - return null; - } - - protected TreeCellRenderer createCellRenderer() { - return new FilterTreeCellRenderer(); - } - - public void runFilter() throws InterruptedException, - InvocationTargetException { - /* - * Special lock object, don't do a synchronized model, as the lock on - * JComponent might deadlock when painting the panel - see comments at - * http://www.mygrid.org.uk/dev/issues/browse/T2-1438 - */ - synchronized (filterLock) { - tree.removeTreeExpansionListener(treeExpandListener); - String text = searchField.getText(); - FilterTreeNode root = (FilterTreeNode) tree.getModel().getRoot(); - if (text.isEmpty()) { - setFilter(null); - root.setUserObject(getAvailableObjectsString()); - filterTreeModel.nodeChanged(root); - for (List<Object> tp : expandedPaths) { - // for (int i = 0; i < tp.length; i++) - // logger.info("Trying to expand " + tp[i]); - tree.expandPath(filterTreeModel.getTreePathForObjectPath(tp)); - } - } else { - setFilter(createFilter(text)); - root.setUserObject(root.getChildCount() > 0 ? getMatchingObjectsString() - : getNoMatchingObjectsString()); - filterTreeModel.nodeChanged(root); - expandTreePaths(); - } - tree.addTreeExpansionListener(treeExpandListener); - } - } - - /** - * @return the availableObjectsString - */ - public String getAvailableObjectsString() { - return availableObjectsString; - } - - /** - * @param availableObjectsString the availableObjectsString to set - */ - public void setAvailableObjectsString(String availableObjectsString) { - this.availableObjectsString = availableObjectsString; - } - - /** - * @return the matchingObjectsString - */ - public String getMatchingObjectsString() { - return matchingObjectsString; - } - - /** - * @param matchingObjectsString the matchingObjectsString to set - */ - public void setMatchingObjectsString(String matchingObjectsString) { - this.matchingObjectsString = matchingObjectsString; - } - - /** - * @return the noMatchingObjectsString - */ - public String getNoMatchingObjectsString() { - return noMatchingObjectsString; - } - - /** - * @param noMatchingObjectsString the noMatchingObjectsString to set - */ - public void setNoMatchingObjectsString(String noMatchingObjectsString) { - this.noMatchingObjectsString = noMatchingObjectsString; - } - - public Filter createFilter(String text) { - return new MyFilter(text); - } - - public void setFilter(Filter filter) { - if (tree.getCellRenderer() instanceof FilterTreeCellRenderer) - ((FilterTreeCellRenderer)tree.getCellRenderer()).setFilter(filter); - filterTreeModel.setFilter(filter); - } - - protected class ExpandRowRunnable implements Runnable { - int rowNumber; - - public ExpandRowRunnable(int rowNumber) { - this.rowNumber = rowNumber; - } - - @Override - public void run() { - tree.expandRow(rowNumber); - } - } - - protected class RunFilter implements Runnable { - @Override - public void run() { - Filter oldFilter = filterTreeModel.getCurrentFilter(); - if (oldFilter != null) - oldFilter.setSuperseded(true); - try { - runFilter(); - } catch (InterruptedException e) { - Thread.interrupted(); - } catch (InvocationTargetException e) { - logger.error("", e); - } - } - } - - protected class SearchFieldKeyAdapter extends KeyAdapter { - private final Runnable runFilterRunnable; - Timer timer = new Timer("Search field timer", true); - - private SearchFieldKeyAdapter() { - this.runFilterRunnable = new RunFilter(); - } - - @Override - public void keyReleased(KeyEvent e) { - timer.cancel(); - timer = new Timer(); - timer.schedule(new TimerTask() { - @Override - public void run() { - invokeLater(runFilterRunnable); - } - }, 500); - } - } - - private void noteExpansions() { - expandedPaths.clear(); - TreePath rootPath = new TreePath(filterTreeModel.getRoot()); - for (Enumeration<TreePath> e = tree.getExpandedDescendants(rootPath); e.hasMoreElements();) { - List<Object> userObjects = new ArrayList<>(); - Object[] expandedPath = e.nextElement().getPath(); - for (int i = 0; i < expandedPath.length; i++) { - FilterTreeNode node = (FilterTreeNode) expandedPath[i]; -// logger.info("The object in the path is a " + expandedPath[i].getClass()); - userObjects.add(node.getUserObject()); -// logger.info("Added " + node.getUserObject() + " to path"); - } - expandedPaths.add(userObjects); - } - } - - protected class TreeExpandCollapseListener implements TreeExpansionListener { - @Override - public void treeCollapsed(TreeExpansionEvent event) { - noteExpansions(); - } - - @Override - public void treeExpanded(TreeExpansionEvent event) { - noteExpansions(); - } - } -} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/PathElementFilterTreeNode.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/PathElementFilterTreeNode.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/PathElementFilterTreeNode.java new file mode 100644 index 0000000..8a4a247 --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/PathElementFilterTreeNode.java @@ -0,0 +1,33 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; + +/** + * @author alanrw + */ +public class PathElementFilterTreeNode extends FilterTreeNode { + private static final long serialVersionUID = 6491242031931630314L; + + public PathElementFilterTreeNode(String userObject) { + super(userObject); + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/RootFilterTreeNode.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/RootFilterTreeNode.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/RootFilterTreeNode.java new file mode 100644 index 0000000..8ae210e --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/RootFilterTreeNode.java @@ -0,0 +1,33 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; + +/** + * @author alanrw + */ +public class RootFilterTreeNode extends FilterTreeNode { + private static final long serialVersionUID = 1047743498806473971L; + + public RootFilterTreeNode(String userObject) { + super(userObject); + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilter.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilter.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilter.java new file mode 100644 index 0000000..c4dd75a --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilter.java @@ -0,0 +1,157 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import static java.beans.Introspector.getBeanInfo; + +import java.beans.BeanInfo; +import java.beans.IntrospectionException; +import java.beans.PropertyDescriptor; +import java.lang.reflect.InvocationTargetException; +import java.lang.reflect.Method; + +import javax.swing.tree.DefaultMutableTreeNode; + +import org.apache.taverna.servicedescriptions.ServiceDescription; +import org.apache.taverna.workbench.ui.servicepanel.tree.Filter; + +import org.apache.log4j.Logger; + +public class ServiceFilter implements Filter { + private static Logger logger = Logger.getLogger(ServiceFilter.class); + + private String filterString; + private boolean superseded; + private String[] filterLowerCaseSplit; + private final Object rootToIgnore; + + public ServiceFilter(String filterString, Object rootToIgnore) { + this.filterString = filterString; + this.rootToIgnore = rootToIgnore; + this.filterLowerCaseSplit = filterString.toLowerCase().split(" "); + this.superseded = false; + } + + private boolean basicFilter(DefaultMutableTreeNode node) { + if (node == rootToIgnore) + return false; + if (filterString.isEmpty()) + return true; + + if (node.getUserObject() instanceof ServiceDescription) { + ServiceDescription serviceDescription = (ServiceDescription) node + .getUserObject(); + for (String searchTerm : filterLowerCaseSplit) { + if (superseded) + return false; + String[] typeSplit = searchTerm.split(":", 2); + String type; + String keyword; + if (typeSplit.length == 2) { + type = typeSplit[0]; + keyword = typeSplit[1].toLowerCase(); + } else { + type = null; + keyword = searchTerm.toLowerCase(); + } + try { + if (!doesPropertySatisfy(serviceDescription, type, keyword)) + return false; + } catch (IntrospectionException | IllegalArgumentException + | IllegalAccessException | InvocationTargetException e) { + logger.error( + "failed to get properties of service description", + e); + return false; + } + } + return true; + } + for (String searchString : filterLowerCaseSplit) + if (!node.getUserObject().toString().toLowerCase().contains( + searchString)) + return false; + return true; + } + + /** + * Determine whether a service description satisfies a search term. + * + * @param serviceDescription + * The service description bean to look in. + * @param type + * The name of the property to look in, or <tt>null</tt> to + * search in all public non-expert properties. + * @param searchTerm + * The string to search for. + * @return <tt>true</tt> if-and-only-if the description matches. + */ + private boolean doesPropertySatisfy(ServiceDescription serviceDescription, + String type, String searchTerm) throws IllegalAccessException, + IllegalArgumentException, InvocationTargetException, + IntrospectionException { + BeanInfo beanInfo = getBeanInfo(serviceDescription.getClass()); + for (PropertyDescriptor property : beanInfo.getPropertyDescriptors()) { + if (superseded) + return false; + if ((type == null && !property.isHidden() && !property.isExpert()) + || property.getName().equalsIgnoreCase(type)) { + Method readMethod = property.getReadMethod(); + if (readMethod == null) + continue; + Object readProperty = readMethod.invoke(serviceDescription, + new Object[0]); + if (readProperty == null) + continue; + if (readProperty.toString().toLowerCase().contains(searchTerm)) + return true; + // Dig deeper? + } + } + return false; + } + + @Override + public boolean pass(DefaultMutableTreeNode node) { + return basicFilter(node); + } + + @Override + public String filterRepresentation(String original) { + return original; + } + + /** + * @return the superseded + */ + @Override + public boolean isSuperseded() { + return superseded; + } + + /** + * @param superseded + * the superseded to set + */ + @Override + public void setSuperseded(boolean superseded) { + this.superseded = superseded; + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilterTreeNode.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilterTreeNode.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilterTreeNode.java new file mode 100644 index 0000000..ef7811e --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceFilterTreeNode.java @@ -0,0 +1,39 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import org.apache.taverna.servicedescriptions.ServiceDescription; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; + +/** + * @author alanrw + */ +public class ServiceFilterTreeNode extends FilterTreeNode { + private static final long serialVersionUID = 6066698619971305454L; + + public ServiceFilterTreeNode(ServiceDescription userObject) { + super(userObject); + } + + @Override + public ServiceDescription getUserObject() { + return (ServiceDescription) super.getUserObject(); + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanel.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanel.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanel.java new file mode 100644 index 0000000..e95869f --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanel.java @@ -0,0 +1,410 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import static javax.swing.JOptionPane.ERROR_MESSAGE; +import static javax.swing.JOptionPane.showMessageDialog; +import static javax.swing.SwingUtilities.invokeLater; +import static org.apache.taverna.servicedescriptions.ServiceDescription.LOCAL_SERVICES; +import static org.apache.taverna.servicedescriptions.ServiceDescription.SERVICE_TEMPLATES; + +import java.awt.BorderLayout; +import java.lang.reflect.InvocationTargetException; +import java.util.Comparator; +import java.util.HashSet; +import java.util.Map; +import java.util.Set; +import java.util.Timer; +import java.util.TimerTask; +import java.util.TreeMap; +import java.util.TreeSet; + +import javax.swing.ImageIcon; +import javax.swing.JLabel; +import javax.swing.JPanel; + +import org.apache.taverna.lang.observer.Observable; +import org.apache.taverna.lang.observer.Observer; +import org.apache.taverna.servicedescriptions.ServiceDescription; +import org.apache.taverna.servicedescriptions.ServiceDescriptionProvider; +import org.apache.taverna.servicedescriptions.ServiceDescriptionRegistry; +import org.apache.taverna.servicedescriptions.events.AbstractProviderEvent; +import org.apache.taverna.servicedescriptions.events.AbstractProviderNotification; +import org.apache.taverna.servicedescriptions.events.PartialServiceDescriptionsNotification; +import org.apache.taverna.servicedescriptions.events.ProviderErrorNotification; +import org.apache.taverna.servicedescriptions.events.RemovedProviderEvent; +import org.apache.taverna.servicedescriptions.events.ServiceDescriptionProvidedEvent; +import org.apache.taverna.servicedescriptions.events.ServiceDescriptionRegistryEvent; +import org.apache.taverna.ui.menu.MenuManager; +import org.apache.taverna.workbench.edits.EditManager; +import org.apache.taverna.workbench.selection.SelectionManager; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeModel; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; +import org.apache.taverna.workbench.ui.zaria.UIComponentSPI; + +import org.apache.log4j.Logger; + +import org.apache.taverna.commons.services.ServiceRegistry; + +/** + * A panel of available services + * + * @author Stian Soiland-Reyes + */ +@SuppressWarnings("serial") +public class ServicePanel extends JPanel implements UIComponentSPI { + private static Logger logger = Logger.getLogger(ServicePanel.class); + private static final int INITIAL_BLANK_OUT_COUNTER = 2; + public static final String AVAILABLE_SERVICES = "Available services"; + public static final String MATCHING_SERVIES = "Matching services"; + public static final String NO_MATCHING_SERVICES = "No matching services"; + public static final String MOBY_OBJECTS = "MOBY Objects"; + /** + * A Comparable constant to be used with buildPathMap + */ + private static final String SERVICES = "4DA84170-7746-4817-8C2E-E29AF8B2984D"; + private static final int STATUS_LINE_MESSAGE_MS = 600; + private static ServicePathElementComparator servicePathElementComparator = new ServicePathElementComparator(); + + public int blankOutCounter = 0; + private TreeUpdaterThread updaterThread; + private RootFilterTreeNode root = new RootFilterTreeNode(AVAILABLE_SERVICES); + private ServiceTreePanel serviceTreePanel; + private JLabel statusLine; + private FilterTreeModel treeModel; + protected Timer statusUpdateTimer; + + private final ServiceDescriptionRegistry serviceDescriptionRegistry; + protected final ServiceDescriptionRegistryObserver serviceDescriptionRegistryObserver = new ServiceDescriptionRegistryObserver(); + protected final Object updateLock = new Object(); + private final EditManager editManager; + private final MenuManager menuManager; + private final SelectionManager selectionManager; + private final ServiceRegistry serviceRegistry; + + public ServicePanel(ServiceDescriptionRegistry serviceDescriptionRegistry, + EditManager editManager, MenuManager menuManager, + SelectionManager selectionManager, ServiceRegistry serviceRegistry) { + this.serviceDescriptionRegistry = serviceDescriptionRegistry; + this.editManager = editManager; + this.menuManager = menuManager; + this.selectionManager = selectionManager; + this.serviceRegistry = serviceRegistry; + serviceDescriptionRegistry.addObserver(serviceDescriptionRegistryObserver); + initialise(); + } + + @Override + public ImageIcon getIcon() { + return null; + } + + @Override + public String getName() { + return "Service panel"; + } + + @Override + public void onDisplay() { + } + + @Override + public void onDispose() { + } + + public void providerStatus(ServiceDescriptionProvider provider, String message) { + logger.info(message + " " + provider); + final String htmlMessage = "<small>" + message + " [" + provider + "]</small>"; + + invokeLater(new Runnable() { + @Override + public void run() { + blankOutCounter = INITIAL_BLANK_OUT_COUNTER; + statusLine.setText("<html>" + htmlMessage + "</html>"); + statusLine.setVisible(true); + } + }); + } + + protected void initialise() { + removeAll(); + setLayout(new BorderLayout()); + treeModel = new FilterTreeModel(root); + serviceTreePanel = new ServiceTreePanel(treeModel, serviceDescriptionRegistry, editManager, menuManager, selectionManager, serviceRegistry); + serviceTreePanel.setAvailableObjectsString(AVAILABLE_SERVICES); + serviceTreePanel.setMatchingObjectsString(MATCHING_SERVIES); + serviceTreePanel.setNoMatchingObjectsString(NO_MATCHING_SERVICES); + add(serviceTreePanel); + statusLine = new JLabel(); + add(statusLine, BorderLayout.SOUTH); + if (statusUpdateTimer != null) + statusUpdateTimer.cancel(); + statusUpdateTimer = new Timer("Clear status line", true); + statusUpdateTimer + .scheduleAtFixedRate(new UpdateStatusLineTask(), 0, STATUS_LINE_MESSAGE_MS); + updateTree(); + } + + protected void updateTree() { + synchronized (updateLock) { + if (updaterThread != null && updaterThread.isAlive()) { + return; + } + updaterThread = new TreeUpdaterThread(); + updaterThread.start(); + } + } + + protected static class ServicePathElementComparator implements Comparator<Object> { + @Override + public int compare(Object o1, Object o2) { + if ((o1 instanceof String) && (o2 instanceof String)) { + if (o1.equals(SERVICE_TEMPLATES)) + return -1; + else if (o2.equals(SERVICE_TEMPLATES)) + return 1; + if (o1.equals(LOCAL_SERVICES)) + return -1; + else if (o2.equals(LOCAL_SERVICES)) + return 1; + if (o1.equals(MOBY_OBJECTS)) + return -1; + else if (o2.equals(MOBY_OBJECTS)) + return 1; + } + return o1.toString().compareToIgnoreCase(o2.toString()); + } + } + + @SuppressWarnings({ "rawtypes", "unchecked" }) + //FIXME this class is type-disastrous! Really bad. + public class TreeUpdaterThread extends Thread { + private boolean aborting = false; + + private TreeUpdaterThread() { + super("Updating service panel"); + setDaemon(true); + } + + public void abort() { + aborting = true; + interrupt(); + } + + @Override + public void run() { + Map<Comparable, Map> pathMap = buildPathMap(); + populateChildren(root, pathMap); + invokeLater(new Runnable() { + @Override + public void run() { + try { + serviceTreePanel.runFilter(); + } catch (InterruptedException | InvocationTargetException e) { + logger.error("failed to filter", e); + } + } + }); + } + + protected Map<Comparable, Map> buildPathMap() { + Map<Comparable, Map> paths = new TreeMap<>(); + for (ServiceDescription serviceDescription : serviceDescriptionRegistry + .getServiceDescriptions()) { + if (aborting) + return paths; + Map currentPath = paths; + for (Object pathElem : serviceDescription.getPath()) { + Map pathEntry = (Map) currentPath.get(pathElem); + if (pathEntry == null) { + pathEntry = new TreeMap(); + currentPath.put(pathElem, pathEntry); + } + currentPath = pathEntry; + } + TreeMap<String, Set<ServiceDescription>> services = (TreeMap) currentPath + .get(SERVICES); + if (services == null) { + services = new TreeMap<>(); + currentPath.put(SERVICES, services); + } + String serviceDescriptionName = serviceDescription.getName(); + if (!services.containsKey(serviceDescriptionName)) { + Set<ServiceDescription> serviceSet = new HashSet<>(); + services.put(serviceDescriptionName, serviceSet); + } + services.get(serviceDescriptionName).add(serviceDescription); + } + return paths; + } + + protected void populateChildren(FilterTreeNode node, Map pathMap) { + if (aborting) + return; + if (node == root) { + // Clear top root + invokeLater(new Runnable() { + @Override + public void run() { + if (aborting) + return; + serviceTreePanel.setFilter(null); + root.removeAllChildren(); + } + }); + } + + Set<Comparable> paths = new TreeSet<>(servicePathElementComparator); + Map<String, Set<ServiceDescription>> services = (Map) pathMap + .get(SERVICES); + if (services == null) + services = new TreeMap<>(); + paths.addAll(pathMap.keySet()); + paths.addAll(services.keySet()); + + for (Comparable pathElement : paths) { + if (aborting) + return; + if (pathElement.equals(SERVICES)) + continue; + Set<FilterTreeNode> childNodes = new HashSet<>(); + if (services.containsKey(pathElement)) { + for (ServiceDescription sd : services.get(pathElement)) + childNodes.add(new ServiceFilterTreeNode(sd)); + } else + childNodes.add(new PathElementFilterTreeNode((String) pathElement)); + invokeLater(new AddNodeRunnable(node, childNodes)); + if ((pathMap.containsKey(pathElement)) && !childNodes.isEmpty()) + populateChildren(childNodes.iterator().next(), (Map) pathMap.get(pathElement)); + } + // if (!services.isEmpty()) { + // Collections.sort(services, serviceComparator); + // for (String serviceName : services.keySet()) { + // if (aborting) { + // return; + // } + // if (pathMap.containsKey(serviceName)) { + // continue; + // } + // SwingUtilities.invokeLater(new AddNodeRunnable(node, + // new ServiceFilterTreeNode(services.get(serviceName)))); + // } + // } + } + + public class AddNodeRunnable implements Runnable { + private final Set<FilterTreeNode> nodes; + private final FilterTreeNode root; + + public AddNodeRunnable(FilterTreeNode root, Set<FilterTreeNode> nodes) { + this.root = root; + this.nodes = nodes; + } + + @Override + public void run() { + if (aborting) + return; + for (FilterTreeNode n : nodes) + root.add(n); + } + } + } + + public static class RemoveNodeRunnable implements Runnable { + private final FilterTreeNode root; + + public RemoveNodeRunnable(FilterTreeNode root) { + this.root = root; + } + + @Override + public void run() { + root.removeFromParent(); + } + } + + private final class ServiceDescriptionRegistryObserver implements + Observer<ServiceDescriptionRegistryEvent> { + Set<ServiceDescriptionProvider> alreadyComplainedAbout = new HashSet<>(); + + @Override + public void notify(Observable<ServiceDescriptionRegistryEvent> sender, + ServiceDescriptionRegistryEvent message) throws Exception { + if (message instanceof ProviderErrorNotification) + reportServiceProviderError((ProviderErrorNotification) message); + else if (message instanceof ServiceDescriptionProvidedEvent + || message instanceof RemovedProviderEvent) { + AbstractProviderEvent ape = (AbstractProviderEvent) message; + alreadyComplainedAbout.remove(ape.getProvider()); + } + + if (message instanceof AbstractProviderNotification) { + AbstractProviderNotification abstractProviderNotification = (AbstractProviderNotification) message; + providerStatus(abstractProviderNotification.getProvider(), + abstractProviderNotification.getMessage()); + } + if (message instanceof PartialServiceDescriptionsNotification) + /* + * TODO: Support other events and only update relevant parts of + * tree, or at least select the recently added provider + */ + updateTree(); + else if (message instanceof RemovedProviderEvent) + updateTree(); + } + + private void reportServiceProviderError( + final ProviderErrorNotification pen) { + ServiceDescriptionProvider provider = pen.getProvider(); + if (serviceDescriptionRegistry + .getDefaultServiceDescriptionProviders().contains(provider)) + return; + if (alreadyComplainedAbout.contains(provider)) + return; + + alreadyComplainedAbout.add(provider); + invokeLater(new Runnable() { + @Override + public void run() { + showMessageDialog(ServicePanel.this, pen.getMessage() + + "\n" + pen.getProvider(), "Import service error", + ERROR_MESSAGE); + } + }); + } + } + + private final class UpdateStatusLineTask extends TimerTask { + @Override + public void run() { + if (blankOutCounter < 0 || blankOutCounter-- > 0) + // Only clear it once + return; + invokeLater(new Runnable() { + @Override + public void run() { + if (blankOutCounter < 0) + statusLine.setVisible(false); + } + }); + } + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanelComponentFactory.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanelComponentFactory.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanelComponentFactory.java new file mode 100644 index 0000000..1bd92a5 --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServicePanelComponentFactory.java @@ -0,0 +1,81 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import javax.swing.ImageIcon; + +import org.apache.taverna.commons.services.ServiceRegistry; + +import org.apache.taverna.servicedescriptions.ServiceDescriptionRegistry; +import org.apache.taverna.ui.menu.MenuManager; +import org.apache.taverna.workbench.edits.EditManager; +import org.apache.taverna.workbench.selection.SelectionManager; +import org.apache.taverna.workbench.ui.zaria.UIComponentFactorySPI; +import org.apache.taverna.workbench.ui.zaria.UIComponentSPI; + +/** + * Service panel factory + * + * @author Stian Soiland-Reyes + */ +public class ServicePanelComponentFactory implements UIComponentFactorySPI { + private ServiceDescriptionRegistry serviceDescriptionRegistry; + private EditManager editManager; + private MenuManager menuManager; + private SelectionManager selectionManager; + private ServiceRegistry serviceRegistry; + + @Override + public UIComponentSPI getComponent() { + return new ServicePanel(serviceDescriptionRegistry, editManager, + menuManager, selectionManager, serviceRegistry); + } + + @Override + public ImageIcon getIcon() { + return null; + } + + @Override + public String getName() { + return "Service panel"; + } + + public void setServiceDescriptionRegistry( + ServiceDescriptionRegistry serviceDescriptionRegistry) { + this.serviceDescriptionRegistry = serviceDescriptionRegistry; + } + + public void setEditManager(EditManager editManager) { + this.editManager = editManager; + } + + public void setMenuManager(MenuManager menuManager) { + this.menuManager = menuManager; + } + + public void setSelectionManager(SelectionManager selectionManager) { + this.selectionManager = selectionManager; + } + + public void setServiceRegistry(ServiceRegistry serviceRegistry) { + this.serviceRegistry = serviceRegistry; + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeCellRenderer.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeCellRenderer.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeCellRenderer.java new file mode 100644 index 0000000..e5f65a9 --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeCellRenderer.java @@ -0,0 +1,76 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import static org.apache.taverna.workbench.activityicons.DefaultActivityIcon.getDefaultIcon; + +import java.awt.Component; + +import javax.swing.Icon; +import javax.swing.JTree; + +import org.apache.taverna.servicedescriptions.ServiceDescription; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeCellRenderer; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; + +@SuppressWarnings("serial") +public class ServiceTreeCellRenderer extends FilterTreeCellRenderer { + @Override + public Component getTreeCellRendererComponent(JTree tree, Object value, + boolean sel, boolean expanded, boolean leaf, int row, + boolean hasFocus) { + Component result = super.getTreeCellRendererComponent(tree, value, sel, + expanded, leaf, row, hasFocus); + if (result instanceof ServiceTreeCellRenderer + && value instanceof FilterTreeNode + && ((FilterTreeNode) value).getUserObject() instanceof ServiceDescription) + prettifyServiceTreeCell((ServiceTreeCellRenderer) result, + (ServiceDescription) ((FilterTreeNode) value) + .getUserObject()); + else { + // Commented out - these are ugly, use the default folder icons instead + /* + * if (expanded) { ((ServiceTreeCellRenderer) result) + * .setIcon(WorkbenchIcons.folderOpenIcon); } else { + * ((ServiceTreeCellRenderer) result) + * .setIcon(WorkbenchIcons.folderClosedIcon); } + */ + } + return result; + } + + private void prettifyServiceTreeCell(ServiceTreeCellRenderer renderer, + ServiceDescription item) { + String name = item.getName(); + if (getFilter() != null) + name = getFilter().filterRepresentation(name); + // serviceTreeCellRenderer.setForeground(Color.red); + String displayName = name; + + String textualDescription = item.getDescription(); + if (textualDescription != null && !textualDescription.isEmpty()) + displayName = displayName + " - " + textualDescription; + renderer.setText(displayName); + + Icon activityIcon = item.getIcon(); + renderer.setIcon(activityIcon != null ? activityIcon + : getDefaultIcon()); + } +} http://git-wip-us.apache.org/repos/asf/incubator-taverna-workbench/blob/a9a52bd5/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeClickListener.java ---------------------------------------------------------------------- diff --git a/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeClickListener.java b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeClickListener.java new file mode 100644 index 0000000..8109cdc --- /dev/null +++ b/taverna-activity-palette-ui/src/main/java/org/apache/taverna/workbench/ui/servicepanel/ServiceTreeClickListener.java @@ -0,0 +1,251 @@ +/* +* Licensed to the Apache Software Foundation (ASF) under one +* or more contributor license agreements. See the NOTICE file +* distributed with this work for additional information +* regarding copyright ownership. The ASF licenses this file +* to you under the Apache License, Version 2.0 (the +* "License"); you may not use this file except in compliance +* with the License. You may obtain a copy of the License at +* +* http://www.apache.org/licenses/LICENSE-2.0 +* +* Unless required by applicable law or agreed to in writing, +* software distributed under the License is distributed on an +* "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +* KIND, either express or implied. See the License for the +* specific language governing permissions and limitations +* under the License. +*/ + +package org.apache.taverna.workbench.ui.servicepanel; + +import static java.awt.Color.RED; +import static javax.swing.SwingUtilities.invokeLater; +import static org.apache.taverna.lang.ui.ShadedLabel.BLUE; +import static org.apache.taverna.lang.ui.ShadedLabel.GREEN; +import static org.apache.taverna.lang.ui.ShadedLabel.ORANGE; +import static org.apache.taverna.lang.ui.ShadedLabel.halfShade; +import static org.apache.taverna.workbench.icons.WorkbenchIcons.minusIcon; +import static org.apache.taverna.workbench.icons.WorkbenchIcons.plusIcon; + +import java.awt.event.ActionEvent; +import java.awt.event.MouseAdapter; +import java.awt.event.MouseEvent; +import java.util.HashSet; +import java.util.Map; +import java.util.Set; +import java.util.TreeMap; + +import javax.swing.AbstractAction; +import javax.swing.JMenuItem; +import javax.swing.JPopupMenu; +import javax.swing.JTree; +import javax.swing.tree.TreePath; + +import org.apache.taverna.lang.ui.ShadedLabel; +import org.apache.taverna.servicedescriptions.ConfigurableServiceProvider; +import org.apache.taverna.servicedescriptions.ServiceDescription; +import org.apache.taverna.servicedescriptions.ServiceDescriptionProvider; +import org.apache.taverna.servicedescriptions.ServiceDescriptionRegistry; +import org.apache.taverna.ui.menu.MenuManager; +import org.apache.taverna.workbench.edits.EditManager; +import org.apache.taverna.workbench.selection.SelectionManager; +import org.apache.taverna.workbench.ui.servicepanel.actions.ExportServiceDescriptionsAction; +import org.apache.taverna.workbench.ui.servicepanel.actions.ImportServiceDescriptionsFromFileAction; +import org.apache.taverna.workbench.ui.servicepanel.actions.ImportServiceDescriptionsFromURLAction; +import org.apache.taverna.workbench.ui.servicepanel.actions.RemoveDefaultServicesAction; +import org.apache.taverna.workbench.ui.servicepanel.actions.RemoveUserServicesAction; +import org.apache.taverna.workbench.ui.servicepanel.actions.RestoreDefaultServicesAction; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeNode; +import org.apache.taverna.workbench.ui.servicepanel.tree.FilterTreeSelectionModel; +import org.apache.taverna.workbench.ui.servicepanel.tree.TreePanel; +import org.apache.taverna.workbench.ui.workflowview.WorkflowView; + +import org.apache.log4j.Logger; + +import org.apache.taverna.commons.services.ServiceRegistry; + +/** + * @author alanrw + */ +public class ServiceTreeClickListener extends MouseAdapter { + private static Logger logger = Logger.getLogger(ServiceTreeClickListener.class); + + private JTree tree; + private TreePanel panel; + private final ServiceDescriptionRegistry serviceDescriptionRegistry; + private final EditManager editManager; + private final MenuManager menuManager; + private final SelectionManager selectionManager; + private final ServiceRegistry serviceRegistry; + + public ServiceTreeClickListener(JTree tree, TreePanel panel, + ServiceDescriptionRegistry serviceDescriptionRegistry, EditManager editManager, + MenuManager menuManager, SelectionManager selectionManager, ServiceRegistry serviceRegistry) { + this.tree = tree; + this.panel = panel; + this.serviceDescriptionRegistry = serviceDescriptionRegistry; + this.editManager = editManager; + this.menuManager = menuManager; + this.selectionManager = selectionManager; + this.serviceRegistry = serviceRegistry; + } + + @SuppressWarnings("serial") + private void handleMouseEvent(MouseEvent evt) { + FilterTreeSelectionModel selectionModel = (FilterTreeSelectionModel) tree + .getSelectionModel(); + // Discover the tree row that was clicked on + int selRow = tree.getRowForLocation(evt.getX(), evt.getY()); + if (selRow == -1) + return; + + // Get the selection path for the row + TreePath selectionPath = tree + .getPathForLocation(evt.getX(), evt.getY()); + if (selectionPath == null) + return; + + // Get the selected node + final FilterTreeNode selectedNode = (FilterTreeNode) selectionPath + .getLastPathComponent(); + + selectionModel.clearSelection(); + selectionModel.mySetSelectionPath(selectionPath); + + if (evt.isPopupTrigger()) { + JPopupMenu menu = new JPopupMenu(); + Object selectedObject = selectedNode.getUserObject(); + logger.info(selectedObject.getClass().getName()); + if (!(selectedObject instanceof ServiceDescription)) { + menu.add(new ShadedLabel("Tree", BLUE)); + menu.add(new JMenuItem(new AbstractAction("Expand all", + plusIcon) { + @Override + public void actionPerformed(ActionEvent evt) { + invokeLater(new Runnable() { + @Override + public void run() { + panel.expandAll(selectedNode, true); + } + }); + } + })); + menu.add(new JMenuItem(new AbstractAction("Collapse all", + minusIcon) { + @Override + public void actionPerformed(ActionEvent evt) { + invokeLater(new Runnable() { + @Override + public void run() { + panel.expandAll(selectedNode, false); + } + }); + } + })); + } + + if (selectedObject instanceof ServiceDescription) { + final ServiceDescription sd = (ServiceDescription) selectedObject; + menu.add(new ShadedLabel(sd.getName(), ORANGE)); + menu.add(new AbstractAction("Add to workflow") { + @Override + public void actionPerformed(ActionEvent e) { + WorkflowView.importServiceDescription(sd, false, editManager, + menuManager, selectionManager, serviceRegistry); + } + }); + menu.add(new AbstractAction("Add to workflow with name...") { + @Override + public void actionPerformed(ActionEvent e) { + WorkflowView.importServiceDescription(sd, true, editManager, + menuManager, selectionManager, serviceRegistry); + } + }); + } + + Map<String, ServiceDescriptionProvider> nameMap = getServiceDescriptionProviderMap(selectedNode); + + boolean first = true; + for (String name : nameMap.keySet()) { + final ServiceDescriptionProvider sdp = nameMap.get(name); + if (!(sdp instanceof ConfigurableServiceProvider)) + continue; + if (first) { + menu.add(new ShadedLabel( + "Remove individual service provider", GREEN)); + first = false; + } + menu.add(new AbstractAction(name) { + @Override + public void actionPerformed(ActionEvent e) { + serviceDescriptionRegistry + .removeServiceDescriptionProvider(sdp); + } + }); + } + + if (selectedNode.isRoot()) { // Root "Available services" + menu.add(new ShadedLabel("Default and added service providers", + ORANGE)); + menu.add(new RemoveUserServicesAction( + serviceDescriptionRegistry)); + menu.add(new RemoveDefaultServicesAction( + serviceDescriptionRegistry)); + menu.add(new RestoreDefaultServicesAction( + serviceDescriptionRegistry)); + + menu.add(new ShadedLabel("Import/export services", halfShade(RED))); + menu.add(new ImportServiceDescriptionsFromFileAction( + serviceDescriptionRegistry)); + menu.add(new ImportServiceDescriptionsFromURLAction( + serviceDescriptionRegistry)); + menu.add(new ExportServiceDescriptionsAction( + serviceDescriptionRegistry)); + } + + menu.show(evt.getComponent(), evt.getX(), evt.getY()); + } + } + + private Map<String, ServiceDescriptionProvider> getServiceDescriptionProviderMap( + FilterTreeNode selectedNode) { + Set<ServiceDescriptionProvider> providers; + + if (selectedNode.isRoot()) + providers = serviceDescriptionRegistry + .getServiceDescriptionProviders(); + else { + providers = new HashSet<>(); + for (FilterTreeNode leaf : selectedNode.getLeaves()) { + if (!leaf.isLeaf()) + logger.info("Not a leaf"); + if (!(leaf.getUserObject() instanceof ServiceDescription)) { + logger.info(leaf.getUserObject().getClass() + .getCanonicalName()); + logger.info(leaf.getUserObject().toString()); + continue; + } + providers + .addAll(serviceDescriptionRegistry + .getServiceDescriptionProviders((ServiceDescription) leaf + .getUserObject())); + } + } + + TreeMap<String, ServiceDescriptionProvider> nameMap = new TreeMap<>(); + for (ServiceDescriptionProvider sdp : providers) + nameMap.put(sdp.toString(), sdp); + return nameMap; + } + + @Override + public void mousePressed(MouseEvent evt) { + handleMouseEvent(evt); + } + + @Override + public void mouseReleased(MouseEvent evt) { + handleMouseEvent(evt); + } +}
