1 /* Jmol 12.0 script library Jmol.js 9:48 PM 1/31/2011 Bob Hanson
\r
3 checkbox heirarchy -- see http://chemapps.stolaf.edu/jmol/docs/examples-11/check.htm
\r
7 * Copyright (C) 2004-2005 Miguel, Jmol Development, www.jmol.org
\r
9 * Contact: hansonr@stolaf.edu
\r
11 * This library is free software; you can redistribute it and/or
\r
12 * modify it under the terms of the GNU Lesser General Public
\r
13 * License as published by the Free Software Foundation; either
\r
14 * version 2.1 of the License, or (at your option) any later version.
\r
16 * This library is distributed in the hope that it will be useful,
\r
17 * but WITHOUT ANY WARRANTY; without even the implied warranty of
\r
18 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
\r
19 * Lesser General Public License for more details.
\r
21 * You should have received a copy of the GNU Lesser General Public
\r
22 * License along with this library; if not, write to the Free Software
\r
23 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
\r
27 // for documentation see www.jmol.org/jslibrary
\r
29 try{if(typeof(_jmol)!="undefined")exit()
\r
31 // place "?NOAPPLET" on your command line to check applet control action with a textarea
\r
32 // place "?JMOLJAR=xxxxx" to use a specific jar file
\r
34 // bob hanson -- jmolResize(w,h) -- resizes absolutely or by percent (w or h 0.5 means 50%)
\r
35 // angel herraez -- update of jmolResize(w,h,targetSuffix) so it is not tied to first applet
\r
36 // bob hanson -- jmolEvaluate -- evaluates molecular math 8:37 AM 2/23/2007
\r
37 // bob hanson -- jmolScriptMessage -- returns all "scriptStatus" messages 8:37 AM 2/23/2007
\r
38 // bob hanson -- jmolScriptEcho -- returns all "scriptEcho" messages 8:37 AM 2/23/2007
\r
39 // bob hanson -- jmolScriptWait -- 11:31 AM 5/2/2006
\r
40 // bob hanson -- remove trailing separatorHTML in radio groups -- 12:18 PM 5/6/2006
\r
41 // bob hanson -- adds support for dynamic DOM script nodes 7:04 AM 5/19/2006
\r
42 // bob hanson -- adds try/catch for wiki - multiple code passes 7:05 AM 5/19/2006
\r
43 // bob hanson -- auto-initiates to defaultdir/defaultjar -- change as desired.
\r
44 // bob hanson -- adding save/restore orientation w/ and w/o delay 11:49 AM 5/25/2006
\r
45 // bob hanson -- adding AjaxJS service 11:16 AM 6/3/2006
\r
46 // bob hanson -- fix for iframes not available for finding applet
\r
47 // bob hanson -- added applet fake ?NOAPPLET URL flag
\r
48 // bob hanson -- added jmolSetCallback(calbackName, funcName) 3:32 PM 6/13/2006
\r
49 // used PRIOR to jmolApplet() or jmolAppletInline()
\r
50 // added 4th array element in jmolRadioGroup -- title
\r
51 // added <span> and id around link, checkbox, radio, menu
\r
52 // fixing AJAX loads for MSIE/Opera-Mozilla incompatibility
\r
53 // -- renamed Jmol-11.js from Jmol-new.js; JmolApplet.jar from JmolAppletProto.jar
\r
54 // renamed Jmol.js for Jmol 11 distribution
\r
55 // -- modified jmolRestoreOrientation() to be immediate, no 1-second delay
\r
56 // bob hanson -- jmolScriptWait always returns a string -- 11:23 AM 9/16/2006
\r
57 // bh -- jmolCommandInput()
\r
58 // bh -- jmolSetTranslation(TF) -- forces translation even if there might be message callback issues
\r
59 // bh -- minor fixes suggested by Angel
\r
60 // bh -- adds jmolSetSyncId() and jmolGetSyncId()
\r
61 // bh 3/2008 -- adds jmolAppendInlineScript() and jmolAppendInlineArray()
\r
62 // bh 3/2008 -- fixes IE7 bug in relation to jmolLoadInlineArray()
\r
63 // bh 6/2008 -- adds jmolSetAppletWindow()
\r
64 // Angel H. 6/2008 -- added html <label> tags to checkboxes and radio buttons [in jmolCheckbox() and _jmolRadio() functions]
\r
65 // bh 7/2008 -- code fix "for(i..." not "for(var i..."
\r
66 // bh 12/2008 -- jmolLoadInline, jmolLoadInlineArray, jmolLoadInlineScript, jmolAppendInlineScript, jmolAppendInlineArray all return error message or null (Jmol 11.7.16)
\r
67 // bh 12/2008 -- jmolScriptWaitOutput() -- waits for script to complete and delivers output normally sent to console
\r
69 // bh 5/2009 -- Support for XHTML using jmolSetXHTML(id)
\r
70 // ah & bh 6/2009 -- New jmolResizeApplet() more flexible, similar to jmolApplet() size syntax
\r
71 // bh 11/2009 -- care in accessing top.document
\r
72 // bh 12/2009 -- added jmolSetParameter(name, value)
\r
73 // bh 12/2009 -- added PARAMS=name:value;name:value;name:value... for command line
\r
74 // bh 12/2009 -- overhaul of target checking
\r
75 // bh 1/2010 -- all _xxxx() methods ALWAYS have complete argument list
\r
76 // bh 1/2010 -- adds option to run a JavaScript function from any Jmol control.
\r
77 // This is accomplished by passing an array rather than a script:
\r
78 // jmolHref([myfunc,"my param 1", "my param 2"], "testing")
\r
79 // function myfunc(jmolControlObject, [myfunc,"my param 1", "my param 2"], target){...}
\r
80 // and allows much more flexibility with responding to controls
\r
81 // bh 4/2010 -- added jmolSetMemoryMb(nMb)
\r
82 // ah 1/2011 -- wider detection of browsers; more browsers now use the object tag instead of the applet tag;
\r
83 // fix of object tag (removed classid) accounts for change of behavior in Chrome
\r
84 // bh 3/2011 -- added jmolLoadAjax_STOLAF_NIH
\r
86 var defaultdir = "."
\r
87 var defaultjar = "JmolApplet.jar"
\r
90 // Note added 12:41 PM 9/21/2008 by Bob Hanson, hansonr@stolaf.edu:
\r
92 // JMOLJAR=xxxxx.jar on the URL for this page will override
\r
93 // the JAR file specified in the jmolInitialize() call.
\r
95 // The idea is that it can be very useful to test a web page with different JAR files
\r
96 // Or for an expert user to substitute a signed applet for an unsigned one
\r
97 // so as to use a broader range of models or to create JPEG files, for example.
\r
99 // If the JAR file is not in the current directory (has any sort of "/" in its name)
\r
100 // then the user is presented with a warning and asked whether it is OK to change Jar files.
\r
101 // The default action, if the user just presses "OK" is to NOT allow the change.
\r
102 // The user must type the word "yes" in the prompt box for the change to be approved.
\r
104 // If you don't want people to be able to switch in their own JAR file on your page,
\r
105 // simply set this next line to read "var allowJMOLJAR = false".
\r
108 var undefined; // for IE 5 ... wherein undefined is undefined
\r
110 ////////////////////////////////////////////////////////////////
\r
111 // Basic Scripting infrastruture
\r
112 ////////////////////////////////////////////////////////////////
\r
114 function jmolInitialize(codebaseDirectory, fileNameOrUseSignedApplet) {
\r
115 if (_jmol.initialized)
\r
117 _jmol.initialized = true;
\r
118 if(_jmol.jmoljar) {
\r
119 var f = _jmol.jmoljar;
\r
120 if (f.indexOf("/") >= 0) {
\r
121 alert ("This web page URL is requesting that the applet used be " + f + ". This is a possible security risk, particularly if the applet is signed, because signed applets can read and write files on your local machine or network.")
\r
122 var ok = prompt("Do you want to use applet " + f + "? ","yes or no")
\r
124 codebaseDirectory = f.substring(0, f.lastIndexOf("/"));
\r
125 fileNameOrUseSignedApplet = f.substring(f.lastIndexOf("/") + 1);
\r
127 _jmolGetJarFilename(fileNameOrUseSignedApplet);
\r
128 alert("The web page URL was ignored. Continuing using " + _jmol.archivePath + ' in directory "' + codebaseDirectory + '"');
\r
131 fileNameOrUseSignedApplet = f;
\r
134 _jmolSetCodebase(codebaseDirectory);
\r
135 _jmolGetJarFilename(fileNameOrUseSignedApplet);
\r
136 _jmolOnloadResetForms();
\r
139 function jmolSetTranslation(TF) {
\r
140 _jmol.params.doTranslate = ''+TF;
\r
143 function _jmolGetJarFilename(fileNameOrFlag) {
\r
144 _jmol.archivePath =
\r
145 (typeof(fileNameOrFlag) == "string" ? fileNameOrFlag : (fileNameOrFlag ? "JmolAppletSigned" : "JmolApplet") + "0.jar");
\r
148 function jmolSetDocument(doc) {
\r
149 _jmol.currentDocument = doc;
\r
152 function jmolSetAppletColor(boxbgcolor, boxfgcolor, progresscolor) {
\r
154 _jmol.params.boxbgcolor = boxbgcolor;
\r
156 _jmol.params.boxfgcolor = boxfgcolor
\r
157 else if (boxbgcolor == "white" || boxbgcolor == "#FFFFFF")
\r
158 _jmol.params.boxfgcolor = "black";
\r
160 _jmol.params.boxfgcolor = "white";
\r
162 _jmol.params.progresscolor = progresscolor;
\r
163 if (_jmol.debugAlert)
\r
164 alert(" boxbgcolor=" + _jmol.params.boxbgcolor +
\r
165 " boxfgcolor=" + _jmol.params.boxfgcolor +
\r
166 " progresscolor=" + _jmol.params.progresscolor);
\r
169 function jmolSetAppletWindow(w) {
\r
170 _jmol.appletWindow = w;
\r
173 function jmolApplet(size, script, nameSuffix) {
\r
175 return _jmolApplet(size, null, script, nameSuffix);
\r
178 ////////////////////////////////////////////////////////////////
\r
180 ////////////////////////////////////////////////////////////////
\r
182 // undefined means it wasn't there; null means it was explicitly listed as null (so as to skip it)
\r
184 function jmolButton(script, label, id, title) {
\r
186 id != undefined && id != null || (id = "jmolButton" + _jmol.buttonCount);
\r
187 label != undefined && label != null || (label = script.substring(0, 32));
\r
188 ++_jmol.buttonCount;
\r
189 var scriptIndex = _jmolAddScript(script);
\r
190 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><input type='button' name='" + id + "' id='" + id +
\r
191 "' value='" + label +
\r
192 "' onclick='_jmolClick(this," + scriptIndex + _jmol.targetText +
\r
193 ")' onmouseover='_jmolMouseOver(" + scriptIndex +
\r
194 ");return true' onmouseout='_jmolMouseOut()' " +
\r
195 _jmol.buttonCssText + " /></span>";
\r
196 if (_jmol.debugAlert)
\r
198 return _jmolDocumentWrite(t);
\r
201 function jmolCheckbox(scriptWhenChecked, scriptWhenUnchecked,
\r
202 labelHtml, isChecked, id, title) {
\r
204 id != undefined && id != null || (id = "jmolCheckbox" + _jmol.checkboxCount);
\r
205 ++_jmol.checkboxCount;
\r
206 if (scriptWhenChecked == undefined || scriptWhenChecked == null ||
\r
207 scriptWhenUnchecked == undefined || scriptWhenUnchecked == null) {
\r
208 alert("jmolCheckbox requires two scripts");
\r
211 if (labelHtml == undefined || labelHtml == null) {
\r
212 alert("jmolCheckbox requires a label");
\r
215 var indexChecked = _jmolAddScript(scriptWhenChecked);
\r
216 var indexUnchecked = _jmolAddScript(scriptWhenUnchecked);
\r
217 var eospan = "</span>"
\r
218 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><input type='checkbox' name='" + id + "' id='" + id +
\r
219 "' onclick='_jmolCbClick(this," +
\r
220 indexChecked + "," + indexUnchecked + _jmol.targetText +
\r
221 ")' onmouseover='_jmolCbOver(this," + indexChecked + "," +
\r
223 ");return true' onmouseout='_jmolMouseOut()' " +
\r
224 (isChecked ? "checked='true' " : "")+ _jmol.checkboxCssText + " />"
\r
225 if (labelHtml.toLowerCase().indexOf("<td>")>=0) {
\r
229 t += "<label for=\"" + id + "\">" + labelHtml + "</label>" +eospan;
\r
230 if (_jmol.debugAlert)
\r
232 return _jmolDocumentWrite(t);
\r
235 function jmolStartNewRadioGroup() {
\r
236 ++_jmol.radioGroupCount;
\r
239 function jmolRadioGroup(arrayOfRadioButtons, separatorHtml, groupName, id, title) {
\r
242 array: [radio1,radio2,radio3...]
\r
243 where radioN = ["script","label",isSelected,"id","title"]
\r
248 var type = typeof arrayOfRadioButtons;
\r
249 if (type != "object" || type == null || ! arrayOfRadioButtons.length) {
\r
250 alert("invalid arrayOfRadioButtons");
\r
253 separatorHtml != undefined && separatorHtml != null || (separatorHtml = " ");
\r
254 var len = arrayOfRadioButtons.length;
\r
255 jmolStartNewRadioGroup();
\r
256 groupName || (groupName = "jmolRadioGroup" + (_jmol.radioGroupCount - 1));
\r
257 var t = "<span id='"+(id ? id : groupName)+"'>";
\r
258 for (var i = 0; i < len; ++i) {
\r
260 separatorHtml = "";
\r
261 var radio = arrayOfRadioButtons[i];
\r
262 type = typeof radio;
\r
263 if (type == "object") {
\r
264 t += _jmolRadio(radio[0], radio[1], radio[2], separatorHtml, groupName, (radio.length > 3 ? radio[3]: (id ? id : groupName)+"_"+i), (radio.length > 4 ? radio[4] : 0), title);
\r
266 t += _jmolRadio(radio, null, null, separatorHtml, groupName, (id ? id : groupName)+"_"+i, title);
\r
270 if (_jmol.debugAlert)
\r
272 return _jmolDocumentWrite(t);
\r
276 function jmolRadio(script, labelHtml, isChecked, separatorHtml, groupName, id, title) {
\r
278 if (_jmol.radioGroupCount == 0)
\r
279 ++_jmol.radioGroupCount;
\r
280 var t = _jmolRadio(script, labelHtml, isChecked, separatorHtml, groupName, (id ? id : groupName + "_" + _jmol.radioCount), title ? title : 0);
\r
281 if (_jmol.debugAlert)
\r
283 return _jmolDocumentWrite(t);
\r
286 function jmolLink(script, label, id, title) {
\r
288 id != undefined && id != null || (id = "jmolLink" + _jmol.linkCount);
\r
289 label != undefined && label != null || (label = script.substring(0, 32));
\r
291 var scriptIndex = _jmolAddScript(script);
\r
292 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><a name='" + id + "' id='" + id +
\r
293 "' href='javascript:_jmolClick(this," + scriptIndex + _jmol.targetText + ");' onmouseover='_jmolMouseOver(" + scriptIndex +
\r
294 ");return true;' onmouseout='_jmolMouseOut()' " +
\r
295 _jmol.linkCssText + ">" + label + "</a></span>";
\r
296 if (_jmol.debugAlert)
\r
298 return _jmolDocumentWrite(t);
\r
301 function jmolCommandInput(label, size, id, title) {
\r
303 id != undefined && id != null || (id = "jmolCmd" + _jmol.cmdCount);
\r
304 label != undefined && label != null || (label = "Execute");
\r
305 size != undefined && !isNaN(size) || (size = 60);
\r
307 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><input name='" + id + "' id='" + id +
\r
308 "' size='"+size+"' onkeypress='_jmolCommandKeyPress(event,\""+id+"\"" + _jmol.targetText + ")'><input type=button value = '"+label+"' onclick='jmolScript(document.getElementById(\""+id+"\").value" + _jmol.targetText + ")' /></span>";
\r
309 if (_jmol.debugAlert)
\r
311 return _jmolDocumentWrite(t);
\r
314 function _jmolCommandKeyPress(e, id, target) {
\r
315 var keycode = (window.event ? window.event.keyCode : e ? e.which : 0);
\r
316 if (keycode == 13) {
\r
317 var inputBox = document.getElementById(id)
\r
318 _jmolScriptExecute(inputBox, inputBox.value, target)
\r
322 function _jmolScriptExecute(element,script,target) {
\r
323 if (typeof(script) == "object")
\r
324 script[0](element, script, target)
\r
326 jmolScript(script, target)
\r
329 function jmolMenu(arrayOfMenuItems, size, id, title) {
\r
331 id != undefined && id != null || (id = "jmolMenu" + _jmol.menuCount);
\r
333 var type = typeof arrayOfMenuItems;
\r
334 if (type != null && type == "object" && arrayOfMenuItems.length) {
\r
335 var len = arrayOfMenuItems.length;
\r
336 if (typeof size != "number" || size == 1)
\r
340 var sizeText = size ? " size='" + size + "' " : "";
\r
341 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><select name='" + id + "' id='" + id +
\r
342 "' onChange='_jmolMenuSelected(this" + _jmol.targetText + ")'" +
\r
343 sizeText + _jmol.menuCssText + ">";
\r
344 for (var i = 0; i < len; ++i) {
\r
345 var menuItem = arrayOfMenuItems[i];
\r
346 type = typeof menuItem;
\r
348 var isSelected = undefined;
\r
349 if (type == "object" && menuItem != null) {
\r
350 script = menuItem[0];
\r
351 text = menuItem[1];
\r
352 isSelected = menuItem[2];
\r
354 script = text = menuItem;
\r
356 text != undefined && text != null || (text = script);
\r
357 if (script=="#optgroup") {
\r
358 t += "<optgroup label='" + text + "'>";
\r
359 } else if (script=="#optgroupEnd") {
\r
360 t += "</optgroup>";
\r
362 var scriptIndex = _jmolAddScript(script);
\r
363 var selectedText = isSelected ? "' selected='true'>" : "'>";
\r
364 t += "<option value='" + scriptIndex + selectedText + text + "</option>";
\r
367 t += "</select></span>";
\r
368 if (_jmol.debugAlert)
\r
370 return _jmolDocumentWrite(t);
\r
374 function jmolHtml(html) {
\r
375 return _jmolDocumentWrite(html);
\r
378 function jmolBr() {
\r
379 return _jmolDocumentWrite("<br />");
\r
382 ////////////////////////////////////////////////////////////////
\r
383 // advanced scripting functions
\r
384 ////////////////////////////////////////////////////////////////
\r
386 function jmolDebugAlert(enableAlerts) {
\r
387 _jmol.debugAlert = (enableAlerts == undefined || enableAlerts)
\r
390 function jmolAppletInline(size, inlineModel, script, nameSuffix) {
\r
392 return _jmolApplet(size, _jmolSterilizeInline(inlineModel),
\r
393 script, nameSuffix);
\r
396 function jmolSetTarget(targetSuffix) {
\r
397 _jmol.targetSuffix = targetSuffix;
\r
398 _jmol.targetText = targetSuffix ? ",\"" + targetSuffix + "\"" : ",0";
\r
401 function jmolScript(script, targetSuffix) {
\r
403 _jmolCheckBrowser();
\r
404 if (targetSuffix == "all") {
\r
406 for (var i = 0; i < appletSuffixes.length; ++i) {
\r
407 var applet = _jmolGetApplet(appletSuffixes[i]);
\r
408 if (applet) applet.script(script);
\r
412 var applet=_jmolGetApplet(targetSuffix);
\r
413 if (applet) applet.script(script);
\r
418 function jmolLoadInline(model, targetSuffix) {
\r
419 if (!model)return "ERROR: NO MODEL"
\r
420 var applet=_jmolGetApplet(targetSuffix);
\r
421 if (!applet)return "ERROR: NO APPLET"
\r
422 if (typeof(model) == "string")
\r
423 return applet.loadInlineString(model, "", false);
\r
425 return applet.loadInlineArray(model, "", false);
\r
429 function jmolLoadInlineScript(model, script, targetSuffix) {
\r
430 if (!model)return "ERROR: NO MODEL"
\r
431 var applet=_jmolGetApplet(targetSuffix);
\r
432 if (!applet)return "ERROR: NO APPLET"
\r
433 return applet.loadInlineString(model, script, false);
\r
437 function jmolLoadInlineArray(ModelArray, script, targetSuffix) {
\r
438 if (!model)return "ERROR: NO MODEL"
\r
439 script || (script="")
\r
440 var applet=_jmolGetApplet(targetSuffix);
\r
441 if (!applet)return "ERROR: NO APPLET"
\r
443 return applet.loadInlineArray(ModelArray, script, false);
\r
446 return applet.loadInlineString(ModelArray.join("\n"), script, false);
\r
450 function jmolAppendInlineArray(ModelArray, script, targetSuffix) {
\r
451 if (!model)return "ERROR: NO MODEL"
\r
452 script || (script="")
\r
453 var applet=_jmolGetApplet(targetSuffix);
\r
454 if (!applet)return "ERROR: NO APPLET"
\r
456 return applet.loadInlineArray(ModelArray, script, true);
\r
459 return applet.loadInlineString(ModelArray.join("\n"), script, true);
\r
463 function jmolAppendInlineScript(model, script, targetSuffix) {
\r
464 if (!model)return "ERROR: NO MODEL"
\r
465 var applet=_jmolGetApplet(targetSuffix);
\r
466 if (!applet)return "ERROR: NO APPLET"
\r
467 return applet.loadInlineString(model, script, true);
\r
470 function jmolCheckBrowser(action, urlOrMessage, nowOrLater) {
\r
471 if (typeof action == "string") {
\r
472 action = action.toLowerCase();
\r
473 action == "alert" || action == "redirect" || action == "popup" || (action = null);
\r
475 if (typeof action != "string")
\r
476 alert("jmolCheckBrowser(action, urlOrMessage, nowOrLater)\n\n" +
\r
477 "action must be 'alert', 'redirect', or 'popup'");
\r
479 if (typeof urlOrMessage != "string")
\r
480 alert("jmolCheckBrowser(action, urlOrMessage, nowOrLater)\n\n" +
\r
481 "urlOrMessage must be a string");
\r
483 _jmol.checkBrowserAction = action;
\r
484 _jmol.checkBrowserUrlOrMessage = urlOrMessage;
\r
487 if (typeof nowOrLater == "string" && nowOrLater.toLowerCase() == "now")
\r
488 _jmolCheckBrowser();
\r
491 ////////////////////////////////////////////////////////////////
\r
492 // Cascading Style Sheet Class support
\r
493 ////////////////////////////////////////////////////////////////
\r
495 function jmolSetAppletCssClass(appletCssClass) {
\r
496 if (_jmol.hasGetElementById) {
\r
497 _jmol.appletCssClass = appletCssClass;
\r
498 _jmol.appletCssText = appletCssClass ? "class='" + appletCssClass + "' " : "";
\r
502 function jmolSetButtonCssClass(buttonCssClass) {
\r
503 if (_jmol.hasGetElementById) {
\r
504 _jmol.buttonCssClass = buttonCssClass;
\r
505 _jmol.buttonCssText = buttonCssClass ? "class='" + buttonCssClass + "' " : "";
\r
509 function jmolSetCheckboxCssClass(checkboxCssClass) {
\r
510 if (_jmol.hasGetElementById) {
\r
511 _jmol.checkboxCssClass = checkboxCssClass;
\r
512 _jmol.checkboxCssText = checkboxCssClass ? "class='" + checkboxCssClass + "' " : "";
\r
516 function jmolSetRadioCssClass(radioCssClass) {
\r
517 if (_jmol.hasGetElementById) {
\r
518 _jmol.radioCssClass = radioCssClass;
\r
519 _jmol.radioCssText = radioCssClass ? "class='" + radioCssClass + "' " : "";
\r
523 function jmolSetLinkCssClass(linkCssClass) {
\r
524 if (_jmol.hasGetElementById) {
\r
525 _jmol.linkCssClass = linkCssClass;
\r
526 _jmol.linkCssText = linkCssClass ? "class='" + linkCssClass + "' " : "";
\r
530 function jmolSetMenuCssClass(menuCssClass) {
\r
531 if (_jmol.hasGetElementById) {
\r
532 _jmol.menuCssClass = menuCssClass;
\r
533 _jmol.menuCssText = menuCssClass ? "class='" + menuCssClass + "' " : "";
\r
537 ////////////////////////////////////////////////////////////////
\r
538 // functions for INTERNAL USE ONLY which are subject to change
\r
539 // use at your own risk ... you have been WARNED!
\r
540 ////////////////////////////////////////////////////////////////
\r
542 currentDocument: document,
\r
550 appletSuffixes: [],
\r
551 appletWindow: null,
\r
552 allowedJmolSize: [25, 2048, 300], // min, max, default (pixels)
\r
553 /* By setting the _jmol.allowedJmolSize[] variable in the webpage
\r
554 before calling jmolApplet(), limits for applet size can be overriden.
\r
555 2048 standard for GeoWall (http://geowall.geo.lsa.umich.edu/home.html)
\r
563 radioGroupCount: 0,
\r
565 appletCssClass: null,
\r
567 buttonCssClass: null,
\r
569 checkboxCssClass: null,
\r
570 checkboxCssText: "",
\r
571 java_arguments: "-Xmx512m",
\r
572 radioCssClass: null,
\r
574 linkCssClass: null,
\r
576 menuCssClass: null,
\r
583 syncId: ("" + Math.random()).substring(3),
\r
584 progressbar: "true",
\r
585 progresscolor: "blue",
\r
586 boxbgcolor: "black",
\r
587 boxfgcolor: "white",
\r
588 boxmessage: "Downloading JmolApplet ..."
\r
590 ua: navigator.userAgent.toLowerCase(),
\r
591 // uaVersion: parseFloat(navigator.appVersion), // not used
\r
594 browser: "unknown",
\r
596 hasGetElementById: !!document.getElementById,
\r
597 isJavaEnabled: navigator.javaEnabled(),
\r
598 // isNetscape47Win: false, // not used, N4.7 is no longer supported even for detection
\r
599 useIEObject: false,
\r
600 useHtml4Object: false,
\r
602 windowsClassId: "clsid:8AD9C840-044E-11D1-B3E9-00805F499D93",
\r
604 "http://java.sun.com/update/1.6.0/jinstall-6u22-windows-i586.cab",
\r
606 isBrowserCompliant: false,
\r
607 isJavaCompliant: false,
\r
608 isFullyCompliant: false,
\r
610 initialized: false,
\r
611 initChecked: false,
\r
613 browserChecked: false,
\r
614 checkBrowserAction: "alert",
\r
615 checkBrowserUrlOrMessage: null,
\r
617 archivePath: null, // JmolApplet0.jar OR JmolAppletSigned0.jar
\r
619 previousOnloadHandler: null,
\r
622 useNoApplet: false,
\r
628 function _jmolTestUA(candidate) {
\r
630 var index = ua.indexOf(candidate);
\r
633 _jmol.browser = candidate;
\r
634 _jmol.browserVersion = parseFloat(ua.substring(index+candidate.length+1));
\r
638 function _jmolTestOS(candidate) {
\r
639 if (_jmol.ua.indexOf(candidate) < 0)
\r
641 _jmol.os = candidate;
\r
645 _jmolTestUA("konqueror") ||
\r
646 _jmolTestUA("webkit") ||
\r
647 _jmolTestUA("omniweb") ||
\r
648 _jmolTestUA("opera") ||
\r
649 _jmolTestUA("webtv") ||
\r
650 _jmolTestUA("icab") ||
\r
651 _jmolTestUA("msie") ||
\r
652 (_jmol.ua.indexOf("compatible") < 0 && _jmolTestUA("mozilla")); //Netscape, Mozilla, Seamonkey, Firefox and anything assimilated
\r
654 _jmolTestOS("linux") ||
\r
655 _jmolTestOS("unix") ||
\r
656 _jmolTestOS("mac") ||
\r
657 _jmolTestOS("win");
\r
660 isNetscape47Win = (os == "win" && browser == "mozilla" &&
\r
661 browserVersion >= 4.78 && browserVersion <= 4.8);
\r
665 isBrowserCompliant = hasGetElementById;
\r
666 } else if (os == "mac") { // mac is the problem child :-(
\r
667 if (browser == "mozilla" && browserVersion >= 5) {
\r
668 // miguel 2004 11 17
\r
669 // checking the plugins array does not work because
\r
670 // Netscape 7.2 OS X still has Java 1.3.1 listed even though
\r
671 // javaplugin.sf.net is installed to upgrade to 1.4.2
\r
672 eval("try {var v = java.lang.System.getProperty('java.version');" +
\r
673 " _jmol.isBrowserCompliant = v >= '1.4.2';" +
\r
674 " } catch (e) { }");
\r
675 } else if (browser == "opera" && browserVersion <= 7.54) {
\r
676 isBrowserCompliant = false;
\r
678 isBrowserCompliant = hasGetElementById &&
\r
679 !((browser == "msie") ||
\r
680 (browser == "webkit" && browserVersion < 125.12));
\r
682 } else if (os == "linux" || os == "unix") {
\r
683 if (browser == "konqueror" && browserVersion <= 3.3)
\r
684 isBrowserCompliant = false;
\r
686 isBrowserCompliant = hasGetElementById;
\r
687 } else { // other OS
\r
688 isBrowserCompliant = hasGetElementById;
\r
691 // possibly more checks in the future for this
\r
692 isJavaCompliant = isJavaEnabled;
\r
694 isFullyCompliant = isBrowserCompliant && isJavaCompliant;
\r
696 useIEObject = (os == "win" && browser == "msie" && browserVersion >= 5.5);
\r
698 (browser == "mozilla" && browserVersion >= 5) ||
\r
699 (browser == "opera" && browserVersion >= 8) ||
\r
700 (browser == "webkit" && browserVersion >= 412.2);
\r
702 if (top.location.search.indexOf("JMOLJAR=")>=0)
\r
703 jmoljar = top.location.search.split("JMOLJAR=")[1].split("&")[0];
\r
705 // can't access top.location
\r
708 useNoApplet = (top.location.search.indexOf("NOAPPLET")>=0);
\r
710 // can't access top.document
\r
714 function jmolSetMemoryMb(nMb) {
\r
715 _jmol.java_arguments = "-Xmx" + Math.round(nMb) + "m"
\r
718 function jmolSetParameter(name,value) {
\r
719 _jmol.params[name] = value
\r
722 function jmolSetCallback(callbackName,funcName) {
\r
723 _jmol.params[callbackName] = funcName
\r
727 // note this is done FIRST, so it cannot override a setting done by the developer
\r
728 if (top.location.search.indexOf("PARAMS=")>=0) {
\r
729 var pars = unescape(top.location.search.split("PARAMS=")[1].split("&")[0]).split(";");
\r
730 for (var i = 0; i < pars.length; i++) {
\r
731 var p = pars[i].split(":");
\r
732 jmolSetParameter(p[0],p[1]);
\r
736 // can't access top.location
\r
739 function jmolSetSyncId(n) {
\r
740 return _jmol.params["syncId"] = n
\r
743 function jmolGetSyncId() {
\r
744 return _jmol.params["syncId"]
\r
747 function jmolSetLogLevel(n) {
\r
748 _jmol.params.logLevel = ''+n;
\r
751 /* AngelH, mar2007:
\r
752 By (re)setting these variables in the webpage before calling jmolApplet(),
\r
753 a custom message can be provided (e.g. localized for user's language) when no Java is installed.
\r
755 if (noJavaMsg==undefined) var noJavaMsg =
\r
756 "You do not have Java applets enabled in your web browser, or your browser is blocking this applet.<br />\n" +
\r
757 "Check the warning message from your browser and/or enable Java applets in<br />\n" +
\r
758 "your web browser preferences, or install the Java Runtime Environment from <a href='http://www.java.com'>www.java.com</a><br />";
\r
759 if (noJavaMsg2==undefined) var noJavaMsg2 =
\r
760 "You do not have the<br />\n" +
\r
761 "Java Runtime Environment<br />\n" +
\r
762 "installed for applet support.<br />\n" +
\r
763 "Visit <a href='http://www.java.com'>www.java.com</a>";
\r
764 function _jmolApplet(size, inlineModel, script, nameSuffix) {
\r
766 Fixed percent / pixel business, to avoid browser errors:
\r
767 put "px" where needed, avoid where not.
\r
770 Fixed inline escape changing returns to |
\r
773 nameSuffix == undefined && (nameSuffix = appletCount);
\r
774 appletSuffixes.push(nameSuffix);
\r
776 script || (script = "select *");
\r
777 var sz = _jmolGetAppletSize(size);
\r
778 var widthAndHeight = " width='" + sz[0] + "' height='" + sz[1] + "' ";
\r
779 var tHeader, tFooter;
\r
780 codebase || jmolInitialize(".");
\r
781 if (useIEObject || useHtml4Object) {
\r
782 params.archive = archivePath;
\r
783 params.mayscript = 'true';
\r
784 params.codebase = codebase;
\r
785 params.code = 'JmolApplet';
\r
787 "<object name='jmolApplet" + nameSuffix +
\r
788 "' id='jmolApplet" + nameSuffix + "' " + appletCssText + "\n" +
\r
789 widthAndHeight + "\n";
\r
790 tFooter = "</object>";
\r
792 if (java_arguments)
\r
793 params.java_arguments = java_arguments;
\r
794 if (useIEObject) { // use MSFT IE6 object tag with .cab file reference
\r
795 tHeader += " classid='" + windowsClassId + "'\n" +
\r
796 (windowsCabUrl ? " codebase='" + windowsCabUrl + "'\n" : "") + ">\n";
\r
797 } else if (useHtml4Object) { // use HTML4 object tag
\r
798 tHeader += " type='application/x-java-applet'\n>\n";
\r
799 /* " classid='java:JmolApplet'\n" + AH removed this
\r
800 Chromium Issue 62076: Java Applets using an <object> with a classid paramater don't load.
\r
801 http://code.google.com/p/chromium/issues/detail?id=62076
\r
802 They say this is the correct behavior according to the spec, and there's no indication at this point
\r
803 that WebKit will be changing the handling, so eventually Safari will acquire this behavior too.
\r
804 Removing the classid parameter seems to be well tolerated by all browsers (even IE!).
\r
806 } else { // use applet tag
\r
808 "<applet name='jmolApplet" + nameSuffix +
\r
809 "' id='jmolApplet" + nameSuffix + "' " + appletCssText + "\n" +
\r
810 widthAndHeight + "\n" +
\r
811 " code='JmolApplet'" +
\r
812 " archive='" + archivePath + "' codebase='" + codebase + "'\n" +
\r
813 " mayscript='true'>\n";
\r
814 tFooter = "</applet>";
\r
817 if (useIEObject || useHtml4Object) {
\r
818 var szX = "width:" + sz[0]
\r
819 if ( szX.indexOf("%")==-1 ) szX+="px"
\r
820 var szY = "height:" + sz[1]
\r
821 if ( szY.indexOf("%")==-1 ) szY+="px"
\r
823 "<p style='background-color:yellow; color:black; " +
\r
824 szX + ";" + szY + ";" +
\r
825 // why doesn't this vertical-align work?
\r
826 "text-align:center;vertical-align:middle;'>\n" +
\r
831 "<table bgcolor='yellow'><tr>" +
\r
832 "<td align='center' valign='middle' " + widthAndHeight + "><font color='black'>\n" +
\r
834 "</font></td></tr></table>";
\r
836 params.loadInline = (inlineModel ? inlineModel : "");
\r
837 params.script = (script ? _jmolSterilizeScript(script) : "");
\r
838 var t = tHeader + _jmolParams() + visitJava + tFooter;
\r
839 jmolSetTarget(nameSuffix);
\r
840 ready["jmolApplet" + nameSuffix] = false;
\r
841 if (_jmol.debugAlert)
\r
843 return _jmolDocumentWrite(t);
\r
847 function _jmolParams() {
\r
849 for (var i in _jmol.params)
\r
850 if(_jmol.params[i]!="")
\r
851 t+=" <param name='"+i+"' value='"+_jmol.params[i]+"' />\n";
\r
855 function _jmolInitCheck() {
\r
856 if (_jmol.initChecked)
\r
858 _jmol.initChecked = true;
\r
859 jmolInitialize(defaultdir, defaultjar)
\r
862 function _jmolCheckBrowser() {
\r
864 if (browserChecked)
\r
866 browserChecked = true;
\r
868 if (isFullyCompliant)
\r
871 if (checkBrowserAction == "redirect")
\r
872 location.href = checkBrowserUrlOrMessage;
\r
873 else if (checkBrowserAction == "popup")
\r
874 _jmolPopup(checkBrowserUrlOrMessage);
\r
876 var msg = checkBrowserUrlOrMessage;
\r
878 msg = "Your web browser is not fully compatible with Jmol\n\n" +
\r
879 "browser: " + browser +
\r
880 " version: " + browserVersion +
\r
882 " isBrowserCompliant: " + isBrowserCompliant +
\r
883 " isJavaCompliant: " + isJavaCompliant +
\r
891 function jmolSetXHTML(id) {
\r
892 _jmol.isXHTML = true
\r
893 _jmol.XhtmlElement = null
\r
894 _jmol.XhtmlAppendChild = false
\r
896 _jmol.XhtmlElement = document.getElementById(id)
\r
897 _jmol.XhtmlAppendChild = true
\r
901 function _jmolDocumentWrite(text) {
\r
902 if (_jmol.currentDocument) {
\r
903 if (_jmol.isXHTML && !_jmol.XhtmlElement) {
\r
904 var s = document.getElementsByTagName("script")
\r
905 _jmol.XhtmlElement = s.item(s.length - 1)
\r
906 _jmol.XhtmlAppendChild = false
\r
908 if (_jmol.XhtmlElement) {
\r
909 _jmolDomDocumentWrite(text)
\r
911 _jmol.currentDocument.write(text);
\r
917 function _jmolDomDocumentWrite(data) {
\r
921 while (Ptr[0] < data.length) {
\r
922 var child = _jmolGetDomElement(data, Ptr)
\r
924 if (_jmol.XhtmlAppendChild)
\r
925 _jmol.XhtmlElement.appendChild(child)
\r
927 _jmol.XhtmlElement.parentNode.insertBefore(child, _jmol.XhtmlElement);
\r
930 function _jmolGetDomElement(data, Ptr, closetag, lvel) {
\r
931 var e = document.createElement("span")
\r
933 Ptr[0] = data.length
\r
938 closetag || (closetag = "")
\r
942 while (pt < data.length && data.charAt(pt) != "<") pt++
\r
944 var text = data.substring(pt0, pt)
\r
946 return document.createTextNode(text)
\r
950 while (pt < data.length && "\n\r\t >".indexOf(ch = data.charAt(pt)) < 0) pt++
\r
951 var tagname = data.substring(pt0, pt)
\r
952 var e = (tagname == closetag || tagname == "/" ? ""
\r
953 : document.createElementNS ? document.createElementNS('http://www.w3.org/1999/xhtml', tagname)
\r
954 : document.createElement(tagname));
\r
959 while (pt < data.length && (ch = data.charAt(pt)) != ">") {
\r
960 while (pt < data.length && "\n\r\t ".indexOf(ch = data.charAt(pt)) >= 0) pt++
\r
962 while (pt < data.length && "\n\r\t =/>".indexOf(ch = data.charAt(pt)) < 0) pt++
\r
963 var attrname = data.substring(pt0, pt).toLowerCase()
\r
964 if (attrname && ch != "=")
\r
965 e.setAttribute(attrname, "true")
\r
966 while (pt < data.length && "\n\r\t ".indexOf(ch = data.charAt(pt)) >= 0) pt++
\r
970 } else if (ch == "=") {
\r
971 var quote = data.charAt(++pt)
\r
973 while (pt < data.length && (ch = data.charAt(pt)) != quote) pt++
\r
974 var attrvalue = data.substring(pt0, pt)
\r
975 e.setAttribute(attrname, attrvalue)
\r
980 while (Ptr[0] < data.length) {
\r
981 var child = _jmolGetDomElement(data, Ptr, "/" + tagname, lvel+1)
\r
983 e.appendChild(child)
\r
988 function _jmolPopup(url) {
\r
989 var popup = window.open(url, "JmolPopup",
\r
990 "left=150,top=150,height=400,width=600," +
\r
991 "directories=yes,location=yes,menubar=yes," +
\r
993 "resizable=yes,scrollbars=yes,status=yes");
\r
998 function _jmolReadyCallback(name) {
\r
999 if (_jmol.debugAlert)
\r
1000 alert(name + " is ready");
\r
1001 _jmol.ready["" + name] = true;
\r
1004 function _jmolSterilizeScript(script) {
\r
1005 script = script.replace(/'/g, "'");
\r
1006 if (_jmol.debugAlert)
\r
1007 alert("script:\n" + script);
\r
1011 function _jmolSterilizeInline(model) {
\r
1012 model = model.replace(/\r|\n|\r\n/g, (model.indexOf("|") >= 0 ? "\\/n" : "|")).replace(/'/g, "'");
\r
1013 if (_jmol.debugAlert)
\r
1014 alert("inline model:\n" + model);
\r
1018 function _jmolRadio(script, labelHtml, isChecked, separatorHtml, groupName, id, title) {
\r
1019 ++_jmol.radioCount;
\r
1020 groupName != undefined && groupName != null || (groupName = "jmolRadioGroup" + (_jmol.radioGroupCount - 1));
\r
1023 labelHtml != undefined && labelHtml != null || (labelHtml = script.substring(0, 32));
\r
1024 separatorHtml || (separatorHtml = "")
\r
1025 var scriptIndex = _jmolAddScript(script);
\r
1026 var eospan = "</span>"
\r
1027 var t = "<span id=\"span_"+id+"\""+(title ? " title=\"" + title + "\"":"")+"><input name='"
\r
1028 + groupName + "' id='"+id+"' type='radio' onclick='_jmolClick(this," +
\r
1029 scriptIndex + _jmol.targetText + ");return true;' onmouseover='_jmolMouseOver(" +
\r
1030 scriptIndex + ");return true;' onmouseout='_jmolMouseOut()' " +
\r
1031 (isChecked ? "checked='true' " : "") + _jmol.radioCssText + " />"
\r
1032 if (labelHtml.toLowerCase().indexOf("<td>")>=0) {
\r
1036 t += "<label for=\"" + id + "\">" + labelHtml + "</label>" +eospan + separatorHtml;
\r
1041 function _jmolFindApplet(target) {
\r
1042 // first look for the target in the current window
\r
1043 var applet = _jmolFindAppletInWindow(_jmol.appletWindow != null ? _jmol.appletWindow : window, target);
\r
1044 // THEN look for the target in child frames
\r
1045 if (applet == undefined)
\r
1046 applet = _jmolSearchFrames(window, target);
\r
1047 // FINALLY look for the target in sibling frames
\r
1048 if (applet == undefined)
\r
1049 applet = _jmolSearchFrames(top, target); // look starting in top frame
\r
1053 function _jmolGetApplet(targetSuffix){
\r
1054 var target = "jmolApplet" + (targetSuffix ? targetSuffix : "0");
\r
1055 var applet = _jmolFindApplet(target);
\r
1056 if (applet) return applet
\r
1057 _jmol.alerted || alert("could not find applet " + target);
\r
1058 _jmol.alerted = true;
\r
1062 function _jmolSearchFrames(win, target) {
\r
1064 var frames = win.frames;
\r
1065 if (frames && frames.length) { // look in all the frames below this window
\r
1067 for (var i = 0; i < frames.length; ++i) {
\r
1068 applet = _jmolSearchFrames(frames[i], target);
\r
1073 if (_jmol.debugAlert)
\r
1074 alert("Jmol.js _jmolSearchFrames cannot access " + win.name + ".frame[" + i + "] consider using jmolSetAppletWindow()")
\r
1077 return applet = _jmolFindAppletInWindow(win, target)
\r
1080 function _jmolFindAppletInWindow(win, target) {
\r
1081 var doc = win.document;
\r
1082 if (doc.getElementById(target))
\r
1083 return doc.getElementById(target);
\r
1084 else if (doc.applets)
\r
1085 return doc.applets[target];
\r
1087 return doc[target];
\r
1090 function _jmolAddScript(script) {
\r
1093 var index = _jmol.scripts.length;
\r
1094 _jmol.scripts[index] = script;
\r
1098 function _jmolClick(elementClicked, scriptIndex, targetSuffix) {
\r
1099 _jmol.element = elementClicked;
\r
1100 _jmolScriptExecute(elementClicked, _jmol.scripts[scriptIndex], targetSuffix);
\r
1103 function _jmolMenuSelected(menuObject, targetSuffix) {
\r
1104 var scriptIndex = menuObject.value;
\r
1105 if (scriptIndex != undefined) {
\r
1106 _jmolScriptExecute(menuObject, _jmol.scripts[scriptIndex], targetSuffix);
\r
1109 var len = menuObject.length;
\r
1110 if (typeof len == "number") {
\r
1111 for (var i = 0; i < len; ++i) {
\r
1112 if (menuObject[i].selected) {
\r
1113 _jmolClick(menuObject[i], menuObject[i].value, targetSuffix);
\r
1118 alert("?Que? menu selected bug #8734");
\r
1122 _jmol.checkboxMasters = {};
\r
1123 _jmol.checkboxItems = {};
\r
1125 function jmolSetCheckboxGroup(chkMaster,chkBox) {
\r
1126 var id = chkMaster;
\r
1127 if(typeof(id)=="number")id = "jmolCheckbox" + id;
\r
1128 chkMaster = document.getElementById(id);
\r
1129 if (!chkMaster)alert("jmolSetCheckboxGroup: master checkbox not found: " + id);
\r
1130 var m = _jmol.checkboxMasters[id] = {};
\r
1131 m.chkMaster = chkMaster;
\r
1133 for (var i = 1; i < arguments.length; i++){
\r
1134 var id = arguments[i];
\r
1135 if(typeof(id)=="number")id = "jmolCheckbox" + id;
\r
1136 checkboxItem = document.getElementById(id);
\r
1137 if (!checkboxItem)alert("jmolSetCheckboxGroup: group checkbox not found: " + id);
\r
1138 m.chkGroup[id] = checkboxItem;
\r
1139 _jmol.checkboxItems[id] = m;
\r
1143 function _jmolNotifyMaster(m){
\r
1144 //called when a group item is checked
\r
1146 var allOff = true;
\r
1147 for (var chkBox in m.chkGroup){
\r
1148 if(m.chkGroup[chkBox].checked)
\r
1153 if (allOn)m.chkMaster.checked = true;
\r
1154 if (allOff)m.chkMaster.checked = false;
\r
1155 if ((allOn || allOff) && _jmol.checkboxItems[m.chkMaster.id])
\r
1156 _jmolNotifyMaster(_jmol.checkboxItems[m.chkMaster.id])
\r
1159 function _jmolNotifyGroup(m, isOn){
\r
1160 //called when a master item is checked
\r
1161 for (var chkBox in m.chkGroup){
\r
1162 var item = m.chkGroup[chkBox]
\r
1163 item.checked = isOn;
\r
1164 if (_jmol.checkboxMasters[item.id])
\r
1165 _jmolNotifyGroup(_jmol.checkboxMasters[item.id], isOn)
\r
1169 function _jmolCbClick(ckbox, whenChecked, whenUnchecked, targetSuffix) {
\r
1170 _jmol.control = ckbox
\r
1171 _jmolClick(ckbox, ckbox.checked ? whenChecked : whenUnchecked, targetSuffix);
\r
1172 if(_jmol.checkboxMasters[ckbox.id])
\r
1173 _jmolNotifyGroup(_jmol.checkboxMasters[ckbox.id], ckbox.checked)
\r
1174 if(_jmol.checkboxItems[ckbox.id])
\r
1175 _jmolNotifyMaster(_jmol.checkboxItems[ckbox.id])
\r
1178 function _jmolCbOver(ckbox, whenChecked, whenUnchecked) {
\r
1179 window.status = _jmol.scripts[ckbox.checked ? whenUnchecked : whenChecked];
\r
1182 function _jmolMouseOver(scriptIndex) {
\r
1183 window.status = _jmol.scripts[scriptIndex];
\r
1186 function _jmolMouseOut() {
\r
1187 window.status = " ";
\r
1191 function _jmolSetCodebase(codebase) {
\r
1192 _jmol.codebase = codebase ? codebase : ".";
\r
1193 if (_jmol.debugAlert)
\r
1194 alert("jmolCodebase=" + _jmol.codebase);
\r
1197 function _jmolOnloadResetForms() {
\r
1198 // must be evaluated ONLY once
\r
1199 _jmol.previousOnloadHandler = window.onload;
\r
1203 if (buttonCount+checkboxCount+menuCount+radioCount+radioGroupCount > 0) {
\r
1204 var forms = document.forms;
\r
1205 for (var i = forms.length; --i >= 0; )
\r
1208 if (previousOnloadHandler)
\r
1209 previousOnloadHandler();
\r
1214 ////////////////////////////////////
\r
1215 /////extensions for getProperty/////
\r
1216 ////////////////////////////////////
\r
1219 function _jmolEvalJSON(s,key){
\r
1222 if(s.charAt(0)!="{"){
\r
1223 if(s.indexOf(" | ")>=0)s=s.replace(/\ \|\ /g, "\n")
\r
1226 var A = eval("("+s+")")
\r
1228 if(key && A[key])A=A[key]
\r
1232 function _jmolEnumerateObject(A,key){
\r
1234 if(typeof(A) == "string" && A!="null"){
\r
1235 sout+="\n"+key+"=\""+A+"\""
\r
1236 }else if(!isNaN(A)||A==null){
\r
1237 sout+="\n"+key+"="+(A+""==""?"null":A)
\r
1238 }else if(A.length){
\r
1240 for(var i=0;i<A.length;i++){
\r
1242 if(typeof(A[i]) == "object"||typeof(A[i]) == "array"){
\r
1243 sout+=_jmolEnumerateObject(A[i],key+"["+i+"]")
\r
1245 sout+=key+"["+i+"]="+(typeof(A[i]) == "string" && A[i]!="null"?"\""+A[i].replace(/\"/g,"\\\"")+"\"":A[i])
\r
1256 if(typeof(A[i]) == "object"||typeof(A[i]) == "array"){
\r
1257 sout+=_jmolEnumerateObject(A[i],key+i)
\r
1259 sout+=key+i+"="+(typeof(A[i]) == "string" && A[i]!="null"?"\""+A[i].replace(/\"/g,"\\\"")+"\"":A[i])
\r
1267 function _jmolSortKey0(a,b){
\r
1268 return (a[0]<b[0]?1:a[0]>b[0]?-1:0)
\r
1271 function _jmolSortMessages(A){
\r
1272 if(!A || typeof(A)!="object")return []
\r
1274 for(var i=A.length-1;i>=0;i--)for(var j=0;j<A[i].length;j++)B[B.length]=A[i][j]
\r
1275 if(B.length == 0) return
\r
1276 B=B.sort(_jmolSortKey0)
\r
1280 /////////additional extensions //////////
\r
1283 function _jmolDomScriptLoad(URL){
\r
1284 //open(URL) //to debug
\r
1285 _jmol.servercall=URL
\r
1286 var node = document.getElementById("_jmolScriptNode")
\r
1287 if (node && _jmol.browser!="msie"){
\r
1288 document.getElementsByTagName("HEAD")[0].removeChild(node)
\r
1292 node.setAttribute("src",URL)
\r
1294 node=document.createElement("script")
\r
1295 node.setAttribute("id","_jmolScriptNode")
\r
1296 node.setAttribute("type","text/javascript")
\r
1297 node.setAttribute("src",URL)
\r
1298 document.getElementsByTagName("HEAD")[0].appendChild(node)
\r
1303 function _jmolExtractPostData(url){
\r
1304 S=url.split("&POST:")
\r
1306 for(var i=1;i<S.length;i++){
\r
1307 KV=S[i].split("=")
\r
1308 s+="&POSTKEY"+i+"="+KV[0]
\r
1309 s+="&POSTVALUE"+i+"="+KV[1]
\r
1311 return "&url="+escape(S[0])+s
\r
1314 function _jmolLoadModel(targetSuffix,remoteURL,array,isError,errorMessage){
\r
1315 //called by server, but in client
\r
1316 //overload this function to customize return
\r
1317 _jmol.remoteURL=remoteURL
\r
1318 isError && alert(errorMessage)
\r
1319 jmolLoadInlineScript(array.join("\n"),_jmol.optionalscript,targetSuffix)
\r
1322 //////////user property/status functions/////////
\r
1324 function jmolGetStatus(strStatus,targetSuffix){
\r
1325 return _jmolSortMessages(jmolGetPropertyAsArray("jmolStatus",strStatus,targetSuffix))
\r
1328 function jmolGetPropertyAsArray(sKey,sValue,targetSuffix) {
\r
1329 return _jmolEvalJSON(jmolGetPropertyAsJSON(sKey,sValue,targetSuffix),sKey)
\r
1332 function jmolGetPropertyAsString(sKey,sValue,targetSuffix) {
\r
1333 var applet = _jmolGetApplet(targetSuffix);
\r
1334 sValue == undefined && (sValue="");
\r
1335 return (applet ? applet.getPropertyAsString(sKey,sValue) + "" : "")
\r
1338 function jmolGetPropertyAsJSON(sKey,sValue,targetSuffix) {
\r
1339 sValue == undefined && (sValue = "")
\r
1340 var applet = _jmolGetApplet(targetSuffix);
\r
1342 return (applet ? applet.getPropertyAsJSON(sKey,sValue) + "" : "")
\r
1348 function jmolGetPropertyAsJavaObject(sKey,sValue,targetSuffix) {
\r
1349 sValue == undefined && (sValue = "")
\r
1350 var applet = _jmolGetApplet(targetSuffix);
\r
1351 return (applet ? applet.getProperty(sKey,sValue) : null)
\r
1355 function jmolDecodeJSON(s) {
\r
1356 return _jmolEnumerateObject(_jmolEvalJSON(s),"")
\r
1360 ///////// synchronous scripting ////////
\r
1362 function jmolScriptWait(script, targetSuffix) {
\r
1363 targetSuffix == undefined && (targetSuffix="0")
\r
1364 var Ret=jmolScriptWaitAsArray(script, targetSuffix)
\r
1366 for(var i=Ret.length;--i>=0;)
\r
1367 for(var j=0;j< Ret[i].length;j++)
\r
1372 function jmolScriptWaitOutput(script, targetSuffix) {
\r
1373 targetSuffix == undefined && (targetSuffix="0")
\r
1377 _jmolCheckBrowser();
\r
1378 var applet=_jmolGetApplet(targetSuffix);
\r
1379 if (applet) ret += applet.scriptWaitOutput(script);
\r
1386 function jmolEvaluate(molecularMath, targetSuffix) {
\r
1388 //carries out molecular math on a model
\r
1390 targetSuffix == undefined && (targetSuffix="0")
\r
1391 var result = "" + jmolGetPropertyAsJavaObject("evaluate", molecularMath, targetSuffix);
\r
1392 var s = result.replace(/\-*\d+/,"")
\r
1393 if (s == "" && !isNaN(parseInt(result)))return parseInt(result);
\r
1394 var s = result.replace(/\-*\d*\.\d*/,"")
\r
1395 if (s == "" && !isNaN(parseFloat(result)))return parseFloat(result);
\r
1399 function jmolScriptEcho(script, targetSuffix) {
\r
1400 // returns a newline-separated list of all echos from a script
\r
1401 targetSuffix == undefined && (targetSuffix="0")
\r
1402 var Ret=jmolScriptWaitAsArray(script, targetSuffix)
\r
1404 for(var i=Ret.length;--i>=0;)
\r
1405 for(var j=Ret[i].length;--j>=0;)
\r
1406 if (Ret[i][j][1] == "scriptEcho")s+=Ret[i][j][3]+"\n"
\r
1407 return s.replace(/ \| /g, "\n")
\r
1411 function jmolScriptMessage(script, targetSuffix) {
\r
1412 // returns a newline-separated list of all messages from a script, ending with "script completed\n"
\r
1413 targetSuffix == undefined && (targetSuffix="0")
\r
1414 var Ret=jmolScriptWaitAsArray(script, targetSuffix)
\r
1416 for(var i=Ret.length;--i>=0;)
\r
1417 for(var j=Ret[i].length;--j>=0;)
\r
1418 if (Ret[i][j][1] == "scriptStatus")s+=Ret[i][j][3]+"\n"
\r
1419 return s.replace(/ \| /g, "\n")
\r
1423 function jmolScriptWaitAsArray(script, targetSuffix) {
\r
1426 jmolGetStatus("scriptEcho,scriptMessage,scriptStatus,scriptError",targetSuffix)
\r
1428 _jmolCheckBrowser();
\r
1429 var applet=_jmolGetApplet(targetSuffix);
\r
1430 if (applet) ret += applet.scriptWait(script);
\r
1431 ret = _jmolEvalJSON(ret,"jmolStatus")
\r
1432 if(typeof ret == "object")
\r
1442 //////////// save/restore orientation /////////////
\r
1444 function jmolSaveOrientation(id, targetSuffix) {
\r
1445 targetSuffix == undefined && (targetSuffix="0")
\r
1446 return _jmol["savedOrientation"+id] = jmolGetPropertyAsArray("orientationInfo","info",targetSuffix).moveTo
\r
1449 function jmolRestoreOrientation(id, targetSuffix) {
\r
1450 targetSuffix == undefined && (targetSuffix="0")
\r
1451 var s=_jmol["savedOrientation"+id]
\r
1452 if (!s || s == "")return
\r
1453 s=s.replace(/1\.0/,"0")
\r
1454 return jmolScriptWait(s,targetSuffix)
\r
1457 function jmolRestoreOrientationDelayed(id, delay, targetSuffix) {
\r
1458 arguments.length < 2 && (delay=1)
\r
1459 targetSuffix == undefined && (targetSuffix="0")
\r
1460 var s=_jmol["savedOrientation"+id]
\r
1461 if (!s || s == "")return
\r
1462 s=s.replace(/1\.0/,delay)
\r
1463 return jmolScriptWait(s,targetSuffix)
\r
1466 //////////// add parameter /////////////
\r
1468 * for adding callbacks or other parameters. Use:
\r
1470 jmolSetDocument(0)
\r
1471 var s= jmolApplet(....)
\r
1472 s = jmolAppletAddParam(s,"messageCallback", "myFunctionName")
\r
1474 jmolSetDocument(document) // if you want to then write buttons and such normally
\r
1478 function jmolAppletAddParam(appletCode,name,value){
\r
1479 return (value == "" ? appletCode : appletCode.replace(/\<param/,"\n<param name='"+name+"' value='"+value+"' />\n<param"))
\r
1482 ///////////////auto load Research Consortium for Structural Biology (RCSB) data ///////////
\r
1484 function jmolLoadAjax_STOLAF_RCSB(fileformat,pdbid,optionalscript,targetSuffix){
\r
1486 _jmol.thismodel || (_jmol.thismodel = "1crn")
\r
1487 _jmol.serverURL || (_jmol.serverURL="http://fusion.stolaf.edu/chemistry/jmol/getajaxjs.cfm")
\r
1488 _jmol.RCSBserver || (_jmol.RCSBserver="http://www.rcsb.org")
\r
1489 _jmol.defaultURL_RCSB || (_jmol.defaultURL_RCSB=_jmol.RCSBserver+"/pdb/files/1CRN.CIF")
\r
1490 fileformat || (fileformat="PDB")
\r
1491 pdbid || (pdbid=prompt("Enter a 4-digit PDB ID:",_jmol.thismodel))
\r
1492 if(!pdbid || pdbid.length != 4)return ""
\r
1493 targetSuffix || (targetSuffix="0")
\r
1494 optionalscript || (optionalscript="")
\r
1495 var url=_jmol.defaultURL_RCSB.replace(/1CRN/g,pdbid.toUpperCase())
\r
1496 fileformat=="CIF" || (url=url.replace(/CIF/,fileformat))
\r
1497 _jmol.optionalscript=optionalscript
\r
1498 _jmol.thismodel=pdbid
\r
1499 _jmol.thistargetsuffix=targetSuffix
\r
1501 _jmol.modelArray = []
\r
1502 url=_jmol.serverURL+"?returnfunction=_jmolLoadModel&returnArray=_jmol.modelArray&id="+targetSuffix+_jmolExtractPostData(url)
\r
1503 _jmolDomScriptLoad(url)
\r
1508 ///////////////auto load NIH CACTVS data -- compound name or SMILES ///////////
\r
1510 function jmolLoadAjax_STOLAF_NIH(compoundid,optionalscript,targetSuffix){
\r
1511 _jmol.thismodel || (_jmol.thismodel = "aspirin")
\r
1512 _jmol.serverURL || (_jmol.serverURL="http://fusion.stolaf.edu/chemistry/jmol/getajaxjs.cfm")
\r
1513 _jmol.defaultURL_NIH || (_jmol.defaultURL_NIH="http://cactus.nci.nih.gov/chemical/structure/FILE/file?format=sdf&get3d=True")
\r
1514 compoundid || (compoundid=prompt("Enter a compound name or a SMILES string:",_jmol.thismodel))
\r
1515 if(!compoundid)return ""
\r
1516 targetSuffix || (targetSuffix="0")
\r
1517 optionalscript || (optionalscript="")
\r
1518 var url=_jmol.defaultURL_NIH.replace(/FILE/g,compoundid)
\r
1519 _jmol.optionalscript=optionalscript
\r
1520 _jmol.thismodel=compoundid
\r
1521 _jmol.thistargetsuffix=targetSuffix
\r
1523 _jmol.modelArray = []
\r
1524 url=_jmol.serverURL+"?returnfunction=_jmolLoadModel&returnArray=_jmol.modelArray&id="+targetSuffix+_jmolExtractPostData(url)
\r
1525 _jmolDomScriptLoad(url)
\r
1530 /////////////// St. Olaf College AJAX server -- ANY URL ///////////
\r
1532 function jmolLoadAjax_STOLAF_ANY(url, userid, optionalscript,targetSuffix){
\r
1533 _jmol.serverURL="http://fusion.stolaf.edu/chemistry/jmol/getajaxjs.cfm"
\r
1534 _jmol.thisurlANY || (_jmol.thisurlANY = "http://www.stolaf.edu/depts/chemistry/mo/struc/data/ycp3-1.mol")
\r
1535 url || (url=prompt("Enter any (uncompressed file) URL:", _jmol.thisurlANY))
\r
1536 userid || (userid="0")
\r
1537 targetSuffix || (targetSuffix="0")
\r
1538 optionalscript || (optionalscript="")
\r
1539 _jmol.optionalscript=optionalscript
\r
1540 _jmol.thistargetsuffix=targetSuffix
\r
1541 _jmol.modelArray = []
\r
1542 _jmol.thisurl = url
\r
1543 url=_jmol.serverURL+"?returnfunction=_jmolLoadModel&returnArray=_jmol.modelArray&id="+targetSuffix+_jmolExtractPostData(url)
\r
1544 _jmolDomScriptLoad(url)
\r
1548 /////////////// Mineralogical Society of America (MSA) data /////////
\r
1550 function jmolLoadAjax_MSA(key,value,optionalscript,targetSuffix){
\r
1552 _jmol.thiskeyMSA || (_jmol.thiskeyMSA = "mineral")
\r
1553 _jmol.thismodelMSA || (_jmol.thismodelMSA = "quartz")
\r
1554 _jmol.ajaxURL_MSA || (_jmol.ajaxURL_MSA="http://rruff.geo.arizona.edu/AMS/result.php?mineral=quartz&viewing=ajaxjs")
\r
1555 key || (key=prompt("Enter a field:", _jmol.thiskeyMSA))
\r
1557 value || (value=prompt("Enter a "+key+":", _jmol.thismodelMSA))
\r
1558 if(!value)return ""
\r
1559 targetSuffix || (targetSuffix="0")
\r
1560 optionalscript || (optionalscript="")
\r
1561 optionalscript == 1 && (optionalscript='load "" {1 1 1}')
\r
1562 var url=_jmol.ajaxURL_MSA.replace(/mineral/g,key).replace(/quartz/g,value)
\r
1563 _jmol.optionalscript=optionalscript
\r
1564 _jmol.thiskeyMSA=key
\r
1565 _jmol.thismodelMSA=value
\r
1566 _jmol.thistargetsuffix=targetSuffix
\r
1568 _jmol.modelArray = []
\r
1569 loadModel=_jmolLoadModel
\r
1570 _jmolDomScriptLoad(url)
\r
1576 function jmolLoadAjaxJS(url, userid, optionalscript,targetSuffix){
\r
1577 userid || (userid="0")
\r
1578 targetSuffix || (targetSuffix="0")
\r
1579 optionalscript || (optionalscript="")
\r
1580 _jmol.optionalscript=optionalscript
\r
1581 _jmol.thismodel=userid
\r
1582 _jmol.thistargetsuffix=targetSuffix
\r
1583 _jmol.modelArray = []
\r
1584 _jmol.thisurl = url
\r
1585 url+="&returnFunction=_jmolLoadModel&returnArray=_jmol.modelArray&id="+targetSuffix
\r
1586 _jmolDomScriptLoad(url)
\r
1590 //// in case Jmol library has already been loaded:
\r
1594 ///////////////moving atoms //////////////
\r
1596 // HIGHLY experimental!!
\r
1598 function jmolSetAtomCoord(i,x,y,z,targetSuffix){
\r
1599 _jmolCheckBrowser();
\r
1600 var applet=_jmolGetApplet(targetSuffix);
\r
1601 if (applet) applet.getProperty('jmolViewer').setAtomCoord(i,x,y,z)
\r
1604 function jmolSetAtomCoordRelative(i,x,y,z,targetSuffix){
\r
1605 _jmolCheckBrowser();
\r
1606 var applet=_jmolGetApplet(targetSuffix);
\r
1607 if (applet) applet.getProperty('jmolViewer').setAtomCoordRelative(i,x,y,z)
\r
1611 ///////////////applet fake for testing buttons/////////////
\r
1614 if(_jmol.useNoApplet){
\r
1615 jmolApplet = function(w){
\r
1616 var s="<table style='background-color:black' width="+w+"><tr height="+w+">"
\r
1617 +"<td align=center valign=center style='background-color:white'>"
\r
1618 +"Applet would be here"
\r
1619 +"<p><textarea id=fakeApplet rows=5 cols=50></textarea>"
\r
1620 +"</td></tr></table>"
\r
1621 return _jmolDocumentWrite(s)
\r
1624 _jmolFindApplet = function(){return jmolApplet0}
\r
1627 script: function(script){document.getElementById("fakeApplet").value="\njmolScript:\n"+script}
\r
1628 ,scriptWait: function(script){document.getElementById("fakeApplet").value="\njmolScriptWait:\n"+script}
\r
1629 ,loadInline: function(data,script){document.getElementById("fakeApplet").value="\njmolLoadInline data:\n"+data+"\n\nscript:\n"+script}
\r
1634 ///////////////////////////////////////////
\r
1636 // This should no longer be needed, jmolResizeApplet() is better; kept for backwards compatibility
\r
1638 Resizes absolutely (pixels) or by percent of window (w or h 0.5 means 50%).
\r
1639 targetSuffix is optional and defaults to zero (first applet in page).
\r
1640 Both w and h are optional, but needed if you want to use targetSuffix.
\r
1642 w defaults to 100% of window
\r
1643 If either w or h is between 0 and 1, then it is taken as percent/100.
\r
1644 If either w or h is greater than 1, then it is taken as a size (pixels).
\r
1646 function jmolResize(w,h,targetSuffix) {
\r
1647 _jmol.alerted = true;
\r
1648 var percentW = (!w ? 100 : w <= 1 && w > 0 ? w * 100 : 0);
\r
1649 var percentH = (!h ? percentW : h <= 1 && h > 0 ? h * 100 : 0);
\r
1650 if (_jmol.browser=="msie") {
\r
1651 var width=document.body.clientWidth;
\r
1652 var height=document.body.clientHeight;
\r
1654 var netscapeScrollWidth=15;
\r
1655 var width=window.innerWidth - netscapeScrollWidth;
\r
1656 var height=window.innerHeight-netscapeScrollWidth;
\r
1658 var applet = _jmolGetApplet(targetSuffix);
\r
1659 if(!applet)return;
\r
1660 applet.style.width = (percentW ? width * percentW/100 : w)+"px";
\r
1661 applet.style.height = (percentH ? height * percentH/100 : (h ? h : w))+"px";
\r
1662 //title=width + " " + height + " " + (new Date());
\r
1665 // 13 Jun 09 -- makes jmolResize() obsolete (kept for backwards compatibility)
\r
1666 function jmolResizeApplet(size,targetSuffix) {
\r
1667 // See _jmolGetAppletSize() for the formats accepted as size [same used by jmolApplet()]
\r
1668 // Special case: an empty value for width or height is accepted, meaning no change in that dimension.
\r
1669 _jmol.alerted = true;
\r
1670 var applet = _jmolGetApplet(targetSuffix);
\r
1671 if(!applet)return;
\r
1672 var sz = _jmolGetAppletSize(size, "px");
\r
1673 sz[0] && (applet.style.width = sz[0]);
\r
1674 sz[1] && (applet.style.height = sz[1]);
\r
1677 function _jmolGetAppletSize(size, units) {
\r
1678 /* Accepts single number or 2-value array, each one can be one of:
\r
1679 percent (text string ending %), decimal 0 to 1 (percent/100), number, or text string (interpreted as nr.)
\r
1680 [width, height] array of strings is returned, with units added if specified.
\r
1681 Percent is relative to container div or element (which should have explicitly set size).
\r
1683 var width, height;
\r
1684 if ( (typeof size) == "object" && size != null ) {
\r
1685 width = size[0]; height = size[1];
\r
1687 width = height = size;
\r
1689 return [_jmolFixDim(width, units), _jmolFixDim(height, units)];
\r
1692 function _jmolFixDim(x, units) {
\r
1694 return (sx.length == 0 ? (units ? "" : _jmol.allowedJmolSize[2])
\r
1695 : sx.indexOf("%") == sx.length-1 ? sx
\r
1696 : (x = parseFloat(x)) <= 1 && x > 0 ? x * 100 + "%"
\r
1697 : (isNaN(x = Math.floor(x)) ? _jmol.allowedJmolSize[2]
\r
1698 : x < _jmol.allowedJmolSize[0] ? _jmol.allowedJmolSize[0]
\r
1699 : x > _jmol.allowedJmolSize[1] ? _jmol.allowedJmolSize[1]
\r
1700 : x) + (units ? units : ""));
\r