Revision: 21043 http://sourceforge.net/p/jmol/code/21043 Author: hansonr Date: 2016-04-11 19:36:20 +0000 (Mon, 11 Apr 2016) Log Message: ----------- Jmol.___JmolVersion="14.4.4_2016.04.11"
bug fix: qchem reader fails to switch to spherical D/F basis for second structure bug fix: pointGroup secondary axis in yellow is too hard to see -- using "orange" instead new feature: symop() options: symop(op) -- returns the 4x4 matrix representation of this operator symop(op, atom) -- returns the point generated by operator op on atom -- op may be a positive or negative integer indictating the operation (or its reverse) to apply from the loaded space group -- for example, symop(3, @1) or symop(-4, {atomindex=16}) -- op may be a string such as "x+1/2,1/2-y,z" representing a specific generic operation symop(atom1, atom2) -- returns the description of the first of possibly several operations that take atom1 to atom2, for example: "2-fold screw axis|translation: 1/2 0 0" symop(atom1, atom2, n) -- returns the description of the nth operation that takes atom1 to atom2 symop(...point...) -- any place an atom can be used in symop(), one can substitute an xyz coordinate. -- for example, symop(@1, {1/2 1/2 1/2}) {atomset}.symop(...) -- when more than one model is loaded, prepending any symop function with an atom set specifies which atoms, space group, and unit cell are being referenced. For example, {2.1}.symop(5) operates only on atoms in the first model of the second loaded file, using the appropriate space group and unit cell. In this way, "@1" will designate one atom only, provided only one model is showing (using the FRAME/MODEL command). If only one model has been loaded, there is no need to use this syntax; symop(...) will do the same. symop(..., outputType) -- All uses of symop() and {atomset}.symop() can be extended using a final parameter that changes the default output described above to be something else. Options for outputType include: "draw" Returns the Jmol script illustrating this operation with DRAW commands. $ print symop(3,"draw") draw ID draw_* delete draw ID draw_frame1X diameter 0.15{5.5172 1.9683 2.7802}{6.5172 1.9683 2.7802} color red ... "full" Returns the tab-separated Jones-Faithful string and descriptor for this operation. $ print symop(3,"full") -x,-y,-z(mx,my,mz) Ci: 0 0 0 "lattice" Returns the lattice type associated with the space group involving this operation. "list" Specifically when two atoms or points are specified, returns a string list of all operations taking the first to the second. $ print symop(@3,@21,"list") 5 x+1/2,-y+1/2,-z+1/2(-mx,my,mz) 2-fold screw axis|translation: 1/2 0 0|time-reversed 7 -x+1/2,y+1/2,z+1/2(-mx,my,mz) n-glide plane|translation: 0 1/2 1/2|time-reversed Note that this string can be turned into a standard array using .lines.split("\t",true): $ print symop(@3,@21,"list").lines.split("\t",true) [ 5 x+1/2,-y+1/2,-z+1/2(-mx,my,mz) 2-fold screw axis|translation: 1/2 0 0|time-reversed ] [ 7 -x+1/2,y+1/2,z+1/2(-mx,my,mz) n-glide plane|translation: 0 1/2 1/2|time-reversed ] "array" Returns an associative array that contains critical information relating to this operation. $ load =magndata/0.34 $ print symop(3,"array") { "inversionCenter" : {0.0 0.0 0.0} "label" : "Ci: 0 0 0" "matrix" : [ [-1.0, 0.0, 0.0, 0.0] [0.0, -1.0, 0.0, 0.0] [0.0, 0.0, -1.0, 0.0] [0.0, 0.0, 0.0, 1.0] ] "timeReversal" : 1 "xyz" : "-x,-y,-z(mx,my,mz)" "xyzOriginal" : "-x,-y,-z,m" } In addition, all possible keys of this array may be used as well for outputType. These include: "axisVector", "cartesianTranslation", "centeringVector", "fractionalTranslation", "inversionCenter", "label", "matrix", "plane", "rotationAngle", "timeReversal", "unitTranslation", "xyz", and "xyzOriginal" Three of these that may be less than obvious are explained below: "centeringVector" For operations that are pure lattice translations, returns the vector for this centering in fractional coordinates. "timeReversal" This quantity is 0 for standard space groups. Magnetic space group operations also include the possibility of inversion of the spin along with any 3D symmetry operation. This inversion characteristic is referred to as "time reversal" and takes the value of 1 or -1. "unitTranslation" Symmetry operations involving two atoms may include an extra lattice translation if the two atoms are in different unit cells. This translation is above and beyond any fractional lattice centering that this operator incorporates for a face- or body-centered space group. new feature: show spacegroup/xxxxx -- selects lines from a space group report similar to the way show state/xxxx works -- example: load =ams/quartz 1 show spacegroup/Class new feature: show/draw symop @1 @2 -- gives full list of matching symmetry operations -- example: $ load =magndata/1.23 {444 555 1} packed $ show symop @153 @299 1 x+2,y,z2(mx,my,mz) translation: 2 0 -2 5 -x,-y,-z(mx,my,mz) Ci: 0 0 0 11 x+2,-y,-z(-mx,my,mz) 2-fold screw axis|translation: 2 0 0|time-reversed 15 -x,y,z2(-mx,my,mz) c-glide plane|translation: 0 0 -2|time-reversed new feature: show/draw symop @1 @2 n -- shows or draws the nth symmetry operation relating atom 1 to atom 2 -- example: $ load =magndata/1.23 {444 555 1} packed $ show symop @153 @299 3 11 x+2,-y,-z(-mx,my,mz) 2-fold screw axis|translation: 2 0 0|time-reversed new feature: print pointgroup("spacegroup", @1) -- analyzes the point group (crystal class) of a crystal. -- uses three irrational-coordinate points to generate all possible operators -- creates a map with keys (somewhat variable depending upon axes present): C2 C3 Ci Cs S6 detail distanceTolerance linearTolerance nAtoms nC2 nC3 nCi nCn nCs nS6 nSn nTotal name points principalAxis new feature: draw SPACEGROUP -- draws all operations in space group new feature: draw POINTGROUP SPACEGROUP -- draws crystal class symmetry operations for a pointgroup -- uses point group style, with circular planes new feature: @1.find("crystalClass", pt) -- generates a list of points based on a model's crystal class (point group) -- uses @1 just to find the unit cell and space group -- optional pt is used as a generator (defaults to @1) -- example: load =ams/calcite 1 x = @3.find("crystalClass") print pointgroup(x).name draw points @x polyhedra ID p {0 0 0} to @x Modified Paths: -------------- trunk/Jmol/src/org/jmol/adapter/readers/quantum/QchemReader.java trunk/Jmol/src/org/jmol/script/ScriptMathProcessor.java trunk/Jmol/src/org/jmol/script/ScriptParam.java trunk/Jmol/src/org/jmol/scriptext/CmdExt.java trunk/Jmol/src/org/jmol/scriptext/IsoExt.java trunk/Jmol/src/org/jmol/scriptext/MathExt.java trunk/Jmol/src/org/jmol/symmetry/SymmetryDesc.java trunk/Jmol/src/org/jmol/symmetry/SymmetryOperation.java trunk/Jmol/src/org/jmol/viewer/Jmol.properties Modified: trunk/Jmol/src/org/jmol/adapter/readers/quantum/QchemReader.java =================================================================== --- trunk/Jmol/src/org/jmol/adapter/readers/quantum/QchemReader.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/adapter/readers/quantum/QchemReader.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -153,6 +153,7 @@ private void readAtoms() throws Exception { asc.newAtomSet(); setMOData(true); + dFixed = fFixed = false; readLines(2); String[] tokens; while (rd() != null && !line.startsWith(" --")) { Modified: trunk/Jmol/src/org/jmol/script/ScriptMathProcessor.java =================================================================== --- trunk/Jmol/src/org/jmol/script/ScriptMathProcessor.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/script/ScriptMathProcessor.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -1259,8 +1259,8 @@ return (isDecimal(x2) || isDecimal(x1) ? addXFloat(x1.asFloat() * x2.asFloat()) : addXInt(x1.asInt() * x2.asInt())); } - pt = (x1.tok == T.matrix3f || x1.tok == T.matrix4f ? ptValue(x2) - : x2.tok == T.matrix3f ? ptValue(x1) : null); + pt = (x1.tok == T.matrix3f || x1.tok == T.matrix4f ? ptValue(x2, null) + : x2.tok == T.matrix3f ? ptValue(x1, null) : null); pt4 = (x1.tok == T.matrix4f ? planeValue(x2) : x2.tok == T.matrix4f ? planeValue(x1) : null); // checking here to make sure arrays remain arrays and @@ -1541,7 +1541,7 @@ .lastIndexOf("-") > 0)); } - public P3 ptValue(SV x) throws ScriptException { + public P3 ptValue(SV x, BS bsRestrict) throws ScriptException { Object pt; switch (x.tok) { case T.point3f: @@ -1550,6 +1550,10 @@ BS bs = (BS) x.value; if (bs.isEmpty()) break; + if (bsRestrict != null) { + bs = BSUtil.copy(bs); + bs.and(bsRestrict); + } return (P3) eval.getBitsetProperty(bs, T.xyz, null, null, x.value, null, false, Integer.MAX_VALUE, false); case T.string: Modified: trunk/Jmol/src/org/jmol/script/ScriptParam.java =================================================================== --- trunk/Jmol/src/org/jmol/script/ScriptParam.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/script/ScriptParam.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -15,6 +15,7 @@ import org.jmol.java.BS; import org.jmol.modelset.TickInfo; +import org.jmol.util.BSUtil; import org.jmol.util.Escape; import org.jmol.util.Edge; import org.jmol.util.Logger; @@ -191,7 +192,9 @@ /** * * @param i - * @param ret return P3 or BS + * @param ret + * return P3 or BS to ret[0]; on input, passing a BS as ret[1] indicates that + * it should be ANDED with this BS prior to calculation (SHOW/DRAW SYMOP) * @return point -- ORIGINAL, non-copied atom, if a single atom * * @throws ScriptException @@ -202,8 +205,14 @@ case T.expressionBegin: BS bs = atomExpression(st, i, 0, true, false, ret, true); if (bs != null) { - if (ret != null) - ret[0] = bs; + if (ret != null) { + if (ret.length == 2 && ret[1] instanceof BS) { + bs = BSUtil.copy(bs); + bs.and((BS) ret[1]); + } else { + ret[0] = bs; + } + } return (bs.cardinality() == 1 ? vwr.ms.at[bs.nextSetBit(0)] : vwr.ms.getAtomSetCenter(bs)); } if (ret != null && ret[0] instanceof P3) Modified: trunk/Jmol/src/org/jmol/scriptext/CmdExt.java =================================================================== --- trunk/Jmol/src/org/jmol/scriptext/CmdExt.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/scriptext/CmdExt.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -4252,8 +4252,9 @@ pt2 = null; int nth = -1; if (slen > 3 && tokAt(3) != T.string) { - pt1 = centerParameter(2); - pt2 = centerParameter(++eval.iToken); + Object[] ret = new Object[] {null, vwr.getFrameAtoms()}; + pt1 = eval.centerParameter(2, ret); + pt2 = eval.centerParameter(++eval.iToken, ret); if (tokAt(eval.iToken + 1) == T.integer) { nth = eval.getToken(++eval.iToken).intValue; } Modified: trunk/Jmol/src/org/jmol/scriptext/IsoExt.java =================================================================== --- trunk/Jmol/src/org/jmol/scriptext/IsoExt.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/scriptext/IsoExt.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -481,10 +481,11 @@ default: if (!eval.isCenterParameter(i)) iSym = intParameter(i++); + Object[] ret = new Object[] {null, vwr.getFrameAtoms()}; if (eval.isCenterParameter(i)) - center = centerParameter(i); + center = eval.centerParameter(i, ret); if (eval.isCenterParameter(eval.iToken + 1)) - target = centerParameter(++eval.iToken); + target = eval.centerParameter(++eval.iToken, ret); if (chk) return; i = eval.iToken; Modified: trunk/Jmol/src/org/jmol/scriptext/MathExt.java =================================================================== --- trunk/Jmol/src/org/jmol/scriptext/MathExt.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/scriptext/MathExt.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -1120,12 +1120,12 @@ } if (tok == T.cross) { - P3 a = P3.newP(mp.ptValue(x1)); - a.cross(a, mp.ptValue(x2)); + P3 a = P3.newP(mp.ptValue(x1, null)); + a.cross(a, mp.ptValue(x2, null)); return mp.addXPt(a); } - P3 pt2 = (x2.tok == T.varray ? null : mp.ptValue(x2)); + P3 pt2 = (x2.tok == T.varray ? null : mp.ptValue(x2, null)); P4 plane2 = mp.planeValue(x2); if (isDist) { int minMax = (op == Integer.MIN_VALUE ? 0 : op & T.minmaxmask); @@ -1187,7 +1187,7 @@ } } } - P3 pt1 = mp.ptValue(x1); + P3 pt1 = mp.ptValue(x1, null); P4 plane1 = mp.planeValue(x1); float f = Float.NaN; try { @@ -1233,8 +1233,8 @@ int tok = T.getTokFromName(type); if (args.length > 2) { // helix(pt1, pt2, dq ...) - P3 pta = mp.ptValue(args[0]); - P3 ptb = mp.ptValue(args[1]); + P3 pta = mp.ptValue(args[0], null); + P3 ptb = mp.ptValue(args[1], null); if (tok == T.nada || args[2].tok != T.point4f || pta == null || ptb == null) return false; Quat dq = Quat.newP4((P4) args[2].value); @@ -2219,7 +2219,7 @@ } P3[] pts = new P3[nPoints]; for (int i = 0; i < nPoints; i++) { - if ((pts[i] = mp.ptValue(args[i])) == null) + if ((pts[i] = mp.ptValue(args[i], null)) == null) return false; } switch (nPoints) { @@ -2321,7 +2321,7 @@ return mp.addXStr(""); return mp.addXList(list); } - pt2 = mp.ptValue(args[0]); + pt2 = mp.ptValue(args[0], null); if (pt2 == null) return mp.addXStr(""); return mp.addXPt(Measure.getIntersection(pt2, null, plane, pt3, norm, @@ -2336,8 +2336,8 @@ return mp.addXPt4(e.getHklPlane(P3.new3(SV.fValue(args[0]), SV.fValue(args[1]), SV.fValue(args[2])))); case T.intersection: - pt1 = mp.ptValue(args[0]); - pt2 = mp.ptValue(args[1]); + pt1 = mp.ptValue(args[0], null); + pt2 = mp.ptValue(args[1], null); if (pt1 == null || pt2 == null) return mp.addXStr(""); V3 vLine = V3.newV(pt2); @@ -2353,7 +2353,7 @@ return mp.addXStr(""); return mp.addXPt(pt1); } - pt3 = mp.ptValue(args[2]); + pt3 = mp.ptValue(args[2], null); if (pt3 == null) return mp.addXStr(""); // intersection(ptLine, vLine, pt2); @@ -2388,13 +2388,13 @@ break; case T.bitset: case T.point3f: - pt1 = mp.ptValue(args[0]); - pt2 = mp.ptValue(args[1]); + pt1 = mp.ptValue(args[0], null); + pt2 = mp.ptValue(args[1], null); if (pt2 == null) return false; pt3 = (args.length > 2 && (args[2].tok == T.bitset || args[2].tok == T.point3f) ? mp - .ptValue(args[2]) : null); + .ptValue(args[2], null) : null); norm = V3.newV(pt2); if (pt3 == null) { plane = new P4(); @@ -2421,7 +2421,7 @@ // plane(<point1>,<point2>,<point3>) // plane(<point1>,<point2>,<point3>,<pointref>) V3 vAB = new V3(); - P3 ptref = (args.length == 4 ? mp.ptValue(args[3]) : null); + P3 ptref = (args.length == 4 ? mp.ptValue(args[3], null) : null); float nd = Measure.getDirectedNormalThroughPoints(pt1, pt2, pt3, ptref, norm, vAB); return mp.addXPt4(P4.new4(norm.x, norm.y, norm.z, nd)); @@ -2581,7 +2581,7 @@ && (args[1].tok == T.integer || args[1].tok == T.bitset)) break; } - if ((pt0 = mp.ptValue(args[0])) == null || tok != T.quaternion + if ((pt0 = mp.ptValue(args[0], null)) == null || tok != T.quaternion && args[1].tok == T.point3f) return false; break; @@ -2653,7 +2653,7 @@ break; } } - P3 pt1 = mp.ptValue(args[1]); + P3 pt1 = mp.ptValue(args[1], null); p4 = mp.planeValue(args[0]); if (pt1 != null) q = Quat.getQuaternionFrame(P3.new3(0, 0, 0), pt0, pt1); @@ -3038,17 +3038,11 @@ // x = y.symop(n,"time") // Returns the time reversal of a symmetry operator in a magnetic space group - + int narg = args.length; if (narg == 0) return false; SV x1 = (haveBitSet ? mp.getX() : null); - BS bsAtoms = null; - if (x1 != null) { - if (x1.tok != T.bitset) - return false; - bsAtoms = (BS) x1.value; - } String xyz = null; int iOp = Integer.MIN_VALUE; int apt = 0; @@ -3066,19 +3060,20 @@ apt++; break; } - int len = apt; - if (bsAtoms == null) - if (apt < narg && args[apt].tok == T.bitset) { - bsAtoms = (BS) args[apt].value; - } else { - bsAtoms = vwr.getAllAtoms(); - } - // check for symop(op, pt) - // check for symop(op, pt1, pt2) + BS bsAtoms = null; + if (x1 != null) { + if (x1.tok != T.bitset) + return false; + bsAtoms = (BS) x1.value; + } else if (apt < narg && args[apt].tok == T.bitset) { + bsAtoms = (BS) args[apt].value; + } else if (apt + 1 < narg && args[apt + 1].tok == T.bitset) { + bsAtoms = (BS) args[apt + 1].value; + } P3 pt1 = null, pt2 = null; - if ((pt1 = (narg > apt ? mp.ptValue(args[apt]) : null)) != null) + if ((pt1 = (narg > apt ? mp.ptValue(args[apt], bsAtoms) : null)) != null) apt++; - if ((pt2 = (narg > apt ? mp.ptValue(args[apt]) : null)) != null) + if ((pt2 = (narg > apt ? mp.ptValue(args[apt], bsAtoms) : null)) != null) apt++; int nth = (pt2 != null && args.length > apt && iOp == Integer.MIN_VALUE && args[apt].tok == T.integer ? args[apt].intValue : 0); @@ -3086,10 +3081,14 @@ apt++; if (iOp == Integer.MIN_VALUE) iOp = 0; - String desc = (narg == apt ? (pt2 != null ? "all" : pt1 != null ? "point" : "matrix") - : SV.sValue(args[apt++]).toLowerCase()); - return (apt == args.length && mp.addXObj(vwr.ms.getSymTemp(false).getSymmetryInfoAtom(vwr.ms, bsAtoms, - xyz, iOp, pt1, pt2, desc, 0, 0, nth))); + String desc = (narg == apt ? (pt2 != null ? "all" : pt1 != null ? "point" + : "matrix") : SV.sValue(args[apt++]).toLowerCase()); + if (bsAtoms == null) + bsAtoms = vwr.getAllAtoms(); + + return (apt == args.length && mp.addXObj(vwr.ms.getSymTemp(false) + .getSymmetryInfoAtom(vwr.ms, bsAtoms, xyz, iOp, pt1, pt2, + desc, 0, 0, nth))); } private boolean evaluateTensor(ScriptMathProcessor mp, SV[] args) Modified: trunk/Jmol/src/org/jmol/symmetry/SymmetryDesc.java =================================================================== --- trunk/Jmol/src/org/jmol/symmetry/SymmetryDesc.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/symmetry/SymmetryDesc.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -63,6 +63,88 @@ "inversionCenter", null /*point*/, "axisVector", "rotationAngle", "matrix", "unitTranslation", "centeringVector", "timeReversal", "plane" }; + private static int getType(String id) { + int type; + if (id.equalsIgnoreCase("matrix")) { + type = T.matrix4f; + } else if (id.equalsIgnoreCase("description")) { + type = T.label; + } else if (id.equalsIgnoreCase("axispoint")) { + type = T.point; + } else if (id.equalsIgnoreCase("time")) { + type = T.times; + } else if (id.equalsIgnoreCase("info")) { + type = T.array; + } else { + // center, draw, plane, axis, translation, angle, array, list + type = T.getTokFromName(id); + if (type == 0) { + for (type = 0; type < keys.length; type++) + if (id.equalsIgnoreCase(keys[type])) + break; + type = (type < keys.length ? -1 - type : T.full); + } + } + return type; + } + + private static Object getInfo(Object[] info, int type) { + if (info == null) + return ""; + if (type < 0 && type >= -keys.length) + return info[-1 - type]; + switch (type) { + case T.array: + Map<String, Object> lst = new Hashtable<String, Object>(); + for (int j = 0, n = info.length; j < n; j++) + if (keys[j] != null && info[j] != null) + lst.put(keys[j], info[j]); + return lst; + // case T.list: + // String[] sinfo = new String[] { + // (String) info[0], + // (String) info[1], + // (String) info[2], + // // skipping DRAW commands here + // Escape.eP((V3) info[4]), Escape.eP((V3) info[5]), + // Escape.eP((P3) info[6]), Escape.eP((P3) info[7]), + // Escape.eP((V3) info[8]), "" + info[9], "" + Escape.e(info[10]), + // "" + info[13] }; + // return sinfo; + case T.angle: + return info[9]; + case T.axes: + return info[8]; + case T.center: + return info[6]; + case T.draw: + return info[3] + "\nprint " + PT.esc(info[0] + " " + info[2]); + case T.full: + return info[0] + " \t" + info[2]; + case T.info: + return info; // internal only; if user selects "info", it is turned into "array" + default: + case T.label: + return info[2]; + case T.matrix4f: + return info[10]; + case T.point: + return info[7]; + // 11: vTrans + // 12: centering + case T.times: + return info[13]; + case T.plane: + return info[14]; + case T.translation: + return info[5]; // cartesian translation + case T.unitcell: + return info[11]; + case T.xyz: + return info[0]; + } + } + /** * * @param op @@ -109,10 +191,9 @@ * */ - private Object[] getDescription(SymmetryOperation op, SymmetryInterface uc, + private Object[] createInfoArray(SymmetryOperation op, SymmetryInterface uc, P3 pta00, P3 ptTarget, String id, ModelSet modelSet, float scaleFactor) { - if (!op.isFinalized) op.doFinalize(); if (scaleFactor == 0) @@ -831,6 +912,31 @@ return pt; } + /** + * multipurpose function handling a variety of tasks, including: + * + * processing of "lattice", "draw", and "point" output types + * + * finding the operator in the given space group + * + * creating a temporary space group for an xyz operator + * + * + * @param sym + * @param iModel + * @param iAtom + * @param uc + * @param xyz + * @param op + * @param pt + * @param pt2 + * @param id + * @param type + * @param modelSet + * @param scaleFactor + * @param nth + * @return a string or an Object[] containing information + */ private Object getSymmetryInfo(Symmetry sym, int iModel, int iAtom, Symmetry uc, String xyz, int op, P3 pt, P3 pt2, String id, int type, @@ -884,9 +990,10 @@ symTemp.toCartesian(sympt, false); return sympt; } - info = getDescription(opTemp, uc, pt, pt2, (id == null ? "sym" : id), + info = createInfoArray(opTemp, uc, pt, pt2, (id == null ? "sym" : id), modelSet, scaleFactor); } else { + // pt1, pt2 boolean isList = (type == T.list); nth = (nth != 0 ? nth : isList ? -1 : 1); Object ret = getSymmetryInfoObject(sym, iModel, op, pt, pt2, null, @@ -895,73 +1002,24 @@ return ret; info = (Object[]) ret; } - if (info == null) - return ""; - /* - * xyz (Jones-Faithful calculated from matrix) - * xyzOriginal (Provided by operation) - * description ("C2 axis", for example) - * translation vector (fractional) - * translation vector (cartesian) - * inversion point - * axis point - * axis vector - * angle of rotation - * matrix representation - * time reversal - */ - switch (type) { - case T.array: - Map<String, Object> lst = new Hashtable<String, Object>(); - for (int j = 0, n = info.length; j < n; j++) - if (keys[j] != null && info[j] != null) - lst.put(keys[j], info[j]); - return lst; - // case T.list: - // String[] sinfo = new String[] { - // (String) info[0], - // (String) info[1], - // (String) info[2], - // // skipping DRAW commands here - // Escape.eP((V3) info[4]), Escape.eP((V3) info[5]), - // Escape.eP((P3) info[6]), Escape.eP((P3) info[7]), - // Escape.eP((V3) info[8]), "" + info[9], "" + Escape.e(info[10]), - // "" + info[13] }; - // return sinfo; - case T.angle: - return info[9]; - case T.axes: - return info[8]; - case T.center: - return info[6]; - case T.draw: - return info[3] + "\nprint " + PT.esc(info[0] + " " + info[2]); - case T.full: - return info[0] + " \t" + info[2]; - case T.info: - return info; // internal only - default: - case T.label: - return info[2]; - case T.matrix4f: - return info[10]; - case T.point: - return info[7]; - // 11: vTrans - // 12: centering - case T.times: - return info[13]; - case T.plane: - return info[14]; - case T.translation: - return info[5]; // cartesian translation - case T.unitcell: - return info[11]; - case T.xyz: - return info[0]; - } + return getInfo(info, type); } + /** + * + * @param sym + * @param modelIndex + * @param symOp + * @param pt1 + * @param pt2 + * @param drawID + * @param type + * @param modelSet + * @param scaleFactor + * @param nth + * @param asString + * @return + */ Object getSymmetryInfoObject(Symmetry sym, int modelIndex, int symOp, P3 pt1, P3 pt2, String drawID, String type, ModelSet modelSet, float scaleFactor, int nth, @@ -969,7 +1027,7 @@ String strOperations = ""; Object[][] infolist; Object ret = (asString ? "" : null); - if (type != null && type.indexOf("y") >= 0) { + if (type != null && type.indexOf(",") >= 0) { // SHOW SYMOP "x,y,...." sym = (Symmetry) modelSet.getSymTemp(true); sym.setSpaceGroup(false); @@ -1092,7 +1150,7 @@ isStandard = false; jf += ";" + op.xyz; Object[] ret = (symOp > 0 && symOp - 1 != iop ? null - : getDescription(op, cellInfo, pt1, pt2, drawID, modelSet, + : createInfoArray(op, cellInfo, pt1, pt2, drawID, modelSet, scaleFactor)); if (ret != null) { if (nth > 0 && ++nop != nth) @@ -1136,25 +1194,8 @@ Object getSymmetryInfoAtom(BS bsAtoms, String xyz, int op, P3 pt, P3 pt2, String id, int type, ModelSet modelSet, float scaleFactor, int nth) { - if (type == 0) { - type = T.xyz; - if (id.equalsIgnoreCase("matrix")) { - type = T.matrix4f; - } else if (id.equalsIgnoreCase("description")) { - type = T.label; - } else if (id.equalsIgnoreCase("axispoint")) { - type = T.point; - } else if (id.equalsIgnoreCase("time")) { - type = T.times; - } else if (id.equalsIgnoreCase("info")) { - type = T.array; - } else { - // center, draw, plane, axis, translation, angle, array, list - type = T.getTokFromName(id); - if (type == 0) - type = T.label; - } - } + if (type == 0) + type = getType(id); int iModel = -1; if (bsAtoms == null) { iModel = modelSet.vwr.am.cmi; Modified: trunk/Jmol/src/org/jmol/symmetry/SymmetryOperation.java =================================================================== --- trunk/Jmol/src/org/jmol/symmetry/SymmetryOperation.java 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/symmetry/SymmetryOperation.java 2016-04-11 19:36:20 UTC (rev 21043) @@ -788,7 +788,7 @@ if (!isFinalized) doFinalize(); if (centering == null && !unCentered) { - if (modDim == 0 && index > 1 && m00 == 1 && m11 == 1 && m22 == 1 + if (modDim == 0 && m00 == 1 && m11 == 1 && m22 == 1 && m01 == 0 && m02 == 0 && m10 == 0 && m12 == 0 && m20 == 0 && m21 == 0 && (m03 != 0 || m13 != 0 || m23 != 0)) { isCenteringOp = true; Modified: trunk/Jmol/src/org/jmol/viewer/Jmol.properties =================================================================== --- trunk/Jmol/src/org/jmol/viewer/Jmol.properties 2016-04-11 03:47:52 UTC (rev 21042) +++ trunk/Jmol/src/org/jmol/viewer/Jmol.properties 2016-04-11 19:36:20 UTC (rev 21043) @@ -74,19 +74,112 @@ TODO: slightly stronger unitcell lines for near point? -Jmol.___JmolVersion="14.5.4_2016.04.08" +Jmol.___JmolVersion="14.5.4_2016.04.11" -new feature: symop() options - -- {atomset}.symop(op, @1, @2, mode) - -- {atomset}.symop(@1, @2, nth, mode) - -- mode can be one of: " - - -- options: - -- just symop(...), not {atomset}.symop(...) uses @1 if present or {*} for setting space group and cell info - -- {atomset}.symop(op, mode) - +bug fix: qchem reader fails to switch to spherical D/F basis for second structure bug fix: pointGroup secondary axis in yellow is too hard to see -- using "orange" instead + +new feature: symop() options: + symop(op) + -- returns the 4x4 matrix representation of this operator + symop(op, atom) + -- returns the point generated by operator op on atom + -- op may be a positive or negative integer indictating the operation (or its reverse) + to apply from the loaded space group -- for example, symop(3, @1) or symop(-4, {atomindex=16}) + -- op may be a string such as "x+1/2,1/2-y,z" representing a specific generic operation + symop(atom1, atom2) + -- returns the description of the first of possibly several operations that take atom1 to atom2, for example: + "2-fold screw axis|translation: 1/2 0 0" + symop(atom1, atom2, n) + -- returns the description of the nth operation that takes atom1 to atom2 + symop(...point...) + -- any place an atom can be used in symop(), one can substitute an xyz coordinate. + -- for example, symop(@1, {1/2 1/2 1/2}) + {atomset}.symop(...) + -- when more than one model is loaded, prepending any symop function with an atom set specifies which + atoms, space group, and unit cell are being referenced. For example, {2.1}.symop(5) operates only on + atoms in the first model of the second loaded file, using the appropriate space group and unit cell. + In this way, "@1" will designate one atom only, provided only one model is showing (using the FRAME/MODEL command). + If only one model has been loaded, there is no need to use this syntax; symop(...) will do the same. + symop(..., outputType) + -- All uses of symop() and {atomset}.symop() can be extended using a final parameter that + changes the default output described above to be something else. Options for outputType include: + + "draw" Returns the Jmol script illustrating this operation with DRAW commands. + + $ print symop(3,"draw") + draw ID draw_* delete + draw ID draw_frame1X diameter 0.15{5.5172 1.9683 2.7802}{6.5172 1.9683 2.7802} color red + ... + + "full" Returns the tab-separated Jones-Faithful string and descriptor for this operation. + + $ print symop(3,"full") + -x,-y,-z(mx,my,mz) Ci: 0 0 0 + + "lattice" Returns the lattice type associated with the space group involving this operation. + + "list" Specifically when two atoms or points are specified, returns a string list of all operations + taking the first to the second. + + $ print symop(@3,@21,"list") + 5 x+1/2,-y+1/2,-z+1/2(-mx,my,mz) 2-fold screw axis|translation: 1/2 0 0|time-reversed + 7 -x+1/2,y+1/2,z+1/2(-mx,my,mz) n-glide plane|translation: 0 1/2 1/2|time-reversed + + Note that this string can be turned into a standard array using .lines.split("\t",true): + + $ print symop(@3,@21,"list").lines.split("\t",true) + [ + 5 + x+1/2,-y+1/2,-z+1/2(-mx,my,mz) + 2-fold screw axis|translation: 1/2 0 0|time-reversed + ] + [ + 7 + -x+1/2,y+1/2,z+1/2(-mx,my,mz) + n-glide plane|translation: 0 1/2 1/2|time-reversed + ] + + "array" Returns an associative array that contains critical information relating to this operation. + + $ load =magndata/0.34 + $ print symop(3,"array") + { + "inversionCenter" : {0.0 0.0 0.0} + "label" : "Ci: 0 0 0" + "matrix" : + [ + [-1.0, 0.0, 0.0, 0.0] + [0.0, -1.0, 0.0, 0.0] + [0.0, 0.0, -1.0, 0.0] + [0.0, 0.0, 0.0, 1.0] ] + "timeReversal" : 1 + "xyz" : "-x,-y,-z(mx,my,mz)" + "xyzOriginal" : "-x,-y,-z,m" + } + + In addition, all possible keys of this array may be used as well for outputType. These include: + + "axisVector", "cartesianTranslation", "centeringVector", "fractionalTranslation", + "inversionCenter", "label", "matrix", "plane", "rotationAngle", + "timeReversal", "unitTranslation", "xyz", and "xyzOriginal" + + Three of these that may be less than obvious are explained below: + + "centeringVector" For operations that are pure lattice translations, returns the vector + for this centering in fractional coordinates. + + "timeReversal" This quantity is 0 for standard space groups. Magnetic space group + operations also include the possibility of inversion of the spin + along with any 3D symmetry operation. This inversion characteristic + is referred to as "time reversal" and takes the value of 1 or -1. + + "unitTranslation" Symmetry operations involving two atoms may include an extra + lattice translation if the two atoms are in different unit cells. + This translation is above and beyond any fractional lattice centering + that this operator incorporates for a face- or body-centered space group. + new feature: show spacegroup/xxxxx -- selects lines from a space group report similar to the way show state/xxxx works @@ -99,25 +192,22 @@ -- gives full list of matching symmetry operations -- example: - $ load =magndata/0.34 {2 2 1} packed + $ load =magndata/1.23 {444 555 1} packed $ show symop @153 @299 - 4 symmetry operations: - 1 x+2,y,z2 translation: 6/3 0 -6/3 - 5 -x,-y,-z(mx,my,mz) Ci: 0 0 0 - 11 x+2,-y,-z(-mx,my,mz) 2-fold screw axis|translation: 6/3 0 0|time-reversed - 15 -x,y,z2(-mx,my,mz) c-glide plane|translation: 0 0 -6/3|time-reversed - - + 1 x+2,y,z2(mx,my,mz) translation: 2 0 -2 + 5 -x,-y,-z(mx,my,mz) Ci: 0 0 0 + 11 x+2,-y,-z(-mx,my,mz) 2-fold screw axis|translation: 2 0 0|time-reversed + 15 -x,y,z2(-mx,my,mz) c-glide plane|translation: 0 0 -2|time-reversed + new feature: show/draw symop @1 @2 n -- shows or draws the nth symmetry operation relating atom 1 to atom 2 -- example: - $ load =magndata/0.34 {2 2 1} packed + $ load =magndata/1.23 {444 555 1} packed $ show symop @153 @299 3 - 5 -x,-y,-z(mx,my,mz) Ci: 0 0 0 - + 11 x+2,-y,-z(-mx,my,mz) 2-fold screw axis|translation: 2 0 0|time-reversed new feature: print pointgroup("spacegroup", @1) -- analyzes the point group (crystal class) of a crystal. This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. ------------------------------------------------------------------------------ Find and fix application performance issues faster with Applications Manager Applications Manager provides deep performance insights into multiple tiers of your business applications. It resolves application problems quickly and reduces your MTTR. Get your free trial! https://ad.doubleclick.net/ddm/clk/302982198;130105516;z _______________________________________________ Jmol-commits mailing list Jmol-commits@lists.sourceforge.net https://lists.sourceforge.net/lists/listinfo/jmol-commits