1 /* $RCSfile$
2  * $Author: hansonr $
3  * $Date: 2006-08-22 03:13:40 -0500 (Tue, 22 Aug 2006) $
4  * $Revision: 5412 $
5 
6  *
7  * Copyright (C) 2002-2005  The Jmol Development Team
8  *
9  * Contact: jmol-developers@lists.sf.net
10  *
11  *  This library is free software; you can redistribute it and/or
12  *  modify it under the terms of the GNU Lesser General Public
13  *  License as published by the Free Software Foundation; either
14  *  version 2.1 of the License, or (at your option) any later version.
15  *
16  *  This library is distributed in the hope that it will be useful,
17  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
18  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
19  *  Lesser General License for more details.
20  *
21  *  You should have received a copy of the GNU Lesser General Public
22  *  License along with this library; if not, write to the Free Software
23  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
24  */
25 
26 package org.jmol.shape;
27 
28 import javajs.util.AU;
29 
30 import org.jmol.atomdata.RadiusData;
31 import org.jmol.atomdata.RadiusData.EnumType;
32 import org.jmol.c.PAL;
33 import org.jmol.c.VDW;
34 import javajs.util.BS;
35 import org.jmol.modelset.Atom;
36 import org.jmol.util.BSUtil;
37 import org.jmol.util.C;
38 import org.jmol.viewer.JC;
39 
40 public abstract class AtomShape extends Shape {
41 
42   // Balls, BioShape Dots, Ellipsoids, Halos, Labels, Polyhedra, Stars, Vectors
43 
44   public short mad = (short)-1;
45   public short[] mads;
46   public short[] colixes;
47   public byte[] paletteIDs;
48   public int ac;
49   public Atom[] atoms;
50   public boolean isActive;
51 
52   public int monomerCount;
53   public BS bsSizeDefault;
54 
55   @Override
initShape()56   public void initShape() {
57     // nothing  to do
58   }
59 
60   @Override
initModelSet()61   protected void initModelSet() {
62     atoms = ms.at;
63     ac = ms.ac;
64     // in case this is due to "load append"
65     if (mads != null)
66       mads = AU.arrayCopyShort(mads, ac);
67     if (colixes != null)
68       colixes = AU.arrayCopyShort(colixes, ac);
69     if (paletteIDs != null)
70       paletteIDs = AU.arrayCopyByte(paletteIDs, ac);
71   }
72 
73   @Override
getSize(int atomIndex)74   public int getSize(int atomIndex) {
75     return (mads == null ? 0 : mads[atomIndex]);
76   }
77 
78   @Override
setSize(int size, BS bsSelected)79   protected void setSize(int   size, BS bsSelected) {
80     setSize2(size, bsSelected);
81   }
82 
83   private RadiusData rd;
84 
setSize2(int size, BS bsSelected)85   protected void setSize2(int size, BS bsSelected) {
86     if (size == 0) {
87       setSizeRD(null, bsSelected);
88       return;
89     }
90     if (rd == null)
91       rd = new RadiusData(null, size, EnumType.SCREEN, null);
92     else
93       rd.value = size;
94     setSizeRD(rd, bsSelected);
95   }
96 
97   @Override
setSizeRD(RadiusData rd, BS bsSelected)98   protected void setSizeRD(RadiusData rd, BS bsSelected) {
99     // Halos Stars Vectors
100     if (atoms == null)  // vector values are ignored if there are none for a model
101       return;
102     isActive = true;
103     boolean isVisible = (rd != null && rd.value != 0);
104     boolean isAll = (bsSelected == null);
105     int i0 = (isAll ? ac - 1 : bsSelected.nextSetBit(0));
106     if (bsSizeSet == null)
107       bsSizeSet = BS.newN(ac);
108     if (mads == null && i0 >= 0)
109       mads = new short[ac];
110     for (int i = i0; i >= 0; i = (isAll ? i - 1 : bsSelected.nextSetBit(i + 1)))
111       setSizeRD2(i, rd, isVisible);
112   }
113 
setSizeRD2(int i, RadiusData rd, boolean isVisible)114   protected void setSizeRD2(int i, RadiusData rd, boolean isVisible) {
115     Atom atom = atoms[i];
116     mads[i] = atom.calculateMad(vwr, rd);
117     bsSizeSet.setBitTo(i, isVisible);
118     atom.setShapeVisibility(vf, isVisible);
119   }
120 
setPropAS(String propertyName, Object value, BS bs)121   protected void setPropAS(String propertyName, Object value, BS bs) {
122     if ("color" == propertyName) {
123       isActive = true;
124       short colix = C.getColixO(value);
125       byte pid = PAL.pidOf(value);
126       int n = checkColixLength(colix, bs.length());
127       for (int i = bs.nextSetBit(0); i >= 0 && i < n; i = bs.nextSetBit(i + 1))
128         setColixAndPalette(colix, pid, i);
129       return;
130     }
131     if ("params" == propertyName) {
132       // PyMOL only
133       isActive = true;
134       Object[] data = (Object[]) value;
135       short[] colixes = (short[]) data[0];
136       float[] atrans = (float[]) data[1];
137       float[] sizes = (float[]) data[2];
138       RadiusData rd = new RadiusData(null, 0, RadiusData.EnumType.FACTOR,
139           VDW.AUTO);
140       if (bsColixSet == null)
141         bsColixSet = new BS();
142       if (bsSizeSet == null)
143         bsSizeSet = new BS();
144       int i0 = bs.nextSetBit(0);
145       if (mads == null && i0 >= 0)
146         mads = new short[ac];
147 
148       int n = checkColixLength(colixes == null ? 0 : C.BLACK, bs.length());
149       for (int i = i0, pt = 0; i >= 0 && i < n; i = bs.nextSetBit(i + 1), pt++) {
150         short colix = (colixes == null ? 0 : colixes[pt]);
151         //if (colix == 0)
152           //colix = C.INHERIT_ALL;  IS 0 already
153         float f = (atrans == null ? 0 : atrans[pt]);
154         if (f > 0.01f)
155           colix = C.getColixTranslucent3(colix, true, f);
156         setColixAndPalette(colix, PAL.UNKNOWN.id, i);
157         if (sizes == null)
158           continue;
159         boolean isVisible = ((rd.value = sizes[pt]) > 0);
160         setSizeRD2(i, rd, isVisible);
161       }
162       return;
163     }
164     if ("translucency" == propertyName) {
165       isActive = true;
166       boolean isTranslucent = (value.equals("translucent"));
167       checkColixLength(C.BLACK, ac);
168       for (int i = bs.nextSetBit(0); i >= 0; i = bs.nextSetBit(i + 1)) {
169         colixes[i] = C.getColixTranslucent3(colixes[i], isTranslucent,
170             translucentLevel);
171         if (isTranslucent)
172           bsColixSet.set(i);
173       }
174       return;
175     }
176     if (propertyName == "deleteModelAtoms") {
177       atoms = (Atom[]) ((Object[]) value)[1];
178       int[] info = (int[]) ((Object[]) value)[2];
179       ac = ms.ac;
180       int firstAtomDeleted = info[1];
181       int nAtomsDeleted = info[2];
182       mads = (short[]) AU.deleteElements(mads, firstAtomDeleted,
183           nAtomsDeleted);
184       colixes = (short[]) AU.deleteElements(colixes, firstAtomDeleted,
185           nAtomsDeleted);
186       paletteIDs = (byte[]) AU.deleteElements(paletteIDs,
187           firstAtomDeleted, nAtomsDeleted);
188       BSUtil.deleteBits(bsSizeSet, bs);
189       BSUtil.deleteBits(bsColixSet, bs);
190       return;
191     }
192     setPropS(propertyName, value, bs);
193   }
194 
checkColixLength(short colix, int n)195   protected int checkColixLength(short colix, int n) {
196     n = Math.min(ac, n);
197     if (colix == C.INHERIT_ALL)
198       return (colixes == null ? 0 : colixes.length);
199     if (colixes == null || n > colixes.length) {
200       colixes = AU.ensureLengthShort(colixes, n);
201       paletteIDs = AU.ensureLengthByte(paletteIDs, n);
202     }
203     if (bsColixSet == null)
204       bsColixSet = BS.newN(ac);
205     return n;
206   }
207 
setColixAndPalette(short colix, byte paletteID, int atomIndex)208   protected void setColixAndPalette(short colix, byte paletteID, int atomIndex) {
209     if (colixes == null) {
210       checkColixLength((short)-1, ac);
211     }
212     colixes[atomIndex] = colix = getColixI(colix, paletteID, atomIndex);
213     bsColixSet.setBitTo(atomIndex, colix != C.INHERIT_ALL || shapeID == JC.SHAPE_BALLS);
214     paletteIDs[atomIndex] = paletteID;
215   }
216 
217   @Override
setAtomClickability()218   public void setAtomClickability() {
219     if (!isActive)
220       return;
221     for (int i = ac; --i >= 0;) {
222       Atom atom = atoms[i];
223       if (atom == null || (atom.shapeVisibilityFlags & vf) == 0
224           || ms.isAtomHidden(i))
225         continue;
226       atom.setClickable(vf);
227     }
228   }
229 
230   /**
231    * @param i
232    * @return script, but only for Measures
233    */
getInfoAsString(int i)234   public String getInfoAsString(int i) {
235     // only in Measures
236     return null;
237   }
238 
239   @Override
getShapeState()240   public String getShapeState() {
241    // implemented in StateCreator, not here
242    return null;
243  }
244 }
245