X-Git-Url: http://source.jalview.org/gitweb/?a=blobdiff_plain;ds=inline;f=src%2Fjalview%2Fext%2Farchaeopteryx%2FAptxInit.java;h=b9a2266f49651437ac5f250513c4246e232b66b3;hb=ccbd3e0bfd34533d8e98b7ef9a6cb48d9684b3da;hp=107aeca8d9e5e120d36d3d8cd5881fe72715e14c;hpb=57c323c357199f78a812adb4d63290a3347f4097;p=jalview.git diff --git a/src/jalview/ext/archaeopteryx/AptxInit.java b/src/jalview/ext/archaeopteryx/AptxInit.java index 107aeca..b9a2266 100644 --- a/src/jalview/ext/archaeopteryx/AptxInit.java +++ b/src/jalview/ext/archaeopteryx/AptxInit.java @@ -5,16 +5,37 @@ import jalview.datamodel.SequenceI; import jalview.ext.treeviewer.ExternalTreeBuilderI; import jalview.ext.treeviewer.ExternalTreeViewerBindingI; import jalview.gui.Desktop; +import jalview.gui.JvOptionPane; +import jalview.util.MessageManager; import jalview.viewmodel.AlignmentViewport; import java.awt.Dimension; +import java.io.File; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.net.MalformedURLException; import java.net.URL; +import java.util.HashMap; import java.util.Map; +import org.forester.archaeopteryx.AptxUtil; import org.forester.archaeopteryx.Archaeopteryx; +import org.forester.archaeopteryx.Configuration; import org.forester.archaeopteryx.MainFrame; +import org.forester.archaeopteryx.webservices.PhylogeniesWebserviceClient; +import org.forester.archaeopteryx.webservices.WebserviceUtil; +import org.forester.io.parsers.PhylogenyParser; +import org.forester.io.parsers.nexus.NexusPhylogeniesParser; +import org.forester.io.parsers.nhx.NHXParser; +import org.forester.io.parsers.phyloxml.PhyloXmlDataFormatException; +import org.forester.io.parsers.phyloxml.PhyloXmlParser; +import org.forester.io.parsers.tol.TolParser; +import org.forester.io.parsers.util.ParserUtils; import org.forester.phylogeny.Phylogeny; +import org.forester.phylogeny.PhylogenyMethods; import org.forester.phylogeny.PhylogenyNode; +import org.forester.phylogeny.data.Identifier; +import org.forester.util.ForesterUtil; /** * Static class for creating Archaeopteryx tree viewer instances from calculated @@ -25,173 +46,459 @@ import org.forester.phylogeny.PhylogenyNode; */ public final class AptxInit { - /** - * Test method, should generally not be used as it does not bind the tree to - * its alignment - * - * @param aptxTrees - * @return - */ - public static MainFrame createUnboundInstance(final Phylogeny aptxTree) - { - Phylogeny[] aptxTrees = { aptxTree }; - return createAptxFrame(aptxTrees); - } + private final static Configuration APTX_CONFIG = new Configuration( + "_aptx_jalview_configuration_file", + false, false, false); + + private final static boolean VALIDATE_PHYLOXML_XSD = APTX_CONFIG + .isValidatePhyloXmlAgainstSchema(); + + private final static boolean REPLACE_NHX_UNDERSCORES = APTX_CONFIG + .isReplaceUnderscoresInNhParsing(); - // public static MainFrame createInstance(final Phylogeny[] aptxTrees, - // AlignmentViewport jalviewAlignmentView) - // { - // return createAptxFrameInJalview(aptxTrees); - // - // } - // - // public static MainFrame createInstance(final Phylogeny aptxTree, - // final AlignmentViewport jalviewAlignmentView) - // { - // Phylogeny[] aptxTrees = { aptxTree }; // future possibility to load in - // // several trees simultaneously - // return createAptxFrameInJalview(aptxTrees); - // - // } - - public static MainFrame createInstance( - final TreeBuilder calculatedTree) // very dense method, to be split up + private final static boolean INTERNAL_NUMBERS_AS_CONFIDENCE = APTX_CONFIG + .isInternalNumberAreConfidenceForNhParsing(); + + private final static boolean MIDPOINT_REROOT = APTX_CONFIG + .isMidpointReroot(); + + private final static NHXParser.TAXONOMY_EXTRACTION TAXONOMY_EXTRACTION = APTX_CONFIG + .getTaxonomyExtraction(); + + private static Map activeAptx = new HashMap<>(); + + + + public static MainFrame createInstanceFromCalculation( + final TreeBuilder calculatedTree) { ExternalTreeBuilderI aptxTreeBuilder = new AptxTreeBuilder( calculatedTree); Phylogeny aptxTree = aptxTreeBuilder.buildTree(); - Phylogeny[] aptxTrees = { aptxTree }; // future possibility to load in - // several trees simultaneously - MainFrame aptxApp = createAptxFrame(aptxTrees); + MainFrame aptxApp = createAptxFrame(aptxTree, + calculatedTree.getAvport(), null); - bindNodesToJalviewSequences(aptxApp, calculatedTree.getAvport(), - aptxTreeBuilder.getAlignmentBoundNodes(), - aptxTreeBuilder.getNodesBoundAlignment()); + return aptxApp; + } - return bindFrameToJalview(aptxApp); + /** + * Refactored from Archaeopteryx.main + * + * @param filePath + * @param viewport + * @return + * @throws IOException + * @throws FileNotFoundException + */ + public static MainFrame[] createInstancesFromFile(String filePath, + AlignmentViewport viewport) + throws FileNotFoundException, IOException + { + File treeFile = new File(filePath); + final String err = ForesterUtil.isReadableFile(treeFile); + if (!ForesterUtil.isEmpty(err)) + { + JvOptionPane.showMessageDialog(Desktop.desktop, err, + MessageManager.getString("label.problem_reading_tree_file"), + JvOptionPane.WARNING_MESSAGE); + } + + if (Desktop.instance != null) + { + Desktop.instance.startLoading(filePath); + } + boolean nhx_or_nexus = false; + final PhylogenyParser parser = ParserUtils.createParserDependingOnFileType( + treeFile, VALIDATE_PHYLOXML_XSD); + if (parser instanceof NHXParser) + { + nhx_or_nexus = true; + final NHXParser nhx = (NHXParser) parser; + nhx.setReplaceUnderscores(REPLACE_NHX_UNDERSCORES); + nhx.setIgnoreQuotes(false); + nhx.setTaxonomyExtraction(TAXONOMY_EXTRACTION); + } + else if (parser instanceof NexusPhylogeniesParser) + { + nhx_or_nexus = true; + final NexusPhylogeniesParser nex = (NexusPhylogeniesParser) parser; + nex.setReplaceUnderscores(REPLACE_NHX_UNDERSCORES); + nex.setIgnoreQuotes(false); + } + else if (parser instanceof PhyloXmlParser) + { + if (VALIDATE_PHYLOXML_XSD == false) + { + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + MessageManager.getString("error.phyloxml_validation"), + MessageManager.getString("label.file_open_error"), + JvOptionPane.WARNING_MESSAGE ); + } + } + Phylogeny[] trees = PhylogenyMethods.readPhylogenies(parser, treeFile); + MainFrame[] aptxFrames = new MainFrame[trees.length]; - } - public static MainFrame createInstanceFromFile(String filePath, + for (int i = 0; i < trees.length; i++) + { + Phylogeny tree = trees[i]; + + if (nhx_or_nexus && INTERNAL_NUMBERS_AS_CONFIDENCE) + { + PhylogenyMethods.transferInternalNodeNamesToConfidence(tree, ""); + } + String treeTitle = treeFile.getName() + "[" + i + "]"; + tree.setName(treeTitle); + aptxFrames[i] = createAptxFrame(tree, viewport, treeTitle); + + } + if (Desktop.instance != null) + { + Desktop.instance.stopLoading(); + } + return aptxFrames; + } + + + public static MainFrame[] createInstancesFromUrl(URL treeUrl, AlignmentViewport viewport) + throws FileNotFoundException, IOException, RuntimeException { - String[] AptxArgs = new String[] { "-c", - "_aptx_jalview_configuration_file", filePath }; - MainFrame aptxApp = Archaeopteryx.main(AptxArgs); + + String treeTitle = treeUrl.getFile(); + if (Desktop.instance != null) + { + Desktop.instance.startLoading(treeTitle); + } + Phylogeny[] trees = AptxUtil.readPhylogeniesFromUrl(treeUrl, + VALIDATE_PHYLOXML_XSD, + REPLACE_NHX_UNDERSCORES, INTERNAL_NUMBERS_AS_CONFIDENCE, + TAXONOMY_EXTRACTION, MIDPOINT_REROOT); - LoadedTreeAssociation bindAptxNodes = new LoadedTreeAssociation( - viewport.getAlignment().getSequencesArray(), - aptxApp.getMainPanel().getCurrentTreePanel().getPhylogeny()); + MainFrame[] aptxFrames = new MainFrame[trees.length]; + for (int i = 0; i < trees.length; i++) + { + Phylogeny tree = trees[i]; + aptxFrames[i] = createAptxFrame(tree, viewport, treeTitle); + } - bindAptxNodes.associateLeavesToSequences(); + if (Desktop.instance != null) + { + Desktop.instance.stopLoading(); + } - bindNodesToJalviewSequences(aptxApp, viewport, - bindAptxNodes.getAlignmentWithNodes(), - bindAptxNodes.getNodesWithAlignment()); + return aptxFrames; - return bindFrameToJalview(aptxApp); } - public static MainFrame createInstanceFromUrl(URL url) + /** + * Refactored from Forester's UrlTreeReader, this can be more efficient + * + * @param databaseIndex + * @param viewport + * @return + */ + public static MainFrame[] createInstancesFromDb( + PhylogeniesWebserviceClient treeDbClient, String identifier, + AlignmentViewport viewport) { + URL url = null; + Phylogeny[] trees = null; + + if ((identifier != null) && (identifier.trim().length() > 0)) + { + if (Desktop.instance != null) + { + Desktop.instance.startLoading(identifier); + } + + identifier = identifier.trim(); + if (treeDbClient.isQueryInteger()) + { + identifier = identifier.replaceAll("^\\D+", ""); + + int id; + try + { + id = Integer.parseInt(identifier); + } catch (final NumberFormatException e) + { + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + MessageManager.formatMessage( + "error.database_id_has_letters", new String[] + { identifier }), + MessageManager.getString("label.invalid_url"), + JvOptionPane.ERROR_MESSAGE); + return new MainFrame[0]; + } + identifier = id + ""; + } + boolean exception = false; + try + { + String url_str = treeDbClient.getUrl(); + url_str = url_str.replaceFirst( + PhylogeniesWebserviceClient.QUERY_PLACEHOLDER, identifier); + url = new URL(url_str); + PhylogenyParser parser = null; + switch (treeDbClient.getReturnFormat()) + { + case TOL_XML_RESPONSE: + parser = new TolParser(); + break; + case NEXUS: + parser = new NexusPhylogeniesParser(); + ((NexusPhylogeniesParser) parser).setReplaceUnderscores(true); + break; + case TREEBASE_TREE: + parser = new NexusPhylogeniesParser(); + ((NexusPhylogeniesParser) parser).setReplaceUnderscores(true); + ((NexusPhylogeniesParser) parser) + .setTaxonomyExtraction(NHXParser.TAXONOMY_EXTRACTION.NO); + break; + case TREEBASE_STUDY: + parser = new NexusPhylogeniesParser(); + ((NexusPhylogeniesParser) parser).setReplaceUnderscores(true); + ((NexusPhylogeniesParser) parser) + .setTaxonomyExtraction(NHXParser.TAXONOMY_EXTRACTION.NO); + break; + case NH: + parser = new NHXParser(); + ((NHXParser) parser) + .setTaxonomyExtraction(NHXParser.TAXONOMY_EXTRACTION.NO); + ((NHXParser) parser).setReplaceUnderscores(true); + ((NHXParser) parser).setGuessRootedness(true); + break; + case NH_EXTRACT_TAXONOMY: + parser = new NHXParser(); + ((NHXParser) parser).setTaxonomyExtraction( + NHXParser.TAXONOMY_EXTRACTION.AGGRESSIVE); + ((NHXParser) parser).setReplaceUnderscores(false); + ((NHXParser) parser).setGuessRootedness(true); + break; + case PFAM: + parser = new NHXParser(); + ((NHXParser) parser).setTaxonomyExtraction( + NHXParser.TAXONOMY_EXTRACTION.PFAM_STYLE_STRICT); + ((NHXParser) parser).setReplaceUnderscores(false); + ((NHXParser) parser).setGuessRootedness(true); + break; + case NHX: + parser = new NHXParser(); + ((NHXParser) parser) + .setTaxonomyExtraction(NHXParser.TAXONOMY_EXTRACTION.NO); + ((NHXParser) parser).setReplaceUnderscores(false); + ((NHXParser) parser).setGuessRootedness(true); + break; + case PHYLOXML: + parser = PhyloXmlParser.createPhyloXmlParserXsdValidating(); + break; + default: + throw new IllegalArgumentException( + "unknown format: " + treeDbClient.getReturnFormat()); + } + // + // if (_main_frame.getMainPanel().getCurrentTreePanel() != null) + // { + // _main_frame.getMainPanel().getCurrentTreePanel().setWaitCursor(); + // } + // else + // { + // _main_frame.getMainPanel().setWaitCursor(); + // } + trees = ForesterUtil.readPhylogeniesFromUrl(url, parser); + } catch (final MalformedURLException e) + { + exception = true; + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + MessageManager.formatMessage( + "exception.unable_to_launch_url", new String[] + { url.toString() }), + MessageManager.getString("label.invalid_url"), + JvOptionPane.ERROR_MESSAGE); + System.err.println(e.getLocalizedMessage()); + } catch (final IOException e) + { + exception = true; + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + "Could not read from " + url + "\n" + + e.getLocalizedMessage(), + "Failed to read tree from " + treeDbClient.getName() + " for " + + identifier, + JvOptionPane.ERROR_MESSAGE); + System.err.println(e.getLocalizedMessage()); + } catch (final NumberFormatException e) + { + exception = true; + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + "Could not read from " + url + "\n" + + e.getLocalizedMessage(), + "Failed to read tree from " + treeDbClient.getName() + " for " + + identifier, + JvOptionPane.ERROR_MESSAGE); + System.err.println(e.getLocalizedMessage()); + } catch (final Exception e) + { + exception = true; + e.printStackTrace(); + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + e.getLocalizedMessage(), "Unexpected Exception", + JvOptionPane.ERROR_MESSAGE); + System.err.println(e.getLocalizedMessage()); + } + if ((trees != null) && (trees.length > 0)) + { + for (final Phylogeny phylogeny : trees) + { + if (!phylogeny.isEmpty()) + { + if (treeDbClient.getName().equals(WebserviceUtil.TREE_FAM_NAME)) + { + phylogeny.setRerootable(false); + phylogeny.setRooted(true); + } + if (treeDbClient.getProcessingInstructions() != null) + { + try + { + WebserviceUtil.processInstructions(treeDbClient, phylogeny); + } catch (final PhyloXmlDataFormatException e) + { + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + "Error:\n" + e.getLocalizedMessage(), "Error", + JvOptionPane.ERROR_MESSAGE); + } + } + if (treeDbClient.getNodeField() != null) + { + try + { + PhylogenyMethods.transferNodeNameToField(phylogeny, + treeDbClient.getNodeField(), false); + } catch (final PhyloXmlDataFormatException e) + { + JvOptionPane.showInternalMessageDialog(Desktop.desktop, + "Error:\n" + e.getLocalizedMessage(), "Error", + JvOptionPane.ERROR_MESSAGE); + } + } + phylogeny.setIdentifier( + new Identifier(identifier, treeDbClient.getName())); + // _main_frame.getJMenuBar().remove(_main_frame.getHelpMenu()); + // _main_frame.getMenuBarOfMainFrame() + // .add(_main_frame.getHelpMenu()); + // _main_frame.getMainPanel().addPhylogenyInNewTab(phylogeny, + // _main_frame.getConfiguration(), + // new File(url.getFile()).getName(), url.toString()); + + MainFrame aptxApp = createAptxFrame(phylogeny, viewport, + url.getFile()); + String my_name_for_file = ""; + if (!ForesterUtil.isEmpty(phylogeny.getName())) + { + my_name_for_file = new String(phylogeny.getName()) + .replaceAll(" ", "_"); + } + else if (phylogeny.getIdentifier() != null) + { + final StringBuffer sb = new StringBuffer(); + if (!ForesterUtil + .isEmpty(phylogeny.getIdentifier().getProvider())) + { + sb.append(phylogeny.getIdentifier().getProvider()); + sb.append("_"); + } + sb.append(phylogeny.getIdentifier().getValue()); + my_name_for_file = new String( + sb.toString().replaceAll(" ", "_")); + } + aptxApp.getMainPanel().getCurrentTreePanel() + .setTreeFile(new File(my_name_for_file)); + AptxUtil.lookAtSomeTreePropertiesForAptxControlSettings( + phylogeny, aptxApp.getMainPanel().getControlPanel(), + APTX_CONFIG); + // _main_frame.getMainPanel().getControlPanel().showWhole(); + + aptxApp.activateSaveAllIfNeeded(); + } + } + } + else if (!exception) // ..what? + { + JvOptionPane.showMessageDialog(null, + ForesterUtil.wordWrap( + "Failed to read in tree(s) from [" + url + "]", 80), + "Error", JvOptionPane.ERROR_MESSAGE); + } + if ((trees != null) && (trees.length > 0)) + { + try + { + JvOptionPane.showMessageDialog(null, + ForesterUtil.wordWrap("Successfully read in " + + trees.length + " tree(s) from [" + url + "]", + 80), + "Success", JvOptionPane.INFORMATION_MESSAGE); + } catch (final Exception e) + { + // Not important if this fails, do nothing. + } + // _main_frame.getContentPane().repaint(); + } + } + + System.gc(); + + + if (Desktop.instance != null) + { + Desktop.instance.stopLoading(); + } return null; - // void readPhylogeniesFromURL() { - // URL url = null; - // Phylogeny[] phys = null; - // final String message = "Please enter a complete URL, for example - // \"http://purl.org/phylo/treebase/phylows/study/TB2:S15480?format=nexus\""; - // final String url_string = JOptionPane - // .showInputDialog( this, - // message, - // "Use URL/webservice to obtain a phylogeny", - // JOptionPane.QUESTION_MESSAGE ); - // boolean nhx_or_nexus = false; - // if ( ( url_string != null ) && ( url_string.length() > 0 ) ) { - // try { - // url = new URL( url_string ); - // PhylogenyParser parser = null; - // if ( url.getHost().toLowerCase().indexOf( "tolweb" ) >= 0 ) { - // parser = new TolParser(); - // } - // else { - // parser = ParserUtils - // .createParserDependingOnUrlContents( url, - // getConfiguration().isValidatePhyloXmlAgainstSchema() ); - // } - // if ( parser instanceof NexusPhylogeniesParser ) { - // nhx_or_nexus = true; - // } - // else if ( parser instanceof NHXParser ) { - // nhx_or_nexus = true; - // } - // if ( _mainpanel.getCurrentTreePanel() != null ) { - // _mainpanel.getCurrentTreePanel().setWaitCursor(); - // } - // else { - // _mainpanel.setWaitCursor(); - // } - // final PhylogenyFactory factory = - // ParserBasedPhylogenyFactory.getInstance(); - // phys = factory.create( url.openStream(), parser ); - // } - // catch ( final MalformedURLException e ) { - // JOptionPane.showMessageDialog( this, - // "Malformed URL: " + url + "\n" + e.getLocalizedMessage(), - // "Malformed URL", - // JOptionPane.ERROR_MESSAGE ); - // } - // catch ( final IOException e ) { - // JOptionPane.showMessageDialog( this, - // "Could not read from " + url + "\n" - // + ForesterUtil.wordWrap( e.getLocalizedMessage(), 80 ), - // "Failed to read URL", - // JOptionPane.ERROR_MESSAGE ); - // } - // catch ( final Exception e ) { - // JOptionPane.showMessageDialog( this, - // ForesterUtil.wordWrap( e.getLocalizedMessage(), 80 ), - // "Unexpected Exception", - // JOptionPane.ERROR_MESSAGE ); - // } - // finally { - // if ( _mainpanel.getCurrentTreePanel() != null ) { - // _mainpanel.getCurrentTreePanel().setArrowCursor(); - // } - // else { - // _mainpanel.setArrowCursor(); - // } - // } - // if ( ( phys != null ) && ( phys.length > 0 ) ) { - // if ( nhx_or_nexus && - // getOptions().isInternalNumberAreConfidenceForNhParsing() ) { - // for( final Phylogeny phy : phys ) { - // PhylogenyMethods.transferInternalNodeNamesToConfidence( phy, "" ); - // } - // } - // AptxUtil.addPhylogeniesToTabs( phys, - // new File( url.getFile() ).getName(), - // new File( url.getFile() ).toString(), - // getConfiguration(), - // getMainPanel() ); - // _mainpanel.getControlPanel().showWhole(); - // } - // } - // activateSaveAllIfNeeded(); - // System.gc(); - // } + } + + public static MainFrame createAptxFrame( - final Phylogeny[] aptxTrees) + final Phylogeny aptxTree, + final AlignmentViewport jalviewAlignport, String treeTitle) { - MainFrame aptxApp = Archaeopteryx.createApplication(aptxTrees, - "_aptx_jalview_configuration_file", null); + if (APTX_CONFIG == null || APTX_CONFIG.isCouldReadConfigFile() == false) + { + int keepGoing = JvOptionPane.showConfirmDialog(Desktop.desktop, + MessageManager.getString("label.aptx_config_not_found"), + MessageManager.formatMessage("label.couldnt_locate", + new String[] + { "_aptx_jalview_configuration_file" }), + JvOptionPane.YES_NO_CANCEL_OPTION); + + if (keepGoing == JvOptionPane.CANCEL_OPTION + || keepGoing == JvOptionPane.CLOSED_OPTION + || keepGoing == JvOptionPane.NO_OPTION) + { + return null; + } + + } + MainFrame aptxApp = Archaeopteryx.createApplication(aptxTree, + APTX_CONFIG, treeTitle); + + LoadedTreeSequenceAssociation bindAptxNodes = new LoadedTreeSequenceAssociation( + jalviewAlignport.getAlignment().getSequencesArray(), aptxTree); + bindAptxNodes.associateLeavesToSequences(); + + bindNodesToJalviewSequences(aptxApp, jalviewAlignport, + bindAptxNodes.getAlignmentWithNodes(), + bindAptxNodes.getNodesWithAlignment()); + bindTreeViewFrameToJalview(aptxApp); + return aptxApp; } @@ -202,25 +509,44 @@ public final class AptxInit final Map alignMappedToNodes, final Map nodesMappedToAlign) { - return new JalviewBinding(aptxApp, jalviewAlignViewport, + JalviewBinding treeBinding = new JalviewBinding(aptxApp, + jalviewAlignViewport, alignMappedToNodes, nodesMappedToAlign); + activeAptx.put(aptxApp, treeBinding); + return treeBinding; } - public static MainFrame bindFrameToJalview(final MainFrame aptxApp) + public static MainFrame bindTreeViewFrameToJalview( + final MainFrame aptxApp) { int width = 400; int height = 550; aptxApp.setMinimumSize(new Dimension(width, height)); // aptxApp.setFont(Desktop.instance.getFont()); // aptxApp.getMainPanel().setFont(Desktop.instance.getFont()); - - Desktop.addInternalFrame(aptxApp, "Archaeopteryx Tree View", true, - width, height, true, true); - + String frameTitle = MessageManager.getString("label.aptx_title"); + File treeFile = aptxApp.getMainPanel().getCurrentTreePanel() + .getTreeFile(); + if (treeFile != null) + { + frameTitle += MessageManager.formatMessage("label.aptx_title_append", + new String[] + { treeFile.getAbsolutePath() }); + } + Desktop.addInternalFrame(aptxApp, frameTitle, true, width, height, true, + true); return aptxApp; } + public static Map getAllAptxFrames() + { + return activeAptx; + } + private static void disableRedundantGuiMenus() + { + + } }