From ab506fbc0fa234dc7ce44e1d2af4944df734fe2c Mon Sep 17 00:00:00 2001 From: gmungoc Date: Tue, 6 Dec 2016 16:22:55 +0000 Subject: [PATCH] JAL-2351 first refactoring and outline of read/write Jmol properties --- resources/lang/Messages.properties | 6 +- src/jalview/ext/rbvi/chimera/ChimeraCommands.java | 6 +- .../ext/rbvi/chimera/JalviewChimeraBinding.java | 20 +++++ src/jalview/gui/AppJmol.java | 74 ++++++++++++++++- src/jalview/gui/ChimeraViewFrame.java | 84 ++++++-------------- src/jalview/gui/Jalview2XML.java | 2 +- src/jalview/gui/StructureViewerBase.java | 67 +++++++++++++++- src/jalview/jbgui/GStructureViewer.java | 1 - 8 files changed, 186 insertions(+), 74 deletions(-) diff --git a/resources/lang/Messages.properties b/resources/lang/Messages.properties index ce39010..27be83b 100644 --- a/resources/lang/Messages.properties +++ b/resources/lang/Messages.properties @@ -716,8 +716,10 @@ label.colour_with_chimera = Colour with Chimera label.align_structures = Align Structures label.jmol = Jmol label.chimera = Chimera -label.create_chimera_attributes = Write Jalview features -label.create_chimera_attributes_tip = Set Chimera residue attributes for visible features +label.create_viewer_attributes = Write Jalview features +label.create_viewer_attributes_tip = Create {0} attributes for visible features +label.fetch_viewer_attributes = Fetch {0} attribute +label.fetch_viewer_attributes_tip = Copy {0} attribute to Jalview feature label.sort_alignment_by_tree = Sort Alignment By Tree label.mark_unlinked_leaves = Mark Unlinked Leaves label.associate_leaves_with = Associate Leaves With diff --git a/src/jalview/ext/rbvi/chimera/ChimeraCommands.java b/src/jalview/ext/rbvi/chimera/ChimeraCommands.java index 07c0015..061f6d9 100644 --- a/src/jalview/ext/rbvi/chimera/ChimeraCommands.java +++ b/src/jalview/ext/rbvi/chimera/ChimeraCommands.java @@ -25,6 +25,7 @@ import jalview.api.SequenceRenderer; import jalview.datamodel.AlignmentI; import jalview.datamodel.SequenceFeature; import jalview.datamodel.SequenceI; +import jalview.gui.StructureViewerBase; import jalview.structure.StructureMapping; import jalview.structure.StructureMappingcommandSet; import jalview.structure.StructureSelectionManager; @@ -46,9 +47,6 @@ import java.util.Map; */ public class ChimeraCommands { - - public static final String NAMESPACE_PREFIX = "jv_"; - /** * Constructs Chimera commands to colour residues as per the Jalview alignment * @@ -506,7 +504,7 @@ public class ChimeraCommands sb.append(Character.isLetterOrDigit(c) ? c : '_'); } } - String attName = NAMESPACE_PREFIX + sb.toString(); + String attName = StructureViewerBase.NAMESPACE_PREFIX + sb.toString(); /* * Chimera treats an attribute name ending in 'color' as colour-valued; diff --git a/src/jalview/ext/rbvi/chimera/JalviewChimeraBinding.java b/src/jalview/ext/rbvi/chimera/JalviewChimeraBinding.java index 75ddc9c..903b409 100644 --- a/src/jalview/ext/rbvi/chimera/JalviewChimeraBinding.java +++ b/src/jalview/ext/rbvi/chimera/JalviewChimeraBinding.java @@ -1351,4 +1351,24 @@ public abstract class JalviewChimeraBinding extends AAStructureBindingModel } return -1; } + + /** + * Queries Chimera for its list of residue attributes and returns their names + * + * @return + */ + public List getResidueAttributes() + { + List result = new ArrayList(); + List atts = sendChimeraCommand("list resattr", true); + for (String att : atts) + { + /* + * expect lines like "resattr chi1" - we just one the second bit + */ + String[] tokens = att.split(" "); + result.add(tokens[tokens.length - 1]); + } + return result; + } } diff --git a/src/jalview/gui/AppJmol.java b/src/jalview/gui/AppJmol.java index e2e54aa..29c388c 100644 --- a/src/jalview/gui/AppJmol.java +++ b/src/jalview/gui/AppJmol.java @@ -50,8 +50,11 @@ import java.awt.Font; import java.awt.Graphics; import java.awt.Rectangle; import java.awt.event.ActionEvent; +import java.awt.event.ActionListener; import java.awt.event.ItemEvent; import java.awt.event.ItemListener; +import java.awt.event.MouseAdapter; +import java.awt.event.MouseEvent; import java.io.BufferedReader; import java.io.File; import java.io.FileOutputStream; @@ -66,7 +69,7 @@ import javax.swing.JCheckBoxMenuItem; import javax.swing.JColorChooser; import javax.swing.JInternalFrame; import javax.swing.JMenu; -import javax.swing.JOptionPane; +import javax.swing.JMenuItem; import javax.swing.JPanel; import javax.swing.JSplitPane; import javax.swing.SwingUtilities; @@ -170,6 +173,8 @@ public class AppJmol extends StructureViewerBase private void initMenus() { + String jmol = MessageManager.getString("label.jmol"); + viewerActionMenu.setText(jmol); seqColour.setSelected(jmb.isColourBySequence()); viewerColour.setSelected(!jmb.isColourBySequence()); if (_colourwith == null) @@ -243,6 +248,35 @@ public class AppJmol extends StructureViewerBase } }); + + JMenuItem writeFeatures = new JMenuItem( + MessageManager.getString("label.create_viewer_attributes")); + writeFeatures.setToolTipText(MessageManager.formatMessage( + "label.create_viewer_attributes_tip", jmol)); + writeFeatures.addActionListener(new ActionListener() + { + @Override + public void actionPerformed(ActionEvent e) + { + sendFeaturesToViewer(); + } + }); + viewerActionMenu.add(writeFeatures); + + final JMenu fetchAttributes = new JMenu(MessageManager.formatMessage( + "label.fetch_viewer_attributes", jmol)); + fetchAttributes.setToolTipText(MessageManager.formatMessage( + "label.fetch_viewer_attributes_tip", jmol)); + fetchAttributes.addMouseListener(new MouseAdapter() + { + + @Override + public void mouseEntered(MouseEvent e) + { + buildAttributesMenu(fetchAttributes); + } + }); + viewerActionMenu.add(fetchAttributes); } IProgressIndicator progressBar = null; @@ -1031,10 +1065,10 @@ public class AppJmol extends StructureViewerBase setChainMenuItems(jmb.getChainNames()); this.setTitle(jmb.getViewerTitle()); - if (jmb.getPdbFile().length > 1 && jmb.getSequence().length > 1) - { + // if (jmb.getPdbFile().length > 1 && jmb.getSequence().length > 1) + // { viewerActionMenu.setVisible(true); - } + // } if (!jmb.isLoadingFromArchive()) { seqColour_actionPerformed(null); @@ -1143,4 +1177,36 @@ public class AppJmol extends StructureViewerBase return jmb; } + @Override + protected void sendFeaturesToViewer() + { + /* + * Atom properties may also be set directly using {atom expression}.xxxx = y. + */ + } + + @Override + protected void getResidueAttributes(String attName) + { + /* + * getproperty atominfo returns properties for all atoms + * - could parse this for unique/specific property names? + * + * _ipt atomID atomIndex atomno bondCount chain clickabilityFlags colix color coord + * element elemno formalCharge groupID info model name occupancy partialCharge + * polymerLength radius resname resno shape spacefill structure sym temp + * visibilityFlags visible x y z + * + * getproperty chaininfo is residue level info + * no sign of average bfactor for a residue :-( + */ + } + + @Override + protected List getResidueAttributeNames() + { + // TODO Auto-generated method stub + return null; + } + } diff --git a/src/jalview/gui/ChimeraViewFrame.java b/src/jalview/gui/ChimeraViewFrame.java index 4c38898..bac8f60 100644 --- a/src/jalview/gui/ChimeraViewFrame.java +++ b/src/jalview/gui/ChimeraViewFrame.java @@ -26,7 +26,6 @@ import jalview.datamodel.AlignmentI; import jalview.datamodel.ColumnSelection; import jalview.datamodel.PDBEntry; import jalview.datamodel.SequenceI; -import jalview.ext.rbvi.chimera.ChimeraCommands; import jalview.ext.rbvi.chimera.JalviewChimeraBinding; import jalview.gui.StructureViewer.ViewerType; import jalview.io.DataSourceType; @@ -62,7 +61,6 @@ import java.io.IOException; import java.io.InputStream; import java.io.PrintWriter; import java.util.ArrayList; -import java.util.Collections; import java.util.List; import java.util.Random; import java.util.Vector; @@ -72,7 +70,6 @@ import javax.swing.JColorChooser; import javax.swing.JInternalFrame; import javax.swing.JMenu; import javax.swing.JMenuItem; -import javax.swing.JOptionPane; import javax.swing.event.InternalFrameAdapter; import javax.swing.event.InternalFrameEvent; import javax.swing.event.MenuEvent; @@ -86,7 +83,7 @@ import javax.swing.event.MenuListener; */ public class ChimeraViewFrame extends StructureViewerBase { - private JalviewChimeraBinding jmb; + JalviewChimeraBinding jmb; private boolean allChainsSelected = false; @@ -106,7 +103,8 @@ public class ChimeraViewFrame extends StructureViewerBase */ private void initMenus() { - viewerActionMenu.setText(MessageManager.getString("label.chimera")); + String chimera = MessageManager.getString("label.chimera"); + viewerActionMenu.setText(chimera); viewerColour.setText(MessageManager .getString("label.colour_with_chimera")); viewerColour.setToolTipText(MessageManager @@ -167,43 +165,39 @@ public class ChimeraViewFrame extends StructureViewerBase viewerActionMenu.add(alpanels); viewerActionMenu.addMenuListener(new MenuListener() { - @Override public void menuSelected(MenuEvent e) { handler.itemStateChanged(null); } - @Override public void menuDeselected(MenuEvent e) { - // TODO Auto-generated method stub } - @Override public void menuCanceled(MenuEvent e) { - // TODO Auto-generated method stub } }); JMenuItem writeFeatures = new JMenuItem( - MessageManager.getString("label.create_chimera_attributes")); - writeFeatures.setToolTipText(MessageManager - .getString("label.create_chimera_attributes_tip")); + MessageManager.getString("label.create_viewer_attributes")); + writeFeatures.setToolTipText(MessageManager.formatMessage( + "label.create_viewer_attributes_tip", chimera)); writeFeatures.addActionListener(new ActionListener() { @Override public void actionPerformed(ActionEvent e) { - sendFeaturesToChimera(); + sendFeaturesToViewer(); } }); viewerActionMenu.add(writeFeatures); - final JMenu fetchAttributes = new JMenu("Fetch Chimera attributes"); - fetchAttributes - .setToolTipText("Copy Chimera attribute to Jalview feature"); + final JMenu fetchAttributes = new JMenu(MessageManager.formatMessage( + "label.fetch_viewer_attributes", chimera)); + fetchAttributes.setToolTipText(MessageManager.formatMessage( + "label.fetch_viewer_attributes_tip", chimera)); fetchAttributes.addMouseListener(new MouseAdapter() { @@ -214,55 +208,16 @@ public class ChimeraViewFrame extends StructureViewerBase } }); viewerActionMenu.add(fetchAttributes); - - } - - /** - * Query Chimera for its residue attribute names and add them as items off the - * attributes menu - * - * @param attributesMenu - */ - protected void buildAttributesMenu(JMenu attributesMenu) - { - List atts = jmb.sendChimeraCommand("list resattr", true); - if (atts == null) - { - return; - } - attributesMenu.removeAll(); - Collections.sort(atts); - for (String att : atts) - { - final String attName = att.split(" ")[1]; - - /* - * ignore 'jv_*' attributes, as these are Jalview features that have - * been transferred to residue attributes in Chimera! - */ - if (!attName.startsWith(ChimeraCommands.NAMESPACE_PREFIX)) - { - JMenuItem menuItem = new JMenuItem(attName); - menuItem.addActionListener(new ActionListener() - { - @Override - public void actionPerformed(ActionEvent e) - { - getChimeraAttributes(attName); - } - }); - attributesMenu.add(menuItem); - } - } } /** - * Read residues in Chimera with the given attribute name, and set as features - * on the corresponding sequence positions (if any) + * Asks Chimera for residues with the given attribute name, and set as + * features on the corresponding sequence positions (if any) * * @param attName */ - protected void getChimeraAttributes(String attName) + @Override + protected void getResidueAttributes(String attName) { jmb.copyStructureAttributesToFeatures(attName, getAlignmentPanel()); } @@ -274,7 +229,8 @@ public class ChimeraViewFrame extends StructureViewerBase *

* For example: setattr r jv:chain "Ferredoxin-1, Chloroplastic" #0:94.A */ - protected void sendFeaturesToChimera() + @Override + protected void sendFeaturesToViewer() { jmb.sendFeaturesToViewer(getAlignmentPanel()); } @@ -1291,4 +1247,10 @@ public class ChimeraViewFrame extends StructureViewerBase { return jmb; } + + @Override + protected List getResidueAttributeNames() + { + return jmb.getResidueAttributes(); + } } diff --git a/src/jalview/gui/Jalview2XML.java b/src/jalview/gui/Jalview2XML.java index 35db33f..2eaed6a 100644 --- a/src/jalview/gui/Jalview2XML.java +++ b/src/jalview/gui/Jalview2XML.java @@ -3967,7 +3967,7 @@ public class Jalview2XML .size()][]); String newViewId = viewerData.getKey(); - ChimeraViewFrame cvf = new ChimeraViewFrame(chimeraSessionFile, + StructureViewerBase cvf = new ChimeraViewFrame(chimeraSessionFile, af.alignPanel, pdbArray, seqsArray, colourByChimera, colourBySequence, newViewId); cvf.setSize(data.getWidth(), data.getHeight()); diff --git a/src/jalview/gui/StructureViewerBase.java b/src/jalview/gui/StructureViewerBase.java index 91d7130..d7d01ca 100644 --- a/src/jalview/gui/StructureViewerBase.java +++ b/src/jalview/gui/StructureViewerBase.java @@ -35,12 +35,13 @@ import java.awt.event.ActionListener; import java.awt.event.ItemEvent; import java.awt.event.ItemListener; import java.util.ArrayList; +import java.util.Collections; import java.util.List; import java.util.Vector; import javax.swing.JCheckBoxMenuItem; +import javax.swing.JMenu; import javax.swing.JMenuItem; -import javax.swing.JOptionPane; /** * Base class with common functionality for JMol, Chimera or other structure @@ -52,6 +53,10 @@ import javax.swing.JOptionPane; public abstract class StructureViewerBase extends GStructureViewer implements Runnable, ViewSetProvider { + /* + * prefix for attributes on structure which are derived from Jalview features + */ + public static final String NAMESPACE_PREFIX = "jv_"; /** * list of sequenceSet ids associated with the view @@ -552,4 +557,64 @@ public abstract class StructureViewerBase extends GStructureViewer abstract void showSelectedChains(); + /** + * Send a command to the structure viewer to create residue attributes for + * Jalview features + */ + abstract protected void sendFeaturesToViewer(); + + /** + * Query the structure viewer for its residue attribute names and add them as + * sub-items of the attributes menu. Names of the form "jv_*" are ignored as + * these originated from Jalview so no need to copy them back. + * + * @param attributesMenu + */ + protected void buildAttributesMenu(JMenu attributesMenu) + { + List atts = getResidueAttributeNames(); + if (atts == null) + { + return; + } + attributesMenu.removeAll(); + Collections.sort(atts); + for (final String att : atts) + { + /* + * ignore 'jv_*' attributes, as these are Jalview features that have + * been transferred to residue attributes in Chimera! + */ + if (!att.startsWith(StructureViewerBase.NAMESPACE_PREFIX)) + { + JMenuItem menuItem = new JMenuItem(att); + menuItem.addActionListener(new ActionListener() + { + @Override + public void actionPerformed(ActionEvent e) + { + getResidueAttributes(att); + } + }); + attributesMenu.add(menuItem); + } + } + } + + /** + * Queries the structure viewer for residues with the given attribute, and + * creates sequence features in Jalview for the corresponding mapped positions + * + * @param attName + */ + protected abstract void getResidueAttributes(String attName); + + /** + * Returns a list of residue attributes in the structure viewer, excluding any + * with prefix "jv_" + * + * @return + */ + protected abstract List getResidueAttributeNames(); + } diff --git a/src/jalview/jbgui/GStructureViewer.java b/src/jalview/jbgui/GStructureViewer.java index bd0f1de..acddc29 100644 --- a/src/jalview/jbgui/GStructureViewer.java +++ b/src/jalview/jbgui/GStructureViewer.java @@ -328,7 +328,6 @@ public abstract class GStructureViewer extends JInternalFrame implements alignStructs_actionPerformed(actionEvent); } }); - viewerActionMenu.setText(MessageManager.getString("label.jmol")); menuBar.add(fileMenu); menuBar.add(viewMenu); menuBar.add(colourMenu); -- 1.7.10.2