Refactoring of Jalview, JalviewAppLoader, JalviewApp, various
[jalview.git] / src / jalview / ext / jmol / JalviewJmolBinding.java
index 80eed4f..cfb30b3 100644 (file)
@@ -44,12 +44,12 @@ import java.awt.event.ComponentEvent;
 import java.awt.event.ComponentListener;
 import java.io.File;
 import java.net.URL;
-import java.security.AccessControlException;
 import java.util.ArrayList;
 import java.util.BitSet;
 import java.util.Hashtable;
 import java.util.List;
 import java.util.Map;
+import java.util.StringTokenizer;
 import java.util.Vector;
 
 import org.jmol.adapter.smarter.SmarterJmolAdapter;
@@ -65,6 +65,8 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
         implements JmolStatusListener, JmolSelectionListener,
         ComponentListener
 {
+  private String lastMessage;
+
   boolean allChainsSelected = false;
 
   /*
@@ -89,8 +91,6 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
 
   String lastCommand;
 
-  String lastMessage;
-
   boolean loadedInline;
 
   StringBuffer resetLastRes = new StringBuffer();
@@ -167,7 +167,9 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
     // remove listeners for all structures in viewer
     getSsm().removeStructureViewerListener(this, this.getStructureFiles());
     if (viewer != null)
+    {
       viewer.dispose();
+    }
     lastCommand = null;
     viewer = null;
     releaseUIResources();
@@ -480,6 +482,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
   }
 
   Thread colourby = null;
+
   /**
    * Sends a set of colour commands to the structure viewer
    * 
@@ -494,7 +497,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
       colourby.interrupt();
       colourby = null;
     }
-    colourby = new Thread(new Runnable()
+    Thread colourby = new Thread(new Runnable()
     {
       @Override
       public void run()
@@ -509,6 +512,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
       }
     });
     colourby.start();
+    this.colourby = colourby;
   }
 
   /**
@@ -615,74 +619,6 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
    */
   private int _modelFileNameMap[];
 
-  // ////////////////////////////////
-  // /StructureListener
-  // @Override
-  public synchronized String[] getPdbFilex()
-  {
-    if (viewer == null)
-    {
-      return new String[0];
-    }
-    if (modelFileNames == null)
-    {
-      List<String> mset = new ArrayList<>();
-      _modelFileNameMap = new int[viewer.ms.mc];
-      String m = viewer.ms.getModelFileName(0);
-      if (m != null)
-      {
-        String filePath = m;
-        try
-        {
-          filePath = new File(m).getAbsolutePath();
-        } catch (AccessControlException x)
-        {
-          // usually not allowed to do this in applet
-          System.err.println(
-                  "jmolBinding: Using local file string from Jmol: " + m);
-        }
-        if (filePath.indexOf("/file:") != -1)
-        {
-          // applet path with docroot - discard as format won't match pdbfile
-          filePath = m;
-        }
-        mset.add(filePath);
-        _modelFileNameMap[0] = 0; // filename index for first model is always 0.
-      }
-      int j = 1;
-      for (int i = 1; i < viewer.ms.mc; i++)
-      {
-        m = viewer.ms.getModelFileName(i);
-        String filePath = m;
-        if (m != null)
-        {
-          try
-          {
-            filePath = new File(m).getAbsolutePath();
-          } catch (AccessControlException x)
-          {
-            // usually not allowed to do this in applet, so keep raw handle
-            // System.err.println("jmolBinding: Using local file string from
-            // Jmol: "+m);
-          }
-        }
-
-        /*
-         * add this model unless it is read from a structure file we have
-         * already seen (example: 2MJW is an NMR structure with 10 models)
-         */
-        if (!mset.contains(filePath))
-        {
-          mset.add(filePath);
-          _modelFileNameMap[j] = i; // record the model index for the filename
-          j++;
-        }
-      }
-      modelFileNames = mset.toArray(new String[mset.size()]);
-    }
-    return modelFileNames;
-  }
-
   @Override
   public synchronized String[] getStructureFiles()
   {
@@ -823,7 +759,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
     viewer.openStringInline(string);
   }
 
-  public void mouseOverStructure(int atomIndex, String strInfo)
+  protected void mouseOverStructure(int atomIndex, final String strInfo)
   {
     int pdbResNum;
     int alocsep = strInfo.indexOf("^");
@@ -877,7 +813,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
       try
       {
         // recover PDB filename for the model hovered over.
-        int mnumber = new Integer(mdlId).intValue() - 1;
+        int mnumber = Integer.valueOf(mdlId).intValue() - 1;
         if (_modelFileNameMap != null)
         {
           int _mp = _modelFileNameMap.length - 1;
@@ -904,18 +840,36 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
       } catch (Exception e)
       {
       }
-      ;
     }
-    if (lastMessage == null || !lastMessage.equals(strInfo))
+
+    /*
+     * highlight position on alignment(s); if some text is returned, 
+     * show this as a second line on the structure hover tooltip
+     */
+    String label = getSsm().mouseOverStructure(pdbResNum, chainId,
+            pdbfilename);
+    if (label != null)
     {
-      getSsm().mouseOverStructure(pdbResNum, chainId, pdbfilename);
+      // change comma to pipe separator (newline token for Jmol)
+      label = label.replace(',', '|');
+      StringTokenizer toks = new StringTokenizer(strInfo, " ");
+      StringBuilder sb = new StringBuilder();
+      sb.append("select ").append(String.valueOf(pdbResNum)).append(":")
+              .append(chainId).append("/1");
+      sb.append(";set hoverLabel \"").append(toks.nextToken()).append(" ")
+              .append(toks.nextToken());
+      sb.append("|").append(label).append("\"");
+      evalStateCommand(sb.toString());
     }
-
-    lastMessage = strInfo;
   }
 
   public void notifyAtomHovered(int atomIndex, String strInfo, String data)
   {
+    if (strInfo.equals(lastMessage))
+    {
+      return;
+    }
+    lastMessage = strInfo;
     if (data != null)
     {
       System.err.println("Ignoring additional hover info: " + data
@@ -1154,8 +1108,7 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
           // see JAL-623 - need method of matching pasted data up
           {
             pdb = getSsm().setMapping(getSequence()[pe], getChains()[pe],
-                    pdbfile, DataSourceType.PASTE,
-                    getIProgressIndicator());
+                    pdbfile, DataSourceType.PASTE, getIProgressIndicator());
             getPdbEntry(modelnum).setFile("INLINE" + pdb.getId());
             matches = true;
             foundEntry = true;
@@ -1330,7 +1283,9 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
 
   public void showHelp()
   {
-    showUrl("http://jmol.sourceforge.net/docs/JmolUserGuide/", "jmolHelp");
+    showUrl("http://wiki.jmol.org"
+    // BH 2018 "http://jmol.sourceforge.net/docs/JmolUserGuide/"
+            , "jmolHelp");
   }
 
   /**
@@ -1354,7 +1309,6 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
    */
   public abstract void showConsole(boolean show);
 
-  
   public static Viewer getJmolData(JmolParser jmolParser)
   {
     return (Viewer) JmolViewer.allocateViewer(null, null, null, null, null,
@@ -1402,9 +1356,9 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
           String commandOptions, final Container consolePanel,
           String buttonsToShow)
   {
-    
+
     System.err.println("Allocating Jmol Viewer: " + commandOptions);
-    
+
     if (commandOptions == null)
     {
       commandOptions = "";
@@ -1414,12 +1368,17 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
             htmlName + ((Object) this).toString(), documentBase, codeBase,
             commandOptions, this);
 
-    viewer.setJmolStatusListener(this); // extends JmolCallbackListener
+    viewer.setJmolStatusListener(this); 
+    
+    // BH how about extending Jmol's status listener? 
 
-    try {
+    try
+    {
       console = createJmolConsole(consolePanel, buttonsToShow);
-    } catch (Throwable e) {
-      System.err.println("Could not create Jmol application console. " + e.getMessage());
+    } catch (Throwable e)
+    {
+      System.err.println("Could not create Jmol application console. "
+              + e.getMessage());
       e.printStackTrace();
     }
     if (consolePanel != null)
@@ -1433,8 +1392,8 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
   protected abstract JmolAppConsoleInterface createJmolConsole(
           Container consolePanel, String buttonsToShow);
 
-  // BH 2018 -- Jmol console is not working due to problems with styled documents.
-  
+  // BH 2018 -- Jmol console is not working due to problems with styled
+  // documents.
 
   protected org.jmol.api.JmolAppConsoleInterface console = null;
 
@@ -1442,20 +1401,20 @@ public abstract class JalviewJmolBinding extends AAStructureBindingModel
   public void setBackgroundColour(java.awt.Color col)
   {
     jmolHistory(false);
-    jmolScript("background [" + col.getRed() + ","
-            + col.getGreen() + "," + col.getBlue() + "];");
+    jmolScript("background [" + col.getRed() + "," + col.getGreen() + ","
+            + col.getBlue() + "];");
     jmolHistory(true);
   }
 
   private String jmolScript(String script)
   {
-    
+
     System.err.println(">>Jmol>> " + script);
-    
+
     String s = viewer.scriptWait(script);
-    
+
     System.err.println("<<Jmol<< " + s);
-    
+
     return s;
   }