2 * Jalview - A Sequence Alignment Editor and Viewer
3 * Copyright (C) 2007 AM Waterhouse, J Procter, G Barton, M Clamp, S Searle
5 * This program is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU General Public License
7 * as published by the Free Software Foundation; either version 2
8 * of the License, or (at your option) any later version.
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA
20 package jalview.appletgui;
24 import java.awt.event.*;
26 import jalview.datamodel.*;
27 import jalview.structure.*;
30 import org.jmol.api.*;
31 import org.jmol.adapter.smarter.SmarterJmolAdapter;
33 import org.jmol.popup.*;
34 import jalview.schemes.*;
37 public class AppletJmol extends EmbmenuFrame
38 implements StructureListener, JmolStatusListener,
39 KeyListener, ActionListener, ItemListener
42 Menu fileMenu = new Menu("File");
43 Menu viewMenu = new Menu("View");
44 Menu coloursMenu = new Menu("Colours");
45 Menu chainMenu = new Menu("Show Chain");
46 Menu helpMenu = new Menu("Help");
47 MenuItem mappingMenuItem = new MenuItem("View Mapping");
49 CheckboxMenuItem seqColour = new CheckboxMenuItem("By Sequence", true);
50 MenuItem chain = new MenuItem("By Chain");
51 MenuItem charge = new MenuItem("Charge & Cysteine");
52 MenuItem zappo = new MenuItem("Zappo");
53 MenuItem taylor = new MenuItem("Taylor");
54 MenuItem hydro = new MenuItem("Hydrophobicity");
55 MenuItem helix = new MenuItem("Helix Propensity");
56 MenuItem strand = new MenuItem("Strand Propensity");
57 MenuItem turn = new MenuItem("Turn Propensity");
58 MenuItem buried = new MenuItem("Buried Index");
59 MenuItem user = new MenuItem("User Defined Colours");
61 MenuItem jmolHelp = new MenuItem("Jmol Help");
71 StructureSelectionManager ssm;
72 RenderPanel renderPanel;
74 String fileLoadingError;
77 boolean colourBySequence = true;
78 Vector atomsPicked = new Vector();
80 public AppletJmol(PDBEntry pdbentry,
89 this.pdbentry = pdbentry;
91 String alreadyMapped = StructureSelectionManager
92 .getStructureSelectionManager()
93 .alreadyMappedToFile(pdbentry.getId());
95 if (alreadyMapped != null)
97 StructureSelectionManager.getStructureSelectionManager()
98 .setMapping(seq, chains, pdbentry.getFile(), protocol);
99 //PROMPT USER HERE TO ADD TO NEW OR EXISTING VIEW?
100 //FOR NOW, LETS JUST OPEN A NEW WINDOW
102 MenuBar menuBar = new MenuBar();
103 menuBar.add(fileMenu);
104 fileMenu.add(mappingMenuItem);
105 menuBar.add(viewMenu);
106 mappingMenuItem.addActionListener(this);
107 viewMenu.add(chainMenu);
108 menuBar.add(coloursMenu);
109 menuBar.add(helpMenu);
111 charge.addActionListener(this);
112 hydro.addActionListener(this);
113 chain.addActionListener(this);
114 seqColour.addItemListener(this);
115 zappo.addActionListener(this);
116 taylor.addActionListener(this);
117 helix.addActionListener(this);
118 strand.addActionListener(this);
119 turn.addActionListener(this);
120 buried.addActionListener(this);
121 user.addActionListener(this);
123 jmolHelp.addActionListener(this);
125 coloursMenu.add(seqColour);
126 coloursMenu.add(chain);
127 coloursMenu.add(charge);
128 coloursMenu.add(zappo);
129 coloursMenu.add(taylor);
130 coloursMenu.add(hydro);
131 coloursMenu.add(helix);
132 coloursMenu.add(strand);
133 coloursMenu.add(turn);
134 coloursMenu.add(buried);
135 coloursMenu.add(user);
137 helpMenu.add(jmolHelp);
141 renderPanel = new RenderPanel();
142 embedMenuIfNeeded(renderPanel);
143 this.add(renderPanel, BorderLayout.CENTER);
144 viewer = JmolViewer.allocateViewer(renderPanel, new SmarterJmolAdapter());
146 viewer.setAppletContext("jalview",
147 ap.av.applet.getDocumentBase(),
148 ap.av.applet.getCodeBase(),
151 viewer.setJmolStatusListener(this);
153 jmolpopup = JmolPopup.newJmolPopup(viewer);
155 this.addWindowListener(new WindowAdapter()
157 public void windowClosing(WindowEvent evt)
164 if(pdbentry.getFile()!=null)
166 if (protocol.equals(AppletFormatAdapter.PASTE))
167 loadInline(pdbentry.getFile());
169 viewer.openFile(pdbentry.getFile());
172 jalview.bin.JalviewLite.addFrame(this, "Jmol", 400,400);
175 public void loadInline(String string)
178 viewer.openStringInline(string);
182 void setChainMenuItems(Vector chains)
184 chainMenu.removeAll();
186 MenuItem menuItem = new MenuItem("All");
187 menuItem.addActionListener(this);
189 chainMenu.add(menuItem);
191 CheckboxMenuItem menuItemCB;
192 for (int c = 0; c < chains.size(); c++)
194 menuItemCB = new CheckboxMenuItem(chains.elementAt(c).toString(), true);
195 menuItemCB.addItemListener(this);
196 chainMenu.add(menuItemCB);
200 boolean allChainsSelected = false;
203 StringBuffer cmd = new StringBuffer();
204 for (int i = 0; i < chainMenu.getItemCount(); i++)
206 if (chainMenu.getItem(i) instanceof CheckboxMenuItem)
208 CheckboxMenuItem item = (CheckboxMenuItem) chainMenu.getItem(i);
210 cmd.append(":" + item.getLabel() + " or ");
214 if (cmd.length() > 0)
215 cmd.setLength(cmd.length() - 4);
217 viewer.evalString("select *;restrict "
218 + cmd + ";cartoon;center " + cmd);
224 viewer.setModeMouse(org.jmol.viewer.JmolConstants.MOUSE_NONE);
225 viewer.evalStringQuiet("zap");
226 viewer.setJmolStatusListener(null);
229 //We'll need to find out what other
230 // listeners need to be shut down in Jmol
231 StructureSelectionManager
232 .getStructureSelectionManager()
233 .removeStructureViewerListener(this, pdbentry.getId());
235 this.setVisible(false);
238 public void actionPerformed(ActionEvent evt)
240 if(evt.getSource()==mappingMenuItem)
242 jalview.appletgui.CutAndPasteTransfer cap
243 = new jalview.appletgui.CutAndPasteTransfer(false, null);
244 Frame frame = new Frame();
247 jalview.bin.JalviewLite.addFrame(frame, "PDB - Sequence Mapping", 550,
250 StructureSelectionManager.getStructureSelectionManager().printMapping(
254 else if (evt.getSource() == charge)
256 colourBySequence = false;
257 seqColour.setState(false);
258 viewer.evalStringQuiet("select *;color white;select ASP,GLU;color red;"
259 +"select LYS,ARG;color blue;select CYS;color yellow");
262 else if (evt.getSource() == chain)
264 colourBySequence = false;
265 seqColour.setState(false);
266 viewer.evalStringQuiet("select *;color chain");
268 else if (evt.getSource() == zappo)
270 setJalviewColourScheme(new ZappoColourScheme());
272 else if (evt.getSource() == taylor)
274 setJalviewColourScheme(new TaylorColourScheme());
276 else if (evt.getSource() == hydro)
278 setJalviewColourScheme(new HydrophobicColourScheme());
280 else if (evt.getSource() == helix)
282 setJalviewColourScheme(new HelixColourScheme());
284 else if (evt.getSource() == strand)
286 setJalviewColourScheme(new StrandColourScheme());
288 else if (evt.getSource() == turn)
290 setJalviewColourScheme(new TurnColourScheme());
292 else if (evt.getSource() == buried)
294 setJalviewColourScheme(new BuriedColourScheme());
296 else if (evt.getSource() == user)
298 new UserDefinedColours(this);
300 else if(evt.getSource() == jmolHelp)
303 ap.av.applet.getAppletContext().showDocument(
304 new java.net.URL("http://jmol.sourceforge.net/docs/JmolUserGuide/"),
306 }catch(java.net.MalformedURLException ex){}
310 allChainsSelected = true;
311 for (int i = 0; i < chainMenu.getItemCount(); i++)
313 if (chainMenu.getItem(i) instanceof CheckboxMenuItem)
314 ( (CheckboxMenuItem) chainMenu.getItem(i)).setState(true);
317 allChainsSelected = false;
321 public void setJalviewColourScheme(ColourSchemeI cs)
323 colourBySequence = false;
324 seqColour.setState(false);
333 Enumeration en = ResidueProperties.aa3Hash.keys();
334 StringBuffer command = new StringBuffer("select *;color white;");
335 while(en.hasMoreElements())
337 res = en.nextElement().toString();
338 index = ((Integer) ResidueProperties.aa3Hash.get(res)).intValue();
342 col = cs.findColour(ResidueProperties.aa[index].charAt(0));
344 command.append("select "+res+";color["
346 + col.getGreen() + ","
347 + col.getBlue() + "];");
350 viewer.evalStringQuiet(command.toString());
353 public void itemStateChanged(ItemEvent evt)
355 if (evt.getSource() == seqColour)
358 colourBySequence = seqColour.getState();
359 colourBySequence(ap);
361 else if (!allChainsSelected)
365 public void keyPressed(KeyEvent evt)
367 if (evt.getKeyCode() == KeyEvent.VK_ENTER
368 && scriptWindow.isVisible())
370 viewer.evalString(inputLine.getText());
371 history.append("\n$ "+inputLine.getText());
372 inputLine.setText("");
377 public void keyTyped(KeyEvent evt)
380 public void keyReleased(KeyEvent evt){}
382 //////////////////////////////////
384 public String getPdbFile()
392 public void mouseOverStructure(int atomIndex, String strInfo)
396 int chainSeparator = strInfo.indexOf(":");
398 if(chainSeparator==-1)
399 chainSeparator = strInfo.indexOf(".");
401 pdbResNum = Integer.parseInt(
402 strInfo.substring(strInfo.indexOf("]")+ 1, chainSeparator));
406 if (strInfo.indexOf(":") > -1)
407 chainId = strInfo.substring
408 (strInfo.indexOf(":")+1, strInfo.indexOf("."));
414 if (lastMessage == null || !lastMessage.equals(strInfo))
415 ssm.mouseOverStructure(pdbResNum, chainId, pdbentry.getFile());
417 lastMessage = strInfo;
420 StringBuffer resetLastRes = new StringBuffer();
421 StringBuffer eval = new StringBuffer();
423 public void highlightAtom(int atomIndex, int pdbResNum, String chain, String pdbfile)
425 if (!pdbfile.equals(pdbentry.getFile()))
428 if (resetLastRes.length() > 0)
430 viewer.evalStringQuiet(resetLastRes.toString());
434 eval.append("select " + pdbResNum);
436 resetLastRes.setLength(0);
437 resetLastRes.append("select " + pdbResNum);
439 if (!chain.equals(" "))
441 eval.append(":" + chain);
442 resetLastRes.append(":" + chain);
445 eval.append(";wireframe 100;"+eval.toString()+".CA;");
447 resetLastRes.append(";wireframe 0;"+resetLastRes.toString()+".CA;spacefill 0;");
449 eval.append("spacefill 200;select none");
451 viewer.evalStringQuiet(eval.toString());
455 public void updateColours(Object source)
457 colourBySequence( (AlignmentPanel) source);
460 //End StructureListener
461 ////////////////////////////
463 public Color getColour(int atomIndex, int pdbResNum, String chain, String pdbfile)
465 if (!pdbfile.equals(pdbentry.getFile()))
468 return new Color(viewer.getAtomArgb(atomIndex));
472 FeatureRenderer fr=null;
473 public void colourBySequence(AlignmentPanel sourceap)
477 if (!colourBySequence)
480 StructureMapping[] mapping = ssm.getMapping(pdbentry.getFile());
482 if (mapping.length < 1)
485 SequenceRenderer sr = new SequenceRenderer(ap.av);
487 boolean showFeatures = false;
489 if (ap.av.showSequenceFeatures)
494 fr = new jalview.appletgui.FeatureRenderer(ap.av);
497 fr.transferSettings(ap.seqPanel.seqCanvas.getFeatureRenderer());
500 StringBuffer command = new StringBuffer();
503 for (int s = 0; s < sequence.length; s++)
505 for (int sp,m = 0; m < mapping.length; m++)
507 if (mapping[m].getSequence() == sequence[s]
508 && (sp=ap.av.alignment.findIndex(sequence[s])) > -1)
510 SequenceI asp = ap.av.alignment.getSequenceAt(sp);
511 for (int r = 0; r < asp.getLength(); r++)
513 // no mapping to gaps in sequence
514 if (jalview.util.Comparison.isGap(asp.getCharAt(r)))
518 int pos = mapping[m].getPDBResNum(
519 asp.findPosition(r));
522 if (pos < 1 || pos == lastPos)
527 Color col = sr.getResidueBoxColour(sequence[s], r);
530 col = fr.findFeatureColour(col, sequence[s], r);
532 if (command.toString().endsWith(":" + mapping[m].getChain() +
535 + col.getGreen() + ","
536 + col.getBlue() + "]"))
538 command = condenseCommand(command.toString(), pos);
542 command.append(";select " + pos);
544 if (!mapping[m].getChain().equals(" "))
546 command.append(":" + mapping[m].getChain());
549 command.append(";color["
551 + col.getGreen() + ","
552 + col.getBlue() + "]");
559 if (lastCommand == null || !lastCommand.equals(command.toString()))
561 viewer.evalStringQuiet(command.toString());
563 lastCommand = command.toString();
567 StringBuffer condenseCommand(String command, int pos)
570 StringBuffer sb = new StringBuffer(command.substring(0, command.lastIndexOf("select")+7));
572 command = command.substring(sb.length());
576 if (command.indexOf("-") > -1)
578 start = command.substring(0,command.indexOf("-"));
582 start = command.substring(0, command.indexOf(":"));
585 sb.append(start+"-"+pos+command.substring(command.indexOf(":")));
590 /////////////////////////////////
593 public String eval(String strEval)
595 // System.out.println(strEval);
596 //"# 'eval' is implemented only for the applet.";
600 public void createImage(String file, String type, int quality)
603 public void setCallbackFunction(String callbackType,
604 String callbackFunction)
607 public void notifyFileLoaded(String fullPathName, String fileName,
608 String modelName, Object clientFile,
613 fileLoadingError = errorMsg;
618 fileLoadingError = null;
620 if (fileName != null)
623 jmolpopup.updateComputedMenus();
624 viewer.evalStringQuiet(
625 "select backbone;restrict;cartoon;wireframe off;spacefill off");
627 ssm = StructureSelectionManager.getStructureSelectionManager();
632 pdb = ssm.setMapping(sequence,chains,
634 AppletFormatAdapter.PASTE);
635 pdbentry.setFile("INLINE"+pdb.id);
639 pdb = ssm.setMapping(sequence,chains,
641 AppletFormatAdapter.URL);
644 pdbentry.setId(pdb.id);
646 ssm.addStructureViewerListener(this);
648 Vector chains = new Vector();
649 for (int i = 0; i < pdb.chains.size(); i++)
651 chains.addElement( ( (MCview.PDBChain) pdb.chains.elementAt(i)).id);
653 setChainMenuItems(chains);
655 colourBySequence(ap);
657 StringBuffer title = new StringBuffer(sequence[0].getName() + ":" +
660 if (pdbentry.getProperty() != null)
662 if (pdbentry.getProperty().get("method") != null)
664 title.append(" Method: ");
665 title.append(pdbentry.getProperty().get("method"));
667 if (pdbentry.getProperty().get("chains") != null)
669 title.append(" Chain:");
670 title.append(pdbentry.getProperty().get("chains"));
674 this.setTitle(title.toString());
681 public void notifyFrameChanged(int frameNo)
683 boolean isAnimationRunning = (frameNo <= -2);
686 public void notifyScriptStart(String statusMessage, String additionalInfo)
689 public void sendConsoleEcho(String strEcho)
691 if (scriptWindow == null)
694 history.append("\n"+strEcho);
697 public void sendConsoleMessage(String strStatus)
699 if(history!=null && strStatus!=null
700 && !strStatus.equals("Script completed"))
702 history.append("\n"+strStatus);
706 public void notifyScriptTermination(String strStatus, int msWalltime)
709 public void handlePopupMenu(int x, int y)
711 jmolpopup.show(x, y);
714 public void notifyNewPickingModeMeasurement(int iatom, String strMeasure)
716 notifyAtomPicked(iatom, strMeasure);
719 public void notifyNewDefaultModeMeasurement(int count, String strInfo)
722 public void notifyAtomPicked(int atomIndex, String strInfo)
725 int chainSeparator = strInfo.indexOf(":");
727 if(chainSeparator==-1)
728 chainSeparator = strInfo.indexOf(".");
731 strInfo.substring(strInfo.indexOf("]")+ 1, chainSeparator);
734 if (strInfo.indexOf(":") > -1)
735 picked+=strInfo.substring(strInfo.indexOf(":")+1,
736 strInfo.indexOf("."));
740 if (!atomsPicked.contains(picked))
742 viewer.evalString("select "+picked+";label %n %r:%c");
743 atomsPicked.addElement(picked);
747 viewer.evalString("select "+picked+";label off");
748 atomsPicked.removeElement(picked);
752 public void notifyAtomHovered(int atomIndex, String strInfo)
754 mouseOverStructure(atomIndex, strInfo);
757 public void sendSyncScript(String script, String appletName)
760 public void showUrl(String url)
763 ap.av.applet.getAppletContext().showDocument(new java.net.URL(url),
765 }catch(java.net.MalformedURLException ex)
769 public void showConsole(boolean showConsole)
771 if (scriptWindow == null)
773 scriptWindow = new Panel(new BorderLayout());
774 inputLine = new TextField();
775 history = new TextArea(5, 40);
776 scriptWindow.add(history, BorderLayout.CENTER);
777 scriptWindow.add(inputLine, BorderLayout.SOUTH);
778 add(scriptWindow, BorderLayout.SOUTH);
779 scriptWindow.setVisible(false);
780 history.setEditable(false);
781 inputLine.addKeyListener(this);
784 scriptWindow.setVisible(!scriptWindow.isVisible());
788 public float functionXY(String functionName, int x, int y)
793 ///End JmolStatusListener
794 ///////////////////////////////
800 Dimension currentSize = new Dimension();
801 Rectangle rectClip = new Rectangle();
803 public void update(Graphics g) {
806 public void paint(Graphics g)
808 currentSize = this.getSize();
809 rectClip = g.getClipBounds();
813 g.setColor(Color.black);
814 g.fillRect(0, 0, currentSize.width, currentSize.height);
815 g.setColor(Color.white);
816 g.setFont(new Font("Verdana", Font.BOLD, 14));
817 g.drawString("Retrieving PDB data....", 20, currentSize.height / 2);
821 viewer.renderScreenImage(g, currentSize, rectClip);